Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
41 changes: 37 additions & 4 deletions hack/bin/upload-image.sh
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,8 @@ readonly DOCKER_TAG=${DOCKER_TAG:?"Please set the DOCKER_TAG env variable"}
readonly usage="USAGE: $0 <image_attr>"
readonly IMAGE_ATTR=${1:?$usage}

SCRIPT_DIR=$(cd -- "$(dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )
ROOT_DIR=$(cd -- "$SCRIPT_DIR/../../" &> /dev/null && pwd)
SCRIPT_DIR=$(cd -- "$(dirname -- "${BASH_SOURCE[0]}")" &>/dev/null && pwd)
ROOT_DIR=$(cd -- "$SCRIPT_DIR/../../" &>/dev/null && pwd)
readonly SCRIPT_DIR ROOT_DIR

credsArgs=""
Expand All @@ -27,6 +27,39 @@ if [[ "${DOCKER_USER+x}" != "" ]]; then
credsArgs="--dest-creds=$DOCKER_USER:$DOCKER_PASSWORD"
fi

# Retry a command with exponential backoff
# quay.io sometimes rate-limits us, so try again.
# Also, skopeo's retry logic doesn't properly work, look here if you want to see very badly written go code:
# https://github.com/containers/skopeo/blob/869d496f185cc086f22d6bbb79bb57ac3a415617/vendor/github.com/containers/common/pkg/retry/retry.go#L52-L113
function retry {
local maxAttempts=$1
local secondsDelay=1
local attemptCount=1
local output=
shift 1

while [ $attemptCount -le "$maxAttempts" ]; do
output=$("$@")
local status=$?

if [ $status -eq 0 ]; then
break
fi

if [ $attemptCount -lt "$maxAttempts" ]; then
echo "Command [$*] failed after attempt $attemptCount of $maxAttempts. Retrying in $secondsDelay second(s)." >&2
sleep $secondsDelay
elif [ $attemptCount -eq "$maxAttempts" ]; then
echo "Command [$*] failed after $attemptCount attempt(s)" >&2
return $status
fi
attemptCount=$((attemptCount + 1))
secondsDelay=$((secondsDelay * 2))
done

echo "$output"
}

tmp_link_store=$(mktemp -d)
# Using dockerTools.streamLayeredImage outputs an executable which prints the
# image tar on stdout when executed. This is done so we don't store large images
Expand All @@ -38,8 +71,8 @@ tmp_link_store=$(mktemp -d)
image_stream_file="$tmp_link_store/image_stream"
nix -v --show-trace -L build -f "$ROOT_DIR/nix" "$IMAGE_ATTR" -o "$image_stream_file"
image_file="$tmp_link_store/image"
"$image_stream_file" > "$image_file"
"$image_stream_file" >"$image_file"
repo=$(skopeo list-tags "docker-archive://$image_file" | jq -r '.Tags[0] | split(":") | .[0]')
printf "*** Uploading $image_file to %s:%s" "$repo" "$DOCKER_TAG"
# shellcheck disable=SC2086
skopeo --insecure-policy copy --retry-times 5 $credsArgs "docker-archive://$image_file" "docker://$repo:$DOCKER_TAG"
retry 5 skopeo --insecure-policy copy --retry-times 5 $credsArgs "docker-archive://$image_file" "docker://$repo:$DOCKER_TAG"