Marvin
Marvin

Reputation: 3045

What is the interaction between docker run "--publish" and "--publish-all"?

I couldn't find this documented. Suppose I wanted to publish one port to a known place, but sometime publish all the other "exposed" ports for debugging or testing.

A simple Dockerfile

FROM alpine
CMD /bin/sleep 600

--publish/-p allows me to bind a specific host port to a container port. --publish-all/-P binds all container ports to random ports, which can be found using, for example docker ps.

$ docker build -t foo .
<build prints>
$ docker run -d -p 8000:8000 -P -p 9000:9000 foo
<some id prints>
$ docker ps --format '{{.Command}} {{.Ports}}'
"/bin/sh -c '/bin/sl…" 0.0.0.0:8000->8000/tcp, 0.0.0.0:9000->9000/tcp

But suppose I have a Dockerfile like this, and publish one port to a known port but the rest to randomly assigned ports.

FROM alpine
EXPOSE 8000
# Various management ports or something
EXPOSE 8005
EXPOSE 8443
EXPOSE 8009
CMD /bin/sleep 600

What is the defined behavior for

$ docker run -d -P -p 8000:8000 foo

Upvotes: 5

Views: 3954

Answers (1)

Marvin
Marvin

Reputation: 3045

Doing exactly this the behavior seems to be "as expected". The explicit port bindings take precedence over the --publish-all, independent of where the flags occur. In the example above, the results are

$ docker ps --format '{{.Command}} {{.Ports}}'
"/bin/sh -c '/bin/sl…" 0.0.0.0:8000->8000/tcp, 0.0.0.0:32792->8005/tcp, 0.0.0.0:32791->8009/tcp, 0.0.0.0:32790->8443/tcp

The explicit requested port binding occurs, and the other ports are bound to os-assigned unused ports.

It also clarified something to me I did not understand. I've always mostly ignored "EXPOSE" since the documentation basically said that it doesn't actually do anything but serve as documentation, and to actually "expose" a port you should publish it explicitly. But --publish-all does use the exposed ports. I had been naively thinking that by doing --publish-all it would publish ALL the ports that the process I had started was listening on, but those ports are opened after the container is already initialized.

Upvotes: 3

Related Questions