ChatGPT解决这个技术问题 Extra ChatGPT

Can we pass ENV variables through cmd line while building a docker image through dockerfile?

I am working on a task that involves building a docker image with centOs as its base using a Dockerfile . One of the steps inside the dockerfile needs http_proxy and https_proxy ENV variables to be set in order to work behind the proxy.

As this Dockerfile will be used by multiple teams having different proxies, I want to avoid having to edit the Dockerfile for each team. Instead I am looking for a solution which allows me to pass ENV variables at build time, e.g.,

sudo docker build -e http_proxy=somevalue .

I'm not sure if there is already an option that provides this. Am I missing something?

what is the problem with passing those at run time? Something like docker run -e http_proxy http://1.2.3.4:3128 -e https_proxy 1.2.3.4:3129? The doc of docker run docs.docker.com/reference/commandline/run
The problem is that one of the steps inside docker file invovles yum installation and it fails if i dont set the http/https ENV variables and without proper installation i can't build the image .so docker run doesnt help me here .
I am afraid you will have to build specific images, the only difference being the values of http_proxy(s) ONBUILD may help, but I am afraid it is not suited here, see the doc docs.docker.com/reference/builder
This have been discussed here github.com/docker/docker/issues/4962 and again here github.com/docker/docker/pull/9176 and closed, so at the moment, it seems you have no solution
Thank you user2915097 for your comments .I have already gone through the above github links ,I asked this question with a tiny hope that someone on Stackoverflow might have faced this similar situation.

R
Rob Bednark

Containers can be built using build arguments (in Docker 1.9+) which work like environment variables.

Here is the method:

FROM php:7.0-fpm
ARG APP_ENV=local
ENV APP_ENV ${APP_ENV}
RUN cd /usr/local/etc/php && ln -sf php.ini-${APP_ENV} php.ini

and then build a production container:

docker build --build-arg APP_ENV=prod .

For your particular problem:

FROM debian
ENV http_proxy ${http_proxy}

and then run:

docker build --build-arg http_proxy=10.11.24.31 .

Note that if you build your containers with docker-compose, you can specify these build-args in the docker-compose.yml file, but not on the command-line. However, you can use variable substitution in the docker-compose.yml file, which uses environment variables.


Because I overlooked it: You need ARG to tell docker that a build argument can be passed to the builder. Without specifying ARG it doesn't work.
This ENV APP_ENV ${APP_ENV} is not needed. It's enough to have ARG APP_ENV without =local and it will grab build argument and use it as any variable set by ENV
@ElmoVanKielmo That's true during the build, but ARG isn't persisted as an environment variable when the docker image is ran. Using ENV APP_ENV ${APP_ENV} ensures that the environment variable is still available when the container is running.
@DuckPuppy true but I sticked to the OP's question
@ElmoVanKielmo OP's question is about passing ENV from command-line, so how does having ARG alone help? You need ARG so that you can pass one via --build-arg and then you need ENV to copy it to an environment variable to be persisted with the image.
N
Nick

So I had to hunt this down by trial and error as many people explain that you can pass ARG -> ENV but it doesn't always work as it highly matters whether the ARG is defined before or after the FROM tag.

The below example should explain this clearly. My main problem originally was that all of my ARGS were defined prior to FROM which resulted all the ENV to be undefined always.

# ARGS PRIOR TO FROM TAG ARE AVAIL ONLY TO FROM for dynamic a FROM tag
ARG NODE_VERSION
FROM node:${NODE_VERSION}-alpine

# ARGS POST FROM can bond/link args to env to make the containers environment dynamic
ARG NPM_AUTH_TOKEN
ARG EMAIL
ARG NPM_REPO

ENV NPM_AUTH_TOKEN ${NPM_AUTH_TOKEN}
ENV EMAIL ${EMAIL}
ENV NPM_REPO ${NPM_REPO}

# for good measure, what do we really have
RUN echo NPM_AUTH_TOKEN: $NPM_AUTH_TOKEN && \
  echo EMAIL: $EMAIL && \
  echo NPM_REPO: $NPM_REPO && \
  echo $HI_5
# remember to change HI_5 every build to break `docker build`'s cache if you want to debug the stdout

..... # rest of whatever you want RUN, CMD, ENTRYPOINT etc..

WOW, dang, happened to me too! No one is speaking about this, nowhere in the docs a mention, warning etc! Thanks a lot!!!
Might I mention this was critical if your deployment environment is from automatic CI. IE I found this when I was trying to make gitlab CI to scale across project domains. IE One project might be settling one different node versions etc...
Saved me some nerves, thank you! I would never figured out that placement of ARGs matters..
I think this is actually explained here: An ARG declared before a FROM is outside of a build stage, so it can’t be used in any instruction after a FROM
Thanks so much, what an annoying problem to track down, cheers
T
Tugrul

I faced the same situation.

According to Sin30's answer pretty solution is using shell,

CMD ["sh", "-c", "cd /usr/local/etc/php && ln -sf php.ini-$APP_ENV php.ini"]