Pass ENV in docker run command

Viewed 23750

Is there a way we can pass a variable lets say in this example I want to pass a list of animals into an entrypoint.sh file using ENV animals="turtle, monkey, goose"

But I want to be able to pass different animals when running the container for example docker run -t image animals="mouse,rat,kangaroo"

How do you go about passing arguments when running the docker run command?

The goal is to take that variable when using the docker run command and insert them into that entrypoint.sh file

Right now i hard code that in my Dockerfile. But i want to be able to do this when running the docker run command so I dont always have to change the Dockerfile.

FROM anapsix/alpine-java:8u121b13_jdk

ENV FILE_NAME="file_to_run.zip"

ENV animals="turtle, monkey, goose"

ADD ${FILE_NAME} .

RUN echo "${FILENAME} ${animals}" > ./entrypoint.sh    

CMD [ "/bin/ash", "./entrypoint.sh" ]
2 Answers

It looks like you might be confusing the image build with the container run. If the difference between the two isn't immediately clear, I'd recommend reviewing some other questions and docs like:

In Docker, what's the difference between a container and an image? https://docs.docker.com/develop/develop-images/dockerfile_best-practices/


RUN echo "${FILENAME} ${animals}" > ./entrypoint.sh

With the above, the variables will be expanded during the image build. The entrypoint.sh will not contain ${FILENAME} ${animals}. Instead, it will contain

file_to_run.zip turtle, monkey, goose

After the build, the docker run command will create a container from that image and run the above script with the environment variables defined but never used since the script already has the variables expanded. To prevent the variable expansion, you need to escape the $ or use single quotes to prevent the expansion, e.g.

RUN echo "\${FILENAME} \${animals}" > ./entrypoint.sh

or

RUN echo '${FILENAME} ${animals}' > ./entrypoint.sh

I would also recommend being explicit with a #!/bin/ash at the top of this script. Then when you run the script, do not override the command with parameters after the image name. Instead set the environment variables with the appropriate flag to run:

docker run -it -e animals="mouse,rat,kangaroo" image 

Simplest way, forward individual variables:

docker run ... --env animals="turtle, monkey, goose" --env FILE_NAME="file_to_run.zip"

Forward several variables using file:

Or if you need to grab all your environment variables from outside, you can do something like this first:

printenv | grep -E 'animals|FILE_NAME' > my-env

The grep is because Docker doesn't like some variables, e.g. with spaces in them, which you might possibly have in your real environment.

Then use that file in your Docker command:

docker run ... --env-file ./my-env

The latter is also useful if you want to avoid sending environment variables to logs (like for sensitive variables). I use this approach in a CI/CD pipeline that runs some scripts.

Using variables inside Docker:

With either approach, the environment variables actually become available to scripts running inside the container to use.

@BMitch's answer has more complete details about how to achieve this in your case, where you have related logic in both build and execution.

Reference

See docs here.

Related