By default, tests should not expose ports on machine's public interfaces.
Thanks! It seems that if we use "publish all" (aka -P in Docker CLI), it defaults to 0.0.0.0.
I guess we can check if DockerClientConfigUtils#getDockerHostIpAddress returns some local host/ip and manually publish on 127.0.0.1 instead.
Although, we need to check whether it works fine with Mac and Windows, since there is a special proxy.
FTR -p also uses 0.0.0.0 by default (tested on Mac):
$ docker run -it -d -p 80 nginx
$ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
efc3a5fc7109 nginx "nginx -g 'daemon of…" 3 seconds ago Up 2 seconds 0.0.0.0:34447->80/tcp relaxed_pare
I hope too by default binding 127.0.0.1.
In the present, it is feasible by below sample code. This use network driver options of Docker.
val network = Network.NetworkImpl.builder().createNetworkCmdModifier {
it.withOptions(mapOf("com.docker.network.bridge.host_binding_ipv4" to "127.0.0.1"))
}.build()
mysqlContainer = KGenericContainer("mysql:5.6").withExposedPorts(3306)
.withNetwork(network)
But this can only bind my running containers, can’t bind ryuk container by TestContainers.
So, select the way to TESTCONTAINERS_RYUK_DISABLE=true however, in this case, it doesn’t automatically stop and remove my running container and it must call mysqlContainer.stop() after end test.
Any progress on this issue? IMHO this is highly needed.
@mkurz could you please clarify "highly needed"?
Also, it would break some deployments where Docker is running not a network device other than the local one (e.g. a sidecar pod in k8s, or even some docker-in-docker scenarios), so it is not something we can simply change and there are reasons why it is like it is right now.
We may consider adding (contributions are welcome!) an environment property "bind to this interface only" that is null by default, but I believe we can't always bind to 127.0.0.1.
I just thought its safer to bind to localhost instead exposing services to the whole world?
IMHO the environment property would be a very good solution.
@mkurz safer - yes. Easier (assuming we do this by default) - definitely not :D
JFYI as this is really Docker-related question, you can already configure Docker to use 127.0.0.1 instead of 0.0.0.0 by default:
https://forums.docker.com/t/can-i-change-the-default-ip-from-0-0-0-0-when-binding/30358/5
tl;dr:
use the following as your Docker Desktop config in Docker > Preferences > Daemon > Advanced if you're on Windows/Mac or tune your daemon config on Linux:
{
"ip" : "127.0.0.1",
"experimental" : false
}
Given that, I am not entirely sure we need a property to be added to Testcontainers TBH :)
Great, thanks, didn't know that was possible.
In case someone else is reading this, in Ubuntu you have to put the config in /etc/docker/daemon.json (which may does not exist yet) and restart docker via sudo systemctl restart docker. See https://docs.docker.com/engine/reference/commandline/dockerd/#daemon-configuration-file
Note: I also ran
sudo chown root:root /etc/docker/daemon.json
sudo chmod 600 /etc/docker/daemon.json
so the config can be read by root only.
It might be sensible to add a note about this to our docs to inform people and give them enough pointers into Docker (or Docker's documentation) so that they can configure this, if they're concerned.