1

I don't think I have the right title, but I'm not 100% sure what the correct one would be. I'm attempting to containerize a Python program that I have which can run as either a server or client based on CLI arguments. I was able to do it successfully by saying:

FROM python:3.5
ADD program/ program/
WORKDIR program/
ENTRYPOINT ["python", "program.py"]

which I can then run with docker run -d program server <port> <protocol> (or client) and it works properly.

I run into problems though, when I try to create images based on the previous image.

For example, if I want to create a server specific image, I tried:

FROM program
ENTRYPOINT ["server"]

and then my goal would be to run it by saying docker run programServer <port> <protocol>, however when I attempt that I get an executable file not found in $PATH" error.

Is there something that I'm missing, or are you not able to "daisy-chain" images this way?

ErikMD
  • 13,377
  • 3
  • 35
  • 71
AndyReifman
  • 1,459
  • 4
  • 18
  • 34
  • Note that each `ENTRYPOINT` line overrides the previous `ENTRYPOINT` definition. So have you tried writing `ENTRYPOINT ["python", "program.py", "server"]`? – ErikMD Jan 12 '21 at 16:15
  • As an aside, you might be interested in the `CMD` directive to provide default arguments… e.g. `CMD ["", ""]` according to your example. See also [What is the difference between CMD and ENTRYPOINT in a Dockerfile?](https://stackoverflow.com/a/39408777/9164010) – ErikMD Jan 12 '21 at 16:18
  • 1
    @ErikMD Ahh, I didn't realize that. So does that mean I should remove the `ENTRYPOINT` statement from my first Dockerfile? It looks like adding your suggestion to my second Dockerfile gets it working. – AndyReifman Jan 12 '21 at 16:20
  • No, it's unneeded to remove the `ENTRYPOINT` from your first Dockerfile (I elaborated on this in [my answer](https://stackoverflow.com/a/65687930/9164010)) – ErikMD Jan 12 '21 at 16:26

1 Answers1

1

Two remarks:

  1. each image should contain one ENTRYPOINT and/or one CMD (either defined in the Dockerfile or inherited from its parent image);

  2. each ENTRYPOINT line overrides the previous ENTRYPOINT definition (as a Docker container is intended to run one process, called the entrypoint).

So:

  • you should just write ENTRYPOINT ["python", "program.py", "server"] in your second Dockerfile (for the child image);
  • but you can just as well keep ENTRYPOINT ["python", "program.py"] in your first Dockerfile (for the parent image) as this causes no harm, and allows one to address rule 1 above.

But if a parent image is only intended to serve as a base image, never to be run "as is", and does not yield a natural entrypoint, you might just put a dummy CMD that prints a warning/error, for example, or a shell − see e.g. the Dockerfile for debian:10.

For more details on {ENTRYPOINT, CMD}, see also this SO answer: What is the difference between CMD and ENTRYPOINT in a Dockerfile?

ErikMD
  • 13,377
  • 3
  • 35
  • 71
  • Thank you! The helps clear things up. The plan is for the parent image to only serve as a base image, so I will look in to the warning/error message. – AndyReifman Jan 12 '21 at 16:32