Mont
Mont

Reputation: 175

docker runs image on wrong port

I have a spring boot application and I created dockerfile like this one :

FROM java:8
EXPOSE 80
ADD /target/test-server.jar test-server.jar
ENTRYPOINT ["java","-jar","test-server.jar"]

Next I follow these steps :

  1. docker build -t test-server .

  2. docker run -p 8888:80 -t test-server

and it works but on port 8080 , which is default to tomcat. I want it to run on 8888

Results from docker ps

3debfb5a9084        test-server       "java -jar test-ser"   About a minute ago   Up About a minute   0.0.0.0:8888->80/tcp   thirsty_euclid

Btw, why it shows test-ser rather than test-server ?

Generally, I want to be able to run this server on few different ports

Result from command

nmap -A -p8080,8888 localhost

is

Starting Nmap 7.12 ( https://nmap.org ) at 2016-12-05 20:49 CET
Nmap scan report for localhost (127.0.0.1)
Host is up (0.000059s latency).
PORT     STATE  SERVICE    VERSION
8080/tcp closed http-proxy
8888/tcp open   tcpwrapped

Service detection performed. Please report any incorrect results at https://nmap.org/submit/ .
Nmap done: 1 IP address (1 host up) scanned in 5.45 seconds

Upvotes: 3

Views: 6169

Answers (2)

Andreas Jägle
Andreas Jägle

Reputation: 12240

There are different ports to take into consideration.

First there is your application that binds on a port. For spring boot this defaults to 8080, which is the port number the process is bound to inside the container.

With the EXPOSE instruction in your Dockerfile you say which ports should be exposed on the container's network interface. So if you start another container accessing the given one directly, you only get access to ports that are exposed. The exposed ports should in most cases match the port numbers the process inside the container binds to.

The third option is the port mapping you define when running a container. That basically says: Open a port on the docker host and route all traffic to the container on the latter port.

So all in all your current setup says:

  • open port 8888 on my docker host
  • map all traffic on 8888 of my docker host to the container's port 80
  • the container exposes port 80
  • in the container there is no process that is bound to port 80
  • the spring boot application is bound to port 8080 inside by default

So, there are different options. You can either expose port 8080 in your Dockerfile and map the ports as -p 8888:8080. If you want your process to run on a specific port inside the container, you can add the configuration property when starting the spring application like --server.port=8888. But be aware that this only affects the port where the java application is bound to and not which port you are accessing it later on. The EXPOSE must always match the internally used port to have access to the process running inside.

One additional information: By mapping a port like -p 8888:8080 you also open up the port 8080 on your container (which can be seen as some kind of exposing the internal port. What happens is the same. There is an iptables rule added such that the port of the container (here 8080) is accessible. So the EXPOSE instruction is relevant for container-to-container communication when there is no port mapping to the host.

Upvotes: 2

BMitch
BMitch

Reputation: 263469

It's a bit difficult to understand from your comments, but it appears that your application is listening on port 8080 inside your container, but you've mapped port 8888 on the host to port 80 inside the container with docker run -p 8888:80 -t test-server. This will result in the unreachable port that you're seeing. You can map to port 8080 with:

docker run -p 8888:8080 -t test-server

Or, since you're using spring boot, you can set the value of server.port in your application properties to port 80 if you want to change the listening port.

Upvotes: 4

Related Questions