about summary refs log tree commit diff
path: root/pkgs/build-support/docker
diff options
context:
space:
mode:
authorKoen Wilde <koen@chillheid.nl>2022-10-12 23:46:01 +0200
committerKoen Wilde <koen@chillheid.nl>2022-10-13 16:27:13 +0200
commit2f5fcda329757f9a3d58dca4842e075c7f14ee2d (patch)
tree8e173b4a891bdf1ab4ce229be5edafd668d834e9 /pkgs/build-support/docker
parent9bf75dd50b7b6d3ce6aaf6563db95f41438b9bdb (diff)
build-support: Fix error when building images with many layers
When building a docker image using `dockertools.buildLayeredImage`, the
resulting image layers are passed to `jq` through the command line. When
building an image with too many layers this would exceed the maximum
command line argument length.

Hence, we store the list of layers in the Nix store and pass them to
`jq` as a file argument using `--slurpfile`.

Fixes #140908.
Diffstat (limited to 'pkgs/build-support/docker')
-rw-r--r--pkgs/build-support/docker/default.nix21
1 files changed, 11 insertions, 10 deletions
diff --git a/pkgs/build-support/docker/default.nix b/pkgs/build-support/docker/default.nix
index 47fd99c12f8e9..7eb81623046a8 100644
--- a/pkgs/build-support/docker/default.nix
+++ b/pkgs/build-support/docker/default.nix
@@ -935,33 +935,34 @@ rec {
           # following lines, double-check that your code behaves properly
           # when the number of layers equals:
           #      maxLayers-1, maxLayers, and maxLayers+1, 0
-          store_layers="$(
-            paths |
-              jq -sR '
-                rtrimstr("\n") | split("\n")
-                  | (.[:$maxLayers-1] | map([.])) + [ .[$maxLayers-1:] ]
-                  | map(select(length > 0))
+          paths |
+            jq -sR '
+              rtrimstr("\n") | split("\n")
+                | (.[:$maxLayers-1] | map([.])) + [ .[$maxLayers-1:] ]
+                | map(select(length > 0))
               ' \
-                --argjson maxLayers "$availableLayers"
-          )"
+              --argjson maxLayers "$availableLayers" > store_layers.json
 
+          # The index on $store_layers is necessary because the --slurpfile
+          # automatically reads the file as an array.
           cat ${baseJson} | jq '
             . + {
               "store_dir": $store_dir,
               "from_image": $from_image,
-              "store_layers": $store_layers,
+              "store_layers": $store_layers[0],
               "customisation_layer", $customisation_layer,
               "repo_tag": $repo_tag,
               "created": $created
             }
             ' --arg store_dir "${storeDir}" \
               --argjson from_image ${if fromImage == null then "null" else "'\"${fromImage}\"'"} \
-              --argjson store_layers "$store_layers" \
+              --slurpfile store_layers store_layers.json \
               --arg customisation_layer ${customisationLayer} \
               --arg repo_tag "$imageName:$imageTag" \
               --arg created "$created" |
             tee $out
         '';
+
         result = runCommand "stream-${baseName}"
           {
             inherit (conf) imageName;