How to change docker's default container name and host alias? - docker

Everytime docker generates a random container name and host alias (a hash) if you do not designate them, which are long and do not make much sense to me, difficult to remember and type.
I hope both the container names and host alias are h1, h2... by default. Is it possible (how to) configure that?
Edit
Per a docker team member's reply, this is not feasible now.

If you are running the containers using docker run then you can use --name to specify container_name and --hostname to specify hostname. Example:
docker run --name mysql --hostname mysql_server mysql:latest
If you are using docker-compose to run the containers, then you can specify the details using
version: '3'
services:
mysql:
image: mysql:latest
container_name: mysql_container
hostname: mysql_host

Related

docker-compose how to define container scoped network like in docker run?

Running 2 containers where mycontainer2 must use the same network stack of mycontainer1. As if the two containers were running in the same machine. Here how I try to do by using docker run with --network container:xxx
$ docker run -it --rm --name mycontainer1 -p 6666:7777 myregistry/my-container1:latest
$ docker run -it --rm --network container:mycontainer1 --name mycontainer2 myregistry/my-container2:latest
I tried to replicate this behavior using docker-compose instead. But the networks: definition of docker-compose.yaml doesn't indicate something equivalent to the --network container:xxx option of docker run. Is it possible in docker-compose to configure two containers to use the same network stack?
This is a network_mode: setting.
version: '3.8'
services:
mycontainer1:
image: myregistry/my-container1:latest
ports: ['6666:7777']
mycontainer2:
image: myregistry/my-container2:latest
network_mode: service:mycontainer1 # <---
Since Compose will generally pick its own container names, this service:name form uses the container matching the named Compose service. (If you override container_name: then you can also use container:mycontainer1 the same way you did with docker run.)
Creating an external network and use it inside docker-compose YAML manifest might help. Here is how you do it.
version: '3.7'
networks:
default:
external:
name: an-external-network
services:
my-container1:
...
my-container2:
...
Note: use docker network create command to create an-external-network before running docker-compose up command.

Docker DNS with Multiple Projects Using the Same Network

I have the following docker-compose.yml file:
version: '3'
services:
frontend:
image: alpine
command: tail -f /dev/null
networks:
- shared
- default
backend:
image: alpine
command: tail -f /dev/null
networks:
- shared
- default
networks:
shared:
external: true
Based on the file from above I create two projects which use the same network (shared) and the same service names (frontend and backend):
docker-compose -p foo up -d
docker-compose -p bar up -d
Does the DNS of docker make sure that docker-compose -p foo exec frontend ping backend only resolves to the backend container in project foo and vice versa for project bar?
According to https://github.com/docker/compose/issues/4645, the resolve order in this case in non deterministic. Since the network is being converted to unordered dict in golang, the order is not preserved. Which implies https://github.com/docker/libnetwork/blob/master/sandbox.go#L593 the order of endpoints being queried don't match the order of network.
The solution is to define https://docs.docker.com/compose/compose-file/compose-file-v2/#priority if using docker-compose version 2. Or fully qualified dns name as service.network such as backend.foo_default or backend.shared.
Based on your setup I have used nslookup to find out whether the DNS resolution is isolated or not.
$ docker-compose -p foo exec frontend nslookup backend
Name: backend
Address 1: 172.19.0.2 foo_backend_1.shared
Address 2: 172.19.0.4 bar_backend_1.shared
As you can see from the output above, backend resolves to both of the containers.
If you use docker swarm you can qualify hostnames with the service name to disambiguate containers. But I don't believe docker-compose does this.

Docker RabbitMQ persistency

RabbitMQ in docker lost data after remove container without volume.
My Dockerfile:
FROM rabbitmq:3-management
ENV RABBITMQ_HIPE_COMPILE 1
ENV RABBITMQ_ERLANG_COOKIE "123456"
ENV RABBITMQ_DEFAULT_VHOST "123456"
My run script:
IMAGE_NAME="service-rabbitmq"
TAG="${REGISTRY_ADDRESS}/${IMAGE_NAME}:${VERSION}"
echo $TAG
docker rm -f $IMAGE_NAME
docker run \
-itd \
-v "rabbitmq_log:/var/log/rabbitmq" \
-v "rabbitmq_data:/var/lib/rabbitmq" \
--name "service-rabbitmq" \
--dns=8.8.8.8 \
-p 8080:15672 \
$TAG
After removing the container, all data are lost.
How do I configure RabbitMQ in docker with persistent data?
Rabbitmq uses the hostname as part of the folder name in the mnesia
directory. Maybe add a --hostname some-rabbit to your docker run?
I had the same issue and I found the answer here.
TL;DR
Didn't do too much digging on this, but it appears that the simplest way to do this is to change the hostname as Pedro mentions above.
MORE INFO:
Using RABBITMQ_NODENAME
If you want to edit the RABBITMQ_NODENAME variable via Docker, it looks like you need to add a hostname as well since the Docker hostnames are generated as random hashes.
If you change the RABBITMQ_NODENAME var to something static like my-rabbit, RabbitMQ will throw something like an "nxdomain not found" error because it's looking for something likemy-rabbit#<docker_hostname_hash>. If you know the Docker hostname and can automate pulling it into your RABBITMQ_NODENAME value like so, my-rabbit#<docker_hostname_hash> I believe it would work.
UPDATE
I previously said,
If you know the Docker hostname and can automate pulling it into your RABBITMQ_NODENAME value like so, my-rabbit#<docker_hostname_hash> I believe it would work.
This would not work as described precisely because the default docker host name is randomly generated at launch, if it is not assigned explicitly. The hurdle would actually be to make sure you use the EXACT SAME <docker_hostname_hash> as your originating run so that the data directory gets picked up correctly. This would be a pain to implement dynamically/robustly. It would be easiest to use an explicit hostname as described below.
The alternative would be to set the hostname to a value you choose -- say, app-messaging -- AND ALSO set the RABBITMQ_NODENAME var to something like rabbit#app-messaging. This way you are controlling the full node name that will be used in the data directory.
Using Hostname
(Recommended)
That said, unless you have a reason NOT to change the hostname, changing the hostname alone is the simplest way to ensure that your data will be mounted to and from the same point every time.
I'm using the following Docker Compose file to successfully persist my setup between launches.
version: '3'
services:
rabbitmq:
hostname: 'mabbit'
image: "${ARTIFACTORY}/rabbitmq:3-management"
ports:
- "15672:15672"
- "5672:5672"
volumes:
- "./data:/var/lib/rabbitmq/mnesia/"
networks:
- rabbitmq
networks:
rabbitmq:
driver: bridge
This creates a data directory next to my compose file and persists the RabbitMQ setup like so:
./data/
rabbit#mabbit/
rabbit#mabbit-plugins-expand/
rabbit#mabbit.pid
rabbit#mabbit-feature_flags

Multiple docker images run from docker file

I am trying to execute multiple docker images run from single docker file with different ports.
Please advise How to execute multiple "docker run" commands from single docker file with different ports.
You want to use docker-compose it sounds like. Here is an example using nginx and redis (It's how I do it anyway)
services:
nginx:
image: nginx
ports:
- "80:80"
redis:
image: redis
ports:
- "1000:1000"
So as you can see, if I run docker-compose up, docker will spin up two containers, nginx and redis, each running off of a different port! If you don't want to you docker-compose, you can do it from docker run
docker run --name nginx -p 1000:10001
docker run --name redis -p 3333:2423
I don't 100% understand your question, but I hope this helps!

How can I add hostnames to a container on the same docker network?

Suppose I have a docker compose file with two containers. Both reference each other in their /etc/hosts file. Container A has a reference for container B and vice versa. And all of this happens automatically. Now I want to add one or more hostnames to B in A's hosts file. How can I go about doing this? Is there a special way I can achieve this in Docker Compose?
Example:
172.0.10.166 service-b my-custom-hostname
Yes. In your compose file, you can specify network aliases.
services:
db:
networks:
default:
aliases:
- database
- postgres
In this example, the db service could be reached by other containers on the default network using db, database, or postgres.
You can also add aliases to running containers using the docker network connect command with the --alias= option.
Docker compose has an extra_hosts feature that allows additional entries to be added to the container's host file.
Example
docker-compose.yml
web1:
image: tomcat:8.0
ports:
- 8081:8080
extra_hosts:
- "somehost:162.242.195.82"
- "otherhost:50.31.209.229"
web2:
image: tomcat:8.0
ports:
- 8082:8080
web3:
image: tomcat:8.0
ports:
- 8083:8080
Demonstrate host file entries
Run docker compose with the new docker 1.9 networking feature:
$ docker-compose --x-networking up -d
Starting tmp_web1_1
Starting tmp_web2_1
Starting tmp_web3_1
and look at the hosts file in the first container. Shows the other containers, plus the additional custom entries:
$ docker exec tmp_web1_1 cat /etc/hosts
..
172.18.0.4 web1
172.18.0.2 tmp_web2_1
172.18.0.3 tmp_web3_1
50.31.209.229 otherhost
162.242.195.82 somehost
If I understand your question correctly, you can pass a host name referenced in your host's /etc/hosts file via --add-host flag :
$ docker run ... --add-host="droid"
Your host's /etc/hosts would need the following entry:
xx.xx.xx.xx droid
Of course, xx.xx.xx.xx will need to be reachable from inside the container you just started using the 'docker run' command. You can have one or more --add-host="xyz".
More details about --add-host here:
http://docs.docker.com/v1.8/reference/commandline/run/

Resources