81

I'm trying to build a custom tcserver docker image. But I'm having some problems starting the webserver and the tomcat.
As far as I understand I should use ENTRYPOINT to run the commands I want.
The question is, is it possible to run multiple commands with ENTRYPOINT?
Or should I create a small bash script to start all?

Basically what I would like to do is:

ENTRYPOINT /opt/pivotal/webserver/instance1/bin/httpdctl start && /opt/pivotal/webserver/instance2/bin/httpdctl start && /opt/pivotal/pivotal-tc-server-standard/standard-4.0.1.RELEASE/tcserver start instance1 -i /opt/pivotal/pivotal-tc-server-standard && /opt/pivotal/pivotal-tc-server-standard/standard-4.0.1.RELEASE/tcserver start instance2 -i /opt/pivotal/pivotal-tc-server-standard

But I don't know if that is a good practice or if that would even work.

radicaled
  • 2,369
  • 5
  • 30
  • 44
  • 1
    Possible duplicate of [How to run multiple processes in a single docker container](https://stackoverflow.com/questions/49658754/how-to-run-multiple-processes-in-a-single-docker-container) – David Maze Jan 10 '19 at 02:19
  • 2
    Your approach with && should work, as it can actually be considered a single command. However, it is better practice to create a bash script. But, as a general rule, you should use a single process per container if you want the benefits of containers. – Yamuk Jan 10 '19 at 02:23
  • 1
    why not using like `ENTRYPOINT ["entry1", "exec1", "entry2", "exec2"]` – PPShein Jan 10 '19 at 02:29

3 Answers3

100

In case you want to run many commands at entrypoint, the best idea is to create a bash file. For example commands.sh like this

#!/bin/bash
mkdir /root/.ssh
echo "Something"
cd tmp
ls
...

And then, in your DockerFile, set entrypoint to commands.sh file (that execute and run all your commands inside)

COPY commands.sh /scripts/commands.sh
RUN ["chmod", "+x", "/scripts/commands.sh"]
ENTRYPOINT ["/scripts/commands.sh"]

After that, each time you start your container, commands.sh will be execute and run all commands that you need. You can take a look here https://github.com/dangminhtruong/drone-chatwork

Wantyapps
  • 83
  • 1
  • 10
Truong Dang
  • 3,119
  • 1
  • 15
  • 21
  • I have one more question. If I use this build as a base (ie: tcserver_build) and later I want to import a new .war file to the tomcat webapps directory. I will create a new build (ie: webapp_build) with just the COPY or the .war file to the tomcat webapps directory. I will need to put a new ENTRYPOINT to start the webserver and tomcat or it will use the one from the base build (tcserver_build)? – radicaled Jan 10 '19 at 12:58
  • > I will need to put a new ENTRYPOINT to start the webserver and tomcat or it will use the one from the base build (tcserver_build)? Docker will use all instructions from the base image, unless you override them in your image. – jeverling Nov 02 '20 at 18:51
  • What if you are part of an organization that is averse to incorporating shell scripts into their infrastructure? How does one simply chain a pair of commands? For example, suppose I mount a drive that requires the docker image to install **particular** versions, or at least run through a requirements file and verify the versions are in order before running a command? Suppose I am *at the docker compose level*? – Chris Jan 06 '21 at 18:33
  • If one is mounting an application folder in docker-compose, is there then any reason to copy the `commands.sh` file into the container first? Doesn't that just complicate things because you then have to rebuild every time you make a change in it? Couldn't one just do `ENTRYPOINT ["/mounted/folder/commands.sh"]`? – TheStoryCoder May 07 '21 at 09:58
  • Note that if you are using secrets, they are only available after the entry point. You would have to use CMD instead of ENTRYPOINT if you want to copy or link your secret at startup – Mudo Jan 06 '23 at 03:12
73

You can use something like this:

ENTRYPOINT ["/bin/sh", "-c" , "<command A> && <command B> && <command C>"]

Latif
  • 831
  • 4
  • 4
  • 5
    Do I have to escape `&` caracter if I want to run the first command in background? E.g.: `ENTRYPOINT ["/bin/sh", "-c" , "service1 & && service2"]` where service1 should run in the background and service2 in foreground. – ochs.tobi Feb 15 '22 at 08:41
  • 1
    Works perfectly if you cannot add a custom shell script (for a pre-built image) – Arnaud de Mouhy Jul 18 '22 at 13:35
  • Does this gracefully terminate (handle SIGTERM)? – Mark Sowul Aug 16 '23 at 19:43
-8

You can use npm concurrently package.

For e.g.

ENTRYPOINT ["npx","concurrently","command1","command2"]

It will run them in parallel.

Aminadav Glickshtein
  • 23,232
  • 12
  • 77
  • 117
  • 11
    This doesn't work if your final container is not Node. Such as when you're building an angular application and hosting it on nginx. – RoboticRenaissance Aug 12 '20 at 22:09
  • 1
    @RoboticRenaissance wth npm, pnpm and npx you can run not only node scripts, but any https://stackoverflow.com/questions/34937724/running-bash-scripts-with-npm So this answer not the best, but shouldn't be that flagged. – Rantiev Aug 26 '23 at 21:45