7

We have a docker-compose.yml file to bring up a db2 and a number of other components of our testing framework. Once we bring up the db2 we have to attach to that container and run a set of shell scripts on it to create schema definitions, etc.

Trouble is that docker-compose gives dynamic names to the containers - and they change everytime we start them with 'run'. How do I find the exact name of the db2 container that's running this time?!

Here is an excerpt from our docker-compose.yml:

  db2:
    container_name: "bluecost-db2"
    image: store/ibmcorp/db2_developer_c:11.1.3.3-x86_64
    command: /bin/bash -c "groupadd bluecost -g 1006;adduser bluecost -u $$(id -u)  -g $$(echo $$(id)| grep -oPm1 'gid=\K\w+')&& echo \"bluecost:bluecost\" | chpasswd;usermod -a -G db2iadm1 bluecost;chown -R bluecost:db2iadm1 /home/bluecost/bluecostDB;mkdir /database/data;"
    hostname: db2server
    privileged: true
    ports:
      - 50001:50000
      - 55000:55000
    networks:
      - back-tier
    volumes:
      - ./standalone/linuxScripts/bluecostDB:/home/bluecost/bluecostDB
    restart: "no"
    env_file:
      - ./standalone/db2/.env_list

Here is a shell script that starts db2 and rest of the commands:

docker-compose -f docker-acceptance.yml run -d db2
printf  "Waiting for db2 to warm-up *************************\n\n\n\n"
sleep 340
printf  "Starting to initialize schema **********************\n\n\n\n"
docker exec -d -t bluecost-db2 /bin/bash -c "cp /home/bluecost`/bluecostDB/*.* /home/db2inst;chmod +x /home/mydir/runBlueCostDBScript.sh;chown db2adm:db2adm /home/db2iadm/*.sql;chown db2adm:db2adm1 /home/db2inst/*.sh;mkdir /database/data/bluecostDB;chown -R db2adm:db2adm1 /database/data/bluecostDB;echo ./runBlueCostDBScript.sh | su - db2adm"` 

Notice above that first line in that script runs the db2. That works, the container starts and it warms up, but when the last docker exec command runs, it refers to that container by name 'bluecost-db2' and that container name that's running is sligtly different: bluecost-db2_run1, bluecostdb2_run2, etc

How can I find the exact name to execute? I found this docker ps --format '{{.Image}} {{.Names}}' but that lists all containers that are running, there may be more than one... how do I get just the name of the db2 container that's running?

JamesD
  • 679
  • 10
  • 36

3 Answers3

3

You can get the name of running containers using

docker ps --format "{{.Image}} {{.Name}}" --filter status=running

enter image description here

If you want only db2 you can run:

docker ps --format "{{.Image}} {{.Name}}" --filter status=running | grep db2

You can get the name of the running db2 container you want to exec the command to, export the name as a variable and reference the var in your script executing the command on the correct container

To accomplish what you want add a label to db2 in your compose file like:

env_file:
    - ./standalone/db2/.env_list
labels:
    - db2.name: "db2"

Then filter the ID of running containers by label:

docker ps --filter "label=db2" --format {{.ID}} --filter status=running
lava
  • 6,020
  • 2
  • 31
  • 28
D. Vinson
  • 1,090
  • 6
  • 8
  • Absolutely, let me know if you need help implementing, happy to help – D. Vinson Jul 09 '18 at 01:50
  • Why doesn't this work: `docker ps --format '{{.ID}}' --filter status=running | grep db2` ? This works though: docker ps --format '{{.ID}} {{.Names}}' --filter status=running | grep db2 - why not just ID? – JamesD Jul 09 '18 at 04:17
  • Because it's only returning the ids of the containers you would need to filter `{{.Name}}` to grep the name – D. Vinson Jul 09 '18 at 04:35
  • Updated answer to filter ids of running containers with the label db2 – D. Vinson Jul 09 '18 at 06:42
  • Results in: `failed to execute template: template: :1:13: executing "" at <.Name>: can't evaluate field Name in type *formatter.ContainerContext` – Distagon Jul 15 '21 at 08:48
  • @Distagron docker ps --format "{{.ID}}||{{.Names}}" --filter Name=docker – lava Dec 31 '21 at 06:25
3

You can use docker-compose ps:

$ docker-compose ps
                Name                               Command                   State                       Ports                
------------------------------------------------------------------------------------------------------------------------------
our-project_airflow-postgres_1  docker-entrypoint.sh postgres    Up (healthy)     5432/tcp                                                                                                                             
our-project_airflow_1           /bin/bash -c source initia ...   Exit 0                                                                       
our-project_healthchecker_1     /bin/sh -c ./compute-healt ...   Up (unhealthy)                                       
our-project_local-ingress_1     docker-entrypoint.sh postgres    Up (healthy)     5432/tcp                            
our-project_local-s3_1          /usr/bin/docker-entrypoint ...   Up (healthy)     9000/tcp  

You can restrict this to a service, too:

$ docker-compose ps local-s3
             Name                           Command                  State               Ports         
-------------------------------------------------------------------------------------------------------
gears-orchestration_local-s3_1   /usr/bin/docker-entrypoint ...   Up (healthy)   9000/tcp

So what you want is something along the lines of this:

$ docker-compose ps local-s3 | tail -n +3 | awk '{ print $1 }'
gears-orchestration_local-s3_1

Be aware that like all docker CLI commands, these will aggressively break lines. A non-interactive shell won't have that problem, but in a terminal emulator you may see your commands fail.

Raphael
  • 9,779
  • 5
  • 63
  • 94
0

The answer of @Raphael worked well for me (should have been picked as the top answer, IMHO).

My use case:

(1) Assign the output to a variable and (2) run another docker command to do something inside the given container.

WEB_CONTAINER=`docker-compose ps local-s3 | tail -n +3 | awk '{ print $1 }'`;
docker exec "${WEB_CONTAINER}" /bin/bash -c "echo ${whoami}";
Artur Barseghyan
  • 12,746
  • 4
  • 52
  • 44