Richard Cook
Richard Cook

Reputation: 33099

Detect if Docker image would change on running build

I am building a Docker image using a command line like the following:

docker build -t myimage .

Once this command has succeeded, then rerunning it is a no-op as the image specified by the Dockerfile has not changed. Is there a way to detect if the Dockerfile (or one of the build context files) subsequently changes without rerunning this command?

Upvotes: 12

Views: 9978

Answers (3)

What follows is not the answer to your exact question, but a work-around that has served me.

Since Docker apparently doesn't offer the "dry-run" feature, you could check the dependencies of the image. Specifically, you could checksum all files within the Docker context, being rough. To be finer, you could check only the actually used files.

The following code will make a hash of all files referenced by COPY commands as well as the Dockerfile itself.

( 
echo Dockerfile 
sed -n 's/^COPY \([^ ]\+\) .*$/\1/p' Dockerfile  
) | xargs --replace find '{}' -type f |
  sort |
  xargs cat | 
  sha256sum | cut -d' ' -f1

Upvotes: 0

Mohamed Ali JAMAOUI
Mohamed Ali JAMAOUI

Reputation: 14689

looking at docker inspect $image_name from one build to another, several information doesn't change if the docker image hasn't changed. One of them is the docker Id. So, I used the Id information to check if a docker has been changed as follows:

First, one can get the image Id as follows:

docker inspect --format {{.Id}} $docker_image_name

Then, to check if there is a change after a build, you can follow these steps:

  1. Get the image id before the build
  2. Build the image
  3. Get the image id after the build
  4. Compare the two ids, if they match there is no change, if they don't match, there was a change.

Code: Here is a working bash script implementing the above idea:

docker inspect --format {{.Id}} $docker_image_name > deploy/last_image_build_id.log
# I get the docker last image id from a file
last_docker_id=$(cat deploy/last_image_build_id.log)
docker build -t $docker_image_name .
docker_id_after_build=$(docker inspect --format {{.Id}} $docker_image_name)
if [ "$docker_id_after_build" != "$last_docker_id" ]; then
   echo "image changed" 
else
   echo "image didn't change" 
fi

Upvotes: 18

ldg
ldg

Reputation: 9402

There isn't a dry-run option if that's what you are looking for. You can use a different tag to avoid affecting existing images and look for ---> Using cache in the output (then delete the tag if you don't want it).

Upvotes: 8

Related Questions