4

As far as I understood, docker run containers with their own IPs, and fully open ports, on the bridge interface docker0.

Let's say I launch a container, and it has its own IP: 172.17.0.11, and I have a virtual ethernet interface, eth0.1, with public IP 93.x.x.x

How do I forward eth0.1 to the docker container, so that I can reach the container via eth0.1 IP?

Can I forward all ports at once? (maybe with a script)

How do I disable docker default behavior, so that each container only gets an IP on docker0 interface, and I manually setup forwarding?

@Xavierlucas

I linked it because I thought it was explained better over there. If you check the debian config, I add to the /etc/net/interfaces file this:

post-up /sbin/ifconfig eth0:X IP.OF.FAIL.OVER netmask 255.255.255.255 broadcast IP.OF.FAIL.OVER
post-down /sbin/ifconfig eth0:X down

this way I have a virtual interface (eth0:0), which has a public IP forwarded by my provider. I think the routing is done by the provider,as there are no additional routes or configs on my server

Note:

There is a followup question

why port forwarding is not working in this setup?

  • 1
    iptables​​​​​​​​​​​​​​​​​​​​​​​​​​​​ – Wesley Dec 23 '14 at 16:51
  • 1
    What do you mean by virtual ethernet interface with public IP ? Can you clarify where is each part of the veth link in your setup ? – Xavier Lucas Dec 23 '14 at 21:40
  • first of all, merry christmas. Secondly, here's the config I was referring to help.ovh.com/IpAlias – Mascarpone Dec 25 '14 at 10:15
  • @Mascarpone I won't read all of this. Answer precisely. – Xavier Lucas Dec 27 '14 at 18:38
  • @XavierLucas I better replied as an edit of the answer – Mascarpone Dec 28 '14 at 8:48
7

Firstly you wouldn't want to forward all ports at once, as then you wouldn't necessarily still have access to the host. This should definitely be a manual process.

I expect that you have a web service running in your Docker container, so if you wish to forward, for example port 80 from your eth0.1 IP address to the Docker container's IP address you could use the following iptables rule;

iptables -A PREROUTING -t nat -i eth0.1 -p tcp --dport 80 -j DNAT --to 172.17.0.11:80
iptables -A FORWARD -p tcp -d 172.17.0.11 --dport 80 -j ACCEPT

These rules can then be modified for any other ports/docker containers as required.

  • it doesnt work, but maybe there's another problem? Check the follow up question for more details. serverfault.com/questions/654978/… – Mascarpone Dec 27 '14 at 12:04
  • 1
    you need to add to postrouting: iptables -t nat -A POSTROUTING -s 172.17.0.11 -j MASQUERADE, so the packets leaving do not have 172.17.0.11 as their source ip. – allo Dec 28 '14 at 11:45
  • 1
    the problem was the first rule. Check My reply here serverfault.com/questions/654978/… If you correct your reply I will mark it as valid – Mascarpone Dec 30 '14 at 20:33
6

OK so I'm gonna throw an alternative answer here as I now understand you are not referring to virtual interfaces but IP aliasing.

First if you don't have to forward all ports but one simply use (you need to expose the port in your dockerfile obviously) :

docker run -d -p 93.x.x.x:hostPort:containerPort registry/image

In the other case, if you don't use this IP alias for anything else than communicating to/from your container with the rest of your network, you can take a look at my modest project : docker-flatip and directly assign this IP to a virtual ethernet link plugged from the container to a second bridge dedicated to flat containers.

I wrote it while facing a use case a bit particular. Keep in mind that this is at the border of what docker containers are and it's quite better to find a solution, if you can, in order to not bind a particular IP address to a container for orchestration and scalability purposes.

The main point of this it to be able to reach a container as it was any other host on your network with easier iptables rules setup. In my case it was necessary to deploy a bunch of load generation agents from a commercial solution with specific iptables rules where each needed a public IP and could not be autodiscovered. It act as a wrapper after running/before stopping your containers so iptables rules are added/removed whith ease.

With this little tool you would end up starting your container like this (if you are really sure you want to forward all ports, not encouraged at all) :

cid=$(docker run -d registry/image)

Or

docker start $cid

Then :

docker-flatip add $cid 93.x.x.x/32 -i tcp:all,udp:all

And stopping it like this :

docker-flatip del $cid

docker stop $cid
  • I starred your project, I'm analyzing this solution. The fact that I'm using IPalias prevents me from using iptables? – Mascarpone Dec 28 '14 at 12:38
  • I run docker run -d -p 93.x.x.x:hostPort:containerPort registry/image, using the ip of eth0:1, but it doesnt work. Why? – Mascarpone Dec 28 '14 at 12:48
  • 1
    @Mascarpone ipalias allows to assign multiple IPs to a single NIC. It doesn't prevent you from using the classic ip forwarding/iptables method. In my project the purpose it to mount the IP directly in the container not on the host's NIC. So if you use ip alias for something else on the host it won't work (it would mean mount the IP two times at different locations). For your second point : can you precise the it doesn't work part ? Regarding what ? – Xavier Lucas Dec 28 '14 at 13:01

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.