diff options
-rw-r--r-- | doc/functions/dockertools.xml | 41 | ||||
-rwxr-xr-x | pkgs/build-support/docker/nix-prefetch-docker | 173 | ||||
-rw-r--r-- | pkgs/build-support/docker/nix-prefetch-docker.nix | 26 | ||||
-rw-r--r-- | pkgs/top-level/all-packages.nix | 2 |
4 files changed, 230 insertions, 12 deletions
diff --git a/doc/functions/dockertools.xml b/doc/functions/dockertools.xml index cb32db74b42..e95ce1979de 100644 --- a/doc/functions/dockertools.xml +++ b/doc/functions/dockertools.xml @@ -437,18 +437,7 @@ pullImage { <callout arearefs='ex-dockerTools-pullImage-2'> <para> <varname>imageDigest</varname> specifies the digest of the image to be - downloaded. Skopeo can be used to get the digest of an image, with its - <varname>inspect</varname> subcommand. Since a given - <varname>imageName</varname> may transparently refer to a manifest list of - images which support multiple architectures and/or operating systems, - supply the `--override-os` and `--override-arch` arguments to specify - exactly which image you want. By default it will match the OS and - architecture of the host the command is run on. -<programlisting> -$ nix-shell --packages skopeo jq --command "skopeo --override-os linux --override-arch x86_64 inspect docker://docker.io/nixos/nix:1.11 | jq -r '.Digest'" -sha256:20d9485b25ecfd89204e843a962c1bd70e9cc6858d65d7f5fadc340246e2116b -</programlisting> - This argument is required. + downloaded. This argument is required. </para> </callout> <callout arearefs='ex-dockerTools-pullImage-3'> @@ -486,6 +475,34 @@ sha256:20d9485b25ecfd89204e843a962c1bd70e9cc6858d65d7f5fadc340246e2116b </para> </callout> </calloutlist> + + <para> + <literal>nix-prefetch-docker</literal> command can be used to get required + image parameters: + +<programlisting> +$ nix run nixpkgs.nix-prefetch-docker -c nix-prefetch-docker --image-name mysql --image-tag 5 +</programlisting> + + Since a given <varname>imageName</varname> may transparently refer to a + manifest list of images which support multiple architectures and/or + operating systems, you can supply the <option>--os</option> and + <option>--arch</option> arguments to specify exactly which image you want. + By default it will match the OS and architecture of the host the command is + run on. + +<programlisting> +$ nix-prefetch-docker --image-name mysql --image-tag 5 --arch x86_64 --os linux +</programlisting> + + Desired image name and tag can be set using + <option>--final-image-name</option> and <option>--final-image-tag</option> + arguments: + +<programlisting> +$ nix-prefetch-docker --image-name mysql --image-tag 5 --final-image-name eu.gcr.io/my-project/mysql --final-image-tag prod +</programlisting> + </para> </section> <section xml:id="ssec-pkgs-dockerTools-exportImage"> diff --git a/pkgs/build-support/docker/nix-prefetch-docker b/pkgs/build-support/docker/nix-prefetch-docker new file mode 100755 index 00000000000..839dc87487a --- /dev/null +++ b/pkgs/build-support/docker/nix-prefetch-docker @@ -0,0 +1,173 @@ +#! /usr/bin/env bash + +set -e -o pipefail + +os= +arch= +imageName= +imageTag= +imageDigest= +finalImageName= +finalImageTag= +hashType=$NIX_HASH_ALGO +hashFormat=$hashFormat +format=nix + +usage(){ + echo >&2 "syntax: nix-prefetch-docker [options] [IMAGE_NAME [IMAGE_TAG|IMAGE_DIGEST]] + +Options: + --os os OS to fetch image for + --arch linux Arch to fetch image for + --image-name name Name of the image to fetch + --image-tag tag Image tag + --image-digest digest Image digest + --final-image-name name Desired name of the image + --final-image-tag tag Desired image tag + --json Output result in json format instead of nix + --quiet Only print the final result +" + exit 1 +} + +get_image_digest(){ + local imageName=$1 + local imageTag=$2 + + if test -z "$imageTag"; then + imageTag="latest" + fi + + skopeo inspect "docker://$imageName:$imageTag" | jq '.Digest' -r +} + +get_name() { + local imageName=$1 + local imageTag=$2 + + echo "docker-image-$(echo "$imageName:$imageTag" | tr '/:' '-').tar" +} + +argi=0 +argfun="" +for arg; do + if test -z "$argfun"; then + case $arg in + --os) argfun=set_os;; + --arch) argfun=set_arch;; + --image-name) argfun=set_imageName;; + --image-tag) argfun=set_imageTag;; + --image-digest) argfun=set_imageDigest;; + --final-image-name) argfun=set_finalImageName;; + --final-image-tag) argfun=set_finalImageTag;; + --quiet) QUIET=true;; + --json) format=json;; + --help) usage; exit;; + *) + : $((++argi)) + case $argi in + 1) imageName=$arg;; + 2) [[ $arg == *"sha256"* ]] && imageDigest=$arg || imageTag=$arg;; + *) exit 1;; + esac + ;; + esac + else + case $argfun in + set_*) + var=${argfun#set_} + eval $var=$arg + ;; + esac + argfun="" + fi +done + +if test -z "$imageName"; then + usage +fi + +if test -z "$os"; then + os=linux +fi + +if test -z "$arch"; then + arch=amd64 +fi + +if test -z "$hashType"; then + hashType=sha256 +fi + +if test -z "$hashFormat"; then + hashFormat=base32 +fi + +if test -z "$finalImageName"; then + finalImageName="$imageName" +fi + +if test -z "$finalImageTag"; then + if test -z "$imageTag"; then + finalImageTag="latest" + else + finalImageTag="$imageTag" + fi +fi + +if test -z "$imageDigest"; then + imageDigest=$(get_image_digest $imageName $imageTag) +fi + +sourceUrl="docker://$imageName@$imageDigest" + +tmpPath="$(mktemp -d "${TMPDIR:-/tmp}/skopeo-copy-tmp-XXXXXXXX")" +trap "rm -rf \"$tmpPath\"" EXIT + +tmpFile="$tmpPath/$(get_name $finalImageName $finalImageTag)" + +if test -z "$QUIET"; then + skopeo --override-os ${os} --override-arch ${arch} copy "$sourceUrl" "docker-archive://$tmpFile:$finalImageName:$finalImageTag" +else + skopeo --override-os ${os} --override-arch ${arch} copy "$sourceUrl" "docker-archive://$tmpFile:$finalImageName:$finalImageTag" > /dev/null +fi + +# Compute the hash. +imageHash=$(nix-hash --flat --type $hashType --base32 "$tmpFile") + +# Add the downloaded file to Nix store. +finalPath=$(nix-store --add-fixed "$hashType" "$tmpFile") + +if test -z "$QUIET"; then + echo "-> ImageName: $imageName" + echo "-> ImageDigest: $imageDigest" + echo "-> FinalImageName: $finalImageName" + echo "-> FinalImageTag: $finalImageTag" + echo "-> ImagePath: $finalPath" + echo "-> ImageHash: $imageHash" +fi + +if [ "$format" == "nix" ]; then +cat <<EOF +{ + imageName = "$imageName"; + imageDigest = "$imageDigest"; + sha256 = "$imageHash"; + finalImageName = "$finalImageName"; + finalImageTag = "$finalImageTag"; +} +EOF + +else + +cat <<EOF +{ + "imageName": "$imageName", + "imageDigest": "$imageDigest", + "sha256": "$imageHash", + "finalImageName": "$finalImageName", + "finalImageTag": "$finalImageTag" +} +EOF + +fi diff --git a/pkgs/build-support/docker/nix-prefetch-docker.nix b/pkgs/build-support/docker/nix-prefetch-docker.nix new file mode 100644 index 00000000000..03a936e08e0 --- /dev/null +++ b/pkgs/build-support/docker/nix-prefetch-docker.nix @@ -0,0 +1,26 @@ +{ stdenv, makeWrapper, nix, skopeo }: + +with stdenv.lib; + +stdenv.mkDerivation { + name = "nix-prefetch-docker"; + + nativeBuildInputs = [ makeWrapper ]; + + unpackPhase = ":"; + + installPhase = '' + install -vD ${./nix-prefetch-docker} $out/bin/$name; + wrapProgram $out/bin/$name \ + --prefix PATH : ${makeBinPath [ nix skopeo ]} \ + --set HOME /homeless-shelter + ''; + + preferLocalBuild = true; + + meta = { + description = "Script used to obtain source hashes for dockerTools.pullImage"; + maintainers = with maintainers; [ offline ]; + platforms = platforms.unix; + }; +} diff --git a/pkgs/top-level/all-packages.nix b/pkgs/top-level/all-packages.nix index 18a364ec2c1..3f7a3dcdfd4 100644 --- a/pkgs/top-level/all-packages.nix +++ b/pkgs/top-level/all-packages.nix @@ -167,6 +167,8 @@ in dockerTools = callPackage ../build-support/docker { }; + nix-prefetch-docker = callPackage ../build-support/docker/nix-prefetch-docker.nix { }; + docker-compose = python3Packages.callPackage ../applications/virtualization/docker-compose {}; docker-ls = callPackage ../tools/misc/docker-ls { }; |