How to configure Jenkins to run on port 80
Asked Answered
A

14

53

I'm running Ubuntu 11.10 and have run sudo apt-get install jenkins to install Jenkins on this system.

I've seen some tutorials on how to setup a reverse proxy (Apache, Nginx, etc), however this is a VM dedicated for just jenkins and I'd like keep it as lean as possible while having jenkins running on port 80.

I've found the upstart config in /etc/init/jenkins.conf and modified the port to 80 env HTTP_PORT=80

When I start jenkins via service jenkins start, ps reveals that it runs for a few seconds then terminates.

Is this because jenkins is running as the jenkins user on a privileged port? If so, how do I fix this? Any other ideas a welcome.

Here is the upstart config:

description "jenkins: Jenkins Continuous Integration Server"
author "James Page <[email protected]>"

start on (local-filesystems and net-device-up IFACE!=lo)
stop on runlevel [!2345]

env USER="jenkins"
env GROUP="jenkins"
env JENKINS_LOG="/var/log/jenkins"
env JENKINS_ROOT="/usr/share/jenkins"
env JENKINS_HOME="/var/lib/jenkins"
env JENKINS_RUN="/var/run/jenkins"
env HTTP_PORT=80
env AJP_PORT=-1
env JAVA_OPTS=""
env JAVA_HOME="/usr/lib/jvm/default-java"

limit nofile 8192 8192

pre-start script
    test -f $JENKINS_ROOT/jenkins.war || { stop ; exit 0; }
    $JENKINS_ROOT/bin/maintain-plugins.sh   
    mkdir $JENKINS_RUN > /dev/null 2>&1  || true
    chown -R $USER:$GROUP $JENKINS_RUN || true
end script

script
    JENKINS_ARGS="--webroot=$JENKINS_RUN/war --httpPort=$HTTP_PORT --ajp13Port=$AJP_PORT"
    exec daemon --name=jenkins --inherit --output=$JENKINS_LOG/jenkins.log --user=$USER \
        -- $JAVA_HOME/bin/java $JAVA_OPTS -jar $JENKINS_ROOT/jenkins.war $JENKINS_ARGS \
        --preferredClassLoader=java.net.URLClassLoader
end script
Aircraftman answered 17/2, 2012 at 14:54 Comment(0)
A
33

Give a try to 'authbind':

sudo apt-get install authbind
sudo touch /etc/authbind/byport/80
sudo chmod 500 /etc/authbind/byport/80 
sudo chown jenkins /etc/authbind/byport/80

Then modify the script above to have (add authbind before the $JAVA_HOME/bin/java part):

exec daemon --name=jenkins --inherit --output=$JENKINS_LOG/jenkins.log \
--user=$USER -- authbind $JAVA_HOME/bin/java $JAVA_OPTS \
-jar $JENKINS_ROOT/jenkins.war $JENKINS_ARGS \
--preferredClassLoader=java.net.URLClassLoader

For newer Jenkins installations (1.598) on newer Ubuntu installations (14.04) edit /etc/init.d/jenkins and add authbind before $JAVA

$SU -l $JENKINS_USER --shell=/bin/bash -c "$DAEMON $DAEMON_ARGS -- authbind $JAVA $JAVA_ARGS -jar $JENKINS_WAR $JENKINS_ARGS" || return 2

As mentioned by Alan (see comment below) if you need IPv6 and your system is lower than Quantal you can instead of using apt-get to install authbind download a higher version. Make sure you have libc6 and libc6-udeb installed. Here is authbind version 2.1.1 from Ubuntu:

Then execute:

sudo dpkg -i authbind_2.1.1_amd64.deb
# or sudo dpkg -i authbind_2.1.1_i386.deb

sudo touch /etc/authbind/byport/80
sudo chmod 500 /etc/authbind/byport/80 
sudo chown jenkins /etc/authbind/byport/80
Alderete answered 17/2, 2012 at 15:32 Comment(7)
Thanks! Referencing the man pageAircraftman
Note to future users of this approach: I'm using Ubuntu 12.04 (Precise) with Jenkins 1.495. The authbind version in Precise is 1.20build3. authbind didn't support ipv6 until 2.0, so I had to use apt pinning to force installation of the authbind version from Quantal (2.1.1). Just FYI in case anyone found this solution but it wasn't working for them. IPv6 may be the problem!Resupinate
Thank you. Didn't know about authbind before. Still don't know how they do that. Have to read sources. However, it worked. Jenkins now on port 80 :)Kerseymere
This didn't work for me until I upgraded to authbind 2.1.1 as suggested (installed was 1.0). It worked for 'nc -l localhost 80' but failed when running 'java /usr/share/jenkins/jenkins.war --httpPort=80'. Upgrading to 2.1.1 made it all good. Note I wasn't using IPv6 specifically, so it seems it just doesn't work with jenkins before this version.Charitycharivari
One thing to add; I also had to use 'authbind --deep' for it to work. So new version + --deep = jenkins on port 80.Charitycharivari
I cannot find authbind or its equivalent for CentOs.Extensity
could never make this work. authbind 2.1.1, turned off ipv6, passed -Djava.net.preferIPv4Stack=true to java, made sure I could make it work with nc -l 0.0.0 80 etc. - ended up using the iptables portforward belowIridosmine
E
50

Another solution is to simply use iptables to reroute incoming traffic from 80 to 8080. The rules would look like:

-A INPUT -i eth0 -p tcp --dport 80 -j ACCEPT
-A INPUT -i eth0 -p tcp --dport 8080 -j ACCEPT
-A PREROUTING -t nat -i eth0 -p tcp --dport 80 -j REDIRECT --to-port 8080

Reformatted as an iptables.rules file:

*filter
:INPUT ACCEPT [100:100000]
:FORWARD ACCEPT [0:0]
:OUTPUT ACCEPT [95:9000]
-A INPUT -i eth0 -p tcp --dport 80 -j ACCEPT
-A INPUT -i eth0 -p tcp --dport 8080 -j ACCEPT
COMMIT

*nat
-A PREROUTING -i eth0 -p tcp --dport 80 -j REDIRECT --to-port 8080
COMMIT

The advantage of a iptable.rules file is the rules can persist after reboots. Just make sure to integrate any other current iptable rules into the same file!

On Redhat/CentOS this file can go in /etc/sysconfig/iptables.

On Debian/Ubuntu systems they can be saved in /etc/iptables/rules.v4 by using the iptables-persistent package. Or the iptable.rules can be called by modifying /etc/network/interfaces or hooking into if-up/if-down scripts. The Ubuntu Community wiki has a great page explaining these methods.

As is usually the case with networking, there's a lot of different ways to accomplish the same result. Use what works best for you!

Epochal answered 15/1, 2013 at 22:8 Comment(3)
for localhost usage you will also need: iptables -A OUTPUT -t nat -p tcp -o lo --dport 80 -j REDIRECT --to-port 8080Darksome
There's also a Jenkins wiki documenting this.Eweneck
Solved the issueAirflow
A
37
  1. Go to /etc/default folder --> Open the file "jenkins"
  2. Modify the line HTTP_PORT=8080 as HTTP_PORT=80
  3. Start jenkins as root by using the command: sudo /etc/init.d/jenkins start
  4. Open a browser and browse as localhost:80

that's it

Adriell answered 10/1, 2013 at 12:18 Comment(14)
for step #3, what user are you starting it with?Aircraftman
for step #3: you can start as root. Or, it's not root user use "sudo" as sudo /etc/init.d/jenkins startAdriell
I've made the change you mentioned and am getting what seems to be a port 80 error in the jenkins log. The snip is:Caused by: java.io.IOException: Failed to listen on port 80 at winstone.HttpListener.getServerSocket(HttpListener.java:119) at winstone.HttpListener.start(HttpListener.java:72) at winstone.Launcher.spawnListener(Launcher.java:220) ... 8 more Caused by: java.net.BindException: Permission deniedAircraftman
Is there any other application running on port 80? please checkAdriell
@hafichuk: Can you please check it by doing change the port as any other value? (e.g. 8888, or 88 etc.)Adriell
It ran on 8080 with no problems.Aircraftman
No other applications are using port 80.Aircraftman
I don't really understand why this answer is not upvoted and instead you try to do some weird workarounds. I did exactly as Ripon suggested and works like a charm. Just one line of configuration. hafichuk has problems with 'permission denied' exception probably because he's not runnig jenkins with root privileges! Linux ports <1024 are restricted to be bound by non-root users.Midday
Starting a webapplication as root is a terrible idea. It is much better to configure Apache HTTPD or redirect with the iptables trick explained in the other answers.Cuddy
Agree that running as root is a bad idea, but I was referring to the particular problem. We can run it as a separate user, chroot it and so forth - Ripon solution would be fine for all these cases.Midday
@PiotrekDe the reason it's not upvoted is because it doesn't work. When I change HTTP_PORT to 80 from 8080, Jenkins fails to start. Here's the backtrace I got: gist.github.com/tubbo/305164071d00409f6259Scarlett
You just suggest another way of setting up jenkins port. In case jenkins not running as root, it will face the same problem described in question.Grisham
It will not work if the port you are trying to configure it to is already being used. I tried 8181 and it failed to start. But 9090 worked for me. Also, one may need sudo for Step#3. ThanksDenver
Yes, the port you want to use must free, I mean it should be unused.Adriell
A
33

Give a try to 'authbind':

sudo apt-get install authbind
sudo touch /etc/authbind/byport/80
sudo chmod 500 /etc/authbind/byport/80 
sudo chown jenkins /etc/authbind/byport/80

Then modify the script above to have (add authbind before the $JAVA_HOME/bin/java part):

exec daemon --name=jenkins --inherit --output=$JENKINS_LOG/jenkins.log \
--user=$USER -- authbind $JAVA_HOME/bin/java $JAVA_OPTS \
-jar $JENKINS_ROOT/jenkins.war $JENKINS_ARGS \
--preferredClassLoader=java.net.URLClassLoader

For newer Jenkins installations (1.598) on newer Ubuntu installations (14.04) edit /etc/init.d/jenkins and add authbind before $JAVA

$SU -l $JENKINS_USER --shell=/bin/bash -c "$DAEMON $DAEMON_ARGS -- authbind $JAVA $JAVA_ARGS -jar $JENKINS_WAR $JENKINS_ARGS" || return 2

As mentioned by Alan (see comment below) if you need IPv6 and your system is lower than Quantal you can instead of using apt-get to install authbind download a higher version. Make sure you have libc6 and libc6-udeb installed. Here is authbind version 2.1.1 from Ubuntu:

Then execute:

sudo dpkg -i authbind_2.1.1_amd64.deb
# or sudo dpkg -i authbind_2.1.1_i386.deb

sudo touch /etc/authbind/byport/80
sudo chmod 500 /etc/authbind/byport/80 
sudo chown jenkins /etc/authbind/byport/80
Alderete answered 17/2, 2012 at 15:32 Comment(7)
Thanks! Referencing the man pageAircraftman
Note to future users of this approach: I'm using Ubuntu 12.04 (Precise) with Jenkins 1.495. The authbind version in Precise is 1.20build3. authbind didn't support ipv6 until 2.0, so I had to use apt pinning to force installation of the authbind version from Quantal (2.1.1). Just FYI in case anyone found this solution but it wasn't working for them. IPv6 may be the problem!Resupinate
Thank you. Didn't know about authbind before. Still don't know how they do that. Have to read sources. However, it worked. Jenkins now on port 80 :)Kerseymere
This didn't work for me until I upgraded to authbind 2.1.1 as suggested (installed was 1.0). It worked for 'nc -l localhost 80' but failed when running 'java /usr/share/jenkins/jenkins.war --httpPort=80'. Upgrading to 2.1.1 made it all good. Note I wasn't using IPv6 specifically, so it seems it just doesn't work with jenkins before this version.Charitycharivari
One thing to add; I also had to use 'authbind --deep' for it to work. So new version + --deep = jenkins on port 80.Charitycharivari
I cannot find authbind or its equivalent for CentOs.Extensity
could never make this work. authbind 2.1.1, turned off ipv6, passed -Djava.net.preferIPv4Stack=true to java, made sure I could make it work with nc -l 0.0.0 80 etc. - ended up using the iptables portforward belowIridosmine
E
7

I'd suggest using apache and mod_proxy. This is what I do, and my vhost config looks kinda like this (I also redirect for SSL but you can omit that):

<VirtualHost *:443>
ServerAdmin [email protected]
ServerName ci.example.com

ProxyRequests Off
<Proxy *>
    Order deny,allow
    Allow from all
</Proxy>
ProxyPreservehost on
ProxyPass / http://localhost:8080/

Header edit Location ^http://ci.example.com/ https://ci.example.com/

SSLEngine on
SSLCertificateFile /etc/apache2/keys/apache.pem
</VirtualHost>
Excurrent answered 24/4, 2012 at 17:7 Comment(2)
I tried the authbind method since it looked the most correct, but couldn't get it to work. This is what I ended up having to do (since I didn't want to worry about IP tables). Btw, for some setup info for mod_proxy on Ubuntu, see here: abhirama.wordpress.com/2008/11/03/apache-mod_proxy-in-ubuntuKirven
Omitting the SSL to <VirtualHost *:80> is also ok, it works for me.Byer
Q
6

You can achieve this using the following methods.

  1. An IP table forwarding rule.
  2. Using a reverse proxy like Nginx.
  3. Running Jenkins behind a load balancer.

Method 1: Running Jenkins On 80 Using IP Table Forwarding Rule

sudo iptables -t nat -A PREROUTING -p tcp --dport 80 -j REDIRECT --to-ports 8080

Now, you should save these rules so that it will persist even after an IPtable or a system restart.

For Redhat based systems, run the following.

sudo iptables-save > /etc/sysconfig/iptables

For Debian based systems, execute the following command.

sudo sh -c "iptables-save > /etc/iptables.rules"

Now if you access Jenkins on port 80, IP table will automatically forward the requests to 8080.

Method 2: Running Jenkins Behind Nginx Reverse Proxy

Step1: Install Nginx

sudo yum install nginx

Step 2: Open the Nginx configuration file.

sudo vi /etc/nginx/nginx.conf

Step 3: Find the following snippet in the nginx.conf file.

location / {
}

Step 4: Add the following lines between the curly braces.

proxy_pass http://127.0.0.1:8080;
proxy_redirect off;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;

Step 5: Execute the SELinux command for the Nginx reverse proxy.

sudo setsebool httpd_can_network_connect 1 -P

Step 6: Restart the Nginx server.

sudo systemctl restart nginx

Now if you will be able to access Jenkins on port 80.

Method 3: Jenkins Behind A Load Balancer

Adding a load balancer will add extra cost to the Jenkins setup. If you are on a cloud, you can opt for a cloud-specific load balancer which will send all its port 80 traffic to backend Jenkins 8080 port.

Quadrangle answered 21/2, 2019 at 14:17 Comment(0)
M
1

Since I used docker. You can use it to run jenkins on port 80, hereafter a snippet of my script:

JENKINS_PORT=80
JENKINS_HOME=/home/jenkins
/usr/bin/docker run -d -p $JENKINS_PORT:8080 -v $JENKINS_HOME jenkins
Metallography answered 13/5, 2015 at 13:6 Comment(0)
C
1

I had the same problem and I found the best solution to it using iptables.

By default Jenkins runs on ports 8080 or 8443. And HTTP/HTTPS servers run on ports 80 and 443.

But this is these are the special ports and the process using them must be owned by root.

But running Jenkins as root is not the best solution(it should be run as its own user) and so does to run Jenkins with a web server such as Apache, and let it proxy requests to Jenkins

The best solution is to use iptables on Linux to forward traffic.

1) Use this command to list the current iptables configuration:

$ iptables -L -n

target     prot opt source               destination
ACCEPT     tcp  --  0.0.0.0/0            0.0.0.0/0            tcp dpt:8443
ACCEPT     tcp  --  0.0.0.0/0            0.0.0.0/0            tcp dpt:8080
ACCEPT     tcp  --  0.0.0.0/0            0.0.0.0/0            tcp dpt:443
ACCEPT     tcp  --  0.0.0.0/0            0.0.0.0/0            tcp dpt:80

2) If you don't see above entries, then you need to run below commands:

sudo iptables -I INPUT 1 -p tcp --dport 8443 -j ACCEPT

sudo iptables -I INPUT 1 -p tcp --dport 8080 -j ACCEPT

sudo iptables -I INPUT 1 -p tcp --dport 443 -j ACCEPT

sudo iptables -I INPUT 1 -p tcp --dport 80 -j ACCEPT

3) Now re-run the $ iptables -L -n command and verify that you are seeing 1st step o/p.

4) The final step is to run the below commands to forward port 80 traffic to 8080, and port 443 traffic to 8443(if you are using HTTPS).

sudo iptables -A PREROUTING -t nat -i eth0 -p tcp --dport 80 -j REDIRECT --to-port 8080

sudo iptables -A PREROUTING -t nat -i eth0 -p tcp --dport 443 -j REDIRECT --to-port 8443

5) Now your URL should stay on port 80

You can find the more details here.

Carnival answered 16/10, 2018 at 14:36 Comment(0)
E
1

Run these lines of code individually:

sudo iptables -t nat -A PREROUTING -p tcp --dport 80 -j REDIRECT --to-ports 8080
sudo iptables -t nat -I OUTPUT -p tcp -d 127.0.0.1 --dport 80 -j REDIRECT --to-ports 8080

If your system is Debian-based, run:

sudo sh -c "iptables-save > /etc/iptables.rules"

If your system is RedHat-based:

sudo iptables-save > /etc/sysconfig/iptables

This process will change your default Jenkins port from 8080 to 80.

Epiphragm answered 11/4, 2019 at 15:40 Comment(0)
T
0

the firewalld way to forward port 8080 to 80:

yum install firewalld
systemctl start firewalld
chkconfig firewalld on
firewall-cmd --permanent --zone=external --change-interface=eth0
firewall-cmd --permanent --zone=external --add-forward-port=port=80:proto=tcp:toport=8080
Thereon answered 24/11, 2014 at 23:25 Comment(0)
C
0

None of the answers tells how to simply redirect 80 to 8080 with iptables.
Fortunately, dskrvk's comment does !

There's also a Jenkins wiki documenting this


I just had to copy/paste those lines in my terminal to get the redirect working :

sudo iptables -I INPUT 1 -p tcp --dport 8443 -j ACCEPT
sudo iptables -I INPUT 1 -p tcp --dport 8080 -j ACCEPT
sudo iptables -I INPUT 1 -p tcp --dport 443 -j ACCEPT
sudo iptables -I INPUT 1 -p tcp --dport 80 -j ACCEPT
sudo iptables -A PREROUTING -t nat -i eth0 -p tcp --dport 80 -j REDIRECT --to-port 8080
sudo iptables -A PREROUTING -t nat -i eth0 -p tcp --dport 443 -j REDIRECT --to-port 8443

Btw, don't forget to include it to your server's init scripts once tested, or you'll lose the redirect after a reboot. Tested on Debian 8.2 (Jessie)

Cerotype answered 5/1, 2017 at 17:33 Comment(2)
You should check out Chris Laskey's answer from a couple years ago. It also shows you how to make the change permanent.Aircraftman
@Aircraftman Yeah, but... I actually didn't want to try thoses for at least two reasons : (1) I didn't really know where I should put those (2) I wanted to try the rules before actually putting them in a file. You may tell me I can create a specific file and run it just once in case I screw something, but what I needed was a list of commands making things work, not a file's content to put "somewhere", and run with "some command". Since I'm not familiar with iptables, the "some' I speak of aren't quite clear to me.Cerotype
T
0

In Ubuntu 16.04, this wiki explains how to do it.

sudo nano /etc/rc.local

Then add the following just before the exit 0

#Requests from outside
iptables -t nat -A PREROUTING -p tcp --dport 80 -j REDIRECT --to-ports 8080
#Requests from localhost
iptables -t nat -I OUTPUT -p tcp -d 127.0.0.1 --dport 80 -j REDIRECT --to-ports 8080

Now reboot or run sudo /etc/rc.local to enable port forwarding

Trypanosome answered 20/3, 2018 at 9:8 Comment(0)
P
0

changing /etc/default/jenkins doesn't work on my setup ubunutu 16.-4 Jenkins 2.89.4 and the solution to use iptable routes 80 to 8080 whis the opposite of the required result of running jenkins on 80

Plascencia answered 13/5, 2018 at 17:19 Comment(0)
F
0

Building on other answers in this question: You could use an Nginx side-car container if you're on ECS like I was. A super simple nginx config to the tune of something like

user  nginx;
worker_processes  1;

error_log  /var/log/nginx/error.log warn;
pid        /var/run/nginx.pid;

events {
    worker_connections  1024;
}

http {

    server {
        listen 80;
        location / {
            proxy_pass http://localhost:8080;
            proxy_redirect off;
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_set_header X-Forwarded-Proto $scheme;
        }
    }
}

should be enough to forward all incoming trafic from port 80->8080. You can then bind this container to port 80, and voila - Jenkins now "resides" on port 80.

Frenum answered 18/12, 2019 at 17:51 Comment(0)
A
0

If you're running jenkins via the 'official' systemd service files, the solution nowadays is pretty simple and documented in the service file:

You have to be root or use sudo for this, of course. Open /lib/systemd/system/jenkins.service and find the line that says:

Environment="JENKINS_PORT=8080"

and change it to

Environment="JENKINS_PORT=80"

The comment in the .service file tells you what to do next, which is to enable another option which will allow jenkins to bind to a priviledged port (<1024). For that, uncomment the 'AmbientCapabilities' line, which should then say:

AmbientCapabilities=CAP_NET_BIND_SERVICE

After that, reload the service files via systemctl daemon-reload and restart the jenkins service via systemctl restart jenkins and it should run on port 80.

Americaamerican answered 9/9, 2022 at 12:28 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.