Docker build requires exactly 1 argument - docker

When I run this command on my gitlab pipeline
docker build --build-arg NPM_TOKEN=${NPM_TOKEN} --tag $REGISTRY_IMAGE/web-public:$CI_COMMIT_SHA --tag $REGISTRY_IMAGE/web-public:$CI_COMMIT_REF_NAME packages/web-public
it fails with
build requires exactly 1 argument
It looks to me like I am actually passing one argument, the path; packages/web-public. Flags are not arguments as far as I know.
What am I missing here?
This is the structure of my project

Quote your variables. Something in those variables is expanding to be more than the single arg to the flag.
docker build --build-arg "NPM_TOKEN=${NPM_TOKEN}" --tag "$REGISTRY_IMAGE/web-public:$CI_COMMIT_SHA" --tag "$REGISTRY_IMAGE/web-public:$CI_COMMIT_REF_NAME" packages/web-public
You can also echo that command to see how the variables are expanding, e.g.
echo docker build ...

from https://docs.docker.com/engine/reference/commandline/build/
docker build [OPTIONS] PATH | URL | -
It looks like there's something wrong with your PATH. Try using the absolute path or change to the directory containing the Dockerfile and use .
see also: "docker build" requires exactly 1 argument(s)

My issue was that I had a multi line script entry, eg
script:
- >
docker build \
--network host \
-t ${CI_REGISTRY}/kylehqcom/project/image:latest \
....
As soon as I added to a single line, we were all ok. So I guess the line breaks got "entered" after the first line which meant that the subsequent lines were ignored and the error was returned. Also note, that I CI linted via the GitLab ui and all was syntactically correct.

Related

How to write this docker shell script in powershell, in building an image in Jenkins?

Here is a shell script used in Jenkins. The $version should be replaced with the set parameter in Jenkins.
docker build -t gitlab.x.com:3030/directory:$version -f windows-config/backend/Dockerfile .
I want to run it on powershell but the logs says "invalid argument "gitlab.x.com:3030/directory:" for "-t, --tag" flag: invalid reference format."
It probably is a syntax problem with the $version
I tried changing it to
docker build -t 'gitlab.x.com:3030/directory:$version' -f windows-config/backend/Dockerfile .
but the logs say ""docker build" requires exactly 1 argument. See 'docker build --help'."

why get error: "docker build" requires exactly 1 argument

I look a sample
Dockerfile
ARG some_variable_name
# or with a default:
# ARG some_variable_name=default_value
RUN echo "Oh dang look at that $some_variable_name
# or with ${some_variable_name}
docker build
$ docker build --build-arg some_variable_name=a_value
result
Oh dang look at that a_value
but, I used the sample always gets error
"docker build" requires exactly 1 argument.
See 'docker build --help'.
Usage: docker build [OPTIONS] PATH | URL | -
Build an image from a Dockerfile
Why? Was I lose something?
in addition to #Ridwan answer, MAKE SURE THERE IS NO ADDITIONAL WHITE SPACE IN BETWEEN
docker build -t mytag .
You seem to have forgotten to put a dot, which represents that the Dockerfile in the local directory.
By that I meant:
docker build -t mytag .
What you were previously doing was:
docker build -t mytag
Thus forgetting to put the dot.

DockerHub autobuild for a GitHub pull request - using the $DOCKER_TAG variable?

I have a project with DockerHub autobuilds running for each branch of the project. These builds are running nicely.
I would like to extend this autobuild configuration to build images for selected pull requests for these branches.
The following documentation indicates that a variable named DOCKER_TAG should be available in a DockerHub autobuild.
https://docs.docker.com/docker-hub/builds/advanced/#environment-variables-for-building-and-testing
I want to configure my auto build in the following manner.
If I attempt to build a tag named "pr1234" then my build will overlay the code from PR #1234 before running the build.
# Assign the env variable DOCKER_TAG to an arg of the same name
ARG DOCKER_TAG=${DOCKER_TAG}
...
# if DOCKER_TAG is in the format prNNNN then merge code for that PR on top of the current branch
RUN PRNUM=`echo ${DOCKER_TAG}| egrep "^pr([0-9]+)$" | sed -e s/pr//` && \
if [ -n "$PRNUM" ]; \
then echo "Merging $PRNUM"; \
curl -o /tmp/pr.patch -L https://github.com/DSpace/DSpace/pull/$PRNUM.diff; \
git apply /tmp/pr.patch; \
fi
If I run my build locally, I am able to set this variable and my docker build runs as I would like.
docker build -t dspace/dspace:pr1234 -f Dockerfile.jdk8-test --build-arg DOCKER_TAG=pr1234 .
When I attempt to run this from Dockerhub, the DOCKER_TAG variable appears to be blank, so I presume that DOCKER_TAG is not being set as I expected.
Can you suggest a way to access this variable or to accomplish an automated build for selected PR's?
I found a solution that seems to work. I created a build hook named hooks/build and pass the variable explicitly.
#!/bin/bash
docker build --build-arg DOCKER_TAG=$DOCKER_TAG -f $DOCKERFILE_PATH -t $IMAGE_NAME .
See https://docs.docker.com/docker-hub/builds/advanced/#custom-build-phase-hooks

Dockerfile capture output of a command

I have the following line in my Dockerfile which is supposed to capture the display number of the host:
RUN DISPLAY_NUMBER="$(echo $DISPLAY | cut -d. -f1 | cut -d: -f2)" && echo $DISPLAY_NUMBER
When I tried to build the Dockerfile, the DISPLAY_NUMBER is empty. But however when I run the same command directly in the terminal I get the see the result. Is there anything that I'm doing wrong here?
Commands specified with RUN are executed when the image is built. There is no display during build hence the output is empty.
You can exchange RUN with ENTRYPOINT then the command is executed when the docker starts.
But how to forward the hosts display to the container is another matter entirely.
Host environment variables cannot be passed during build, only at run-time.
Only build args can be specified by:
first "declaring the arg"
ARG DISPLAY_NUMBER
and then running
docker build . --no-cache -t disp --build-arg DISPLAY_NUMBER=$DISPLAY_NUMBER
You can work around this issue using the envsubst trick
RUN echo $DISPLAY_NUMBER
And on the command line:
envsubst < Dockerfile | docker build . -f -
Which will rewrite the Dockerfile in memory and pass it to Docker with the environment variable changed.
Edit: Note that this solution is pretty useless though, because you probably
want to do this during run-time anyways, because this value should depend on not on where the image is built, but rather where it is run.
I would personally move that logic into your ENTRYPOINT or CMD script.

Equivalent of --env-file for build-arg?

I'm building a Docker image using multiple build args, and was wondering if it was possible to pass them to docker build as a file, in the same way --env-file can be pased to docker run. The env file will be parsed by docker run automatically and the variables made available in the container.
Is it possible to specify a file of build arguments in the same way?
There's no such an option, at least for now. But if you have too many build args and want to save it in a file, you can archive it as follows:
Save the following shell to buildargs.sh, make it executable and put it in your PATH:
#!/bin/bash
awk '{ sub ("\\\\$", " "); printf " --build-arg %s", $0 } END { print "" }' $#
Build your image with argfile like:
docker build $(buildargs.sh argfile) -t your_image .
This code is safe for build-arg's that contain spaces and special characters:
for arg in buildarg1 buildarg2 ; do opts+=(--build-arg "$arg") ; done
...
docker run ... "${opts[#]}"
Just substitute buildarg1 and so on with your build-arg's escaped.
Using linux you can create a file (example: arg_file) with the variables declared:
ARG_VAL_1=Hello
ARG_VAL_2=World
Execute the source command on that file:
source arg_file
Then build a docker image using that variables run this command:
docker build \
--build-arg "ARG_VAL_1=$ARG_VAL_1" \
--build-arg "ARG_VAL_2=$ARG_VAL_2" .

Resources