Dockerfiles are the backbone of containerized applications, and two key instructions often used in Dockerfiles are CMD and ENTRYPOINT. While both are used to define how a container runs, they serve distinct purposes and are used differently. In this article, we will dive into the differences between CMD and ENTRYPOINT with real-world examples, so you can make informed decisions when building your Docker images.

What is CMD in Docker?

The CMD instruction is used to specify the default command and arguments to run when a container starts. However, if a user provides a command when running the container, it overrides the CMD instruction.

Syntax


CMD ["executable", "param1", "param2"] # Exec form
CMD command param1 param2              # Shell form
							

Example: Default Web Server

Here’s a Dockerfile that uses CMD to set up a simple Python HTTP server:


FROM python:3.9-slim
WORKDIR /app
CMD ["python", "-m", "http.server", "8000"]
							

When you build and run this image:


docker build -t python-server .
docker run -p 8000:8000 python-server
							

The container will start a web server on port 8000.

However, if you override the command:

docker run python-server python -c "print('Hello World')"

The CMD instruction is completely replaced, and the container runs the provided command instead.

What is ENTRYPOINT in Docker?

The ENTRYPOINT instruction is used to configure a container to run as an executable. Unlike CMD, arguments passed during docker run are appended to the ENTRYPOINT command rather than replacing it.

Syntax


ENTRYPOINT ["executable", "param1", "param2"] # Exec form
ENTRYPOINT command param1 param2               # Shell form
							

Example: Ping Utility

Here’s a Dockerfile that uses ENTRYPOINT to create a container for running ping commands:


FROM alpine:latest
ENTRYPOINT ["ping"]
							

When you build and run this image:


docker build -t ping-tool .
docker run ping-tool google.com
							

The google.com argument is appended to ping, and the container runs ping google.com.

Combining CMD and ENTRYPOINT

You can use both ENTRYPOINT and CMD together for more flexibility. In this setup, CMD provides default arguments to the ENTRYPOINT executable but can be overridden during runtime.

Example: Customizable Ping Tool


FROM alpine:latest
ENTRYPOINT ["ping"]
CMD ["localhost"]
							
  • Default behavior:
    docker run ping-tool
    Runs ping localhost.
  • Custom behavior:
    docker run ping-tool google.com
    Runs ping google.com.

Key Differences Between CMD and ENTRYPOINT

Feature CMD ENTRYPOINT
Purpose Default command to run Configures the container as an executable
Overridable Fully overridden by docker run Arguments are appended to ENTRYPOINT
Syntax Exec and shell forms Exec and shell forms
Best Use Case Default behavior with flexibility Fixed behavior with optional arguments

Real-World Use Cases

Case 1: Web Server

For a web server, CMD is preferred as it allows flexibility to override the default behavior if needed.

Case 2: CLI Tool

For command-line utilities or tools, ENTRYPOINT is ideal because it ensures the container always behaves as the tool, and users can pass arguments as needed.

Best Practices

  1. Use CMD for default commands that users might want to override.
  2. Use ENTRYPOINT for containers designed as executables.
  3. Combine ENTRYPOINT and CMD for default arguments with flexibility.
  4. Always use the exec form (["executable", "param1", "param2"]) to avoid issues with signal handling and process termination.

Conclusion

Understanding the differences between CMD and ENTRYPOINT is crucial for writing effective Dockerfiles. While CMD provides default commands, ENTRYPOINT ensures the container behaves predictably as an executable. By combining both instructions strategically, you can create flexible and robust Docker images tailored to your application’s needs.