Initial support for ls

This commit is contained in:
Joe 2021-05-04 21:28:35 -05:00
parent 8f71fce660
commit 2c05bfe4f8
1 changed files with 74 additions and 21 deletions

View File

@ -12,26 +12,26 @@ function docker_cli_plugin_metadata {
}
__usage="
Usage: docker artifact [command] [options]
Usage: docker artifact [command] [options] [args]
Commands:
ls - List files available to download directly from an image
download - Download files directly from an image that has been labeled
label - Label an image
ls - List labeled files available to download directly from an image
download - Download labeled files directly from an image
label - Label files in an image
Command usage:
docker artifact ls [options] image_name
docker artifact download [options] image_name file...
docker artifact label [options] image_name file...
Options:
-v - verbose output
-q - quiet output
Examples:
docker artifact ls infogulch/artifact-test
docker artifact download infogulch/artifact-test /app/othertestfile.txt
docker artifact label infogulch/artifact-test /testfile.txt
@ -44,7 +44,7 @@ function main {
;;
artifact)
case "$2" in
ls)
ls|list)
list "${@:3}"
;;
label)
@ -61,15 +61,57 @@ function main {
esac
}
function _search_layer {
local idmap="$1"
local imagetar="$2"
local layertar="$3"
local search="$4"
# look up digest associated with layer path
local digest="$(jq --arg key "$layertar" -r '.[$key]' <<< "$idmap")"
# extract layer from image | list files in layer | add / prefix | search for file | append =$digest to each found file
tar -f "$imagetar" -x "$layertar" -O | tar -t | sed s_^_/_ | grep -wx "$search" | sed 's_.$_\0='"$digest"'_'
function list {
local list="$(list_json "$@" | jq -r 'keys | .[]' | sed 's_^_ _')"
echo " ** The following files are available to download from $1: "
echo "$list"
}
function list_json {
local image="$1"
local regex='^([-_a-z\.]+)/([-_a-z]+)(:([-_a-z]+))?$'
if [[ $image =~ $regex ]] ; then
registry="${BASH_REMATCH[1]}"
image="${BASH_REMATCH[2]}"
tag="${BASH_REMATCH[4]:-latest}"
if ! [[ $registry =~ \. ]] ; then
image="$registry/$image"
registry="registry-1.docker.io"
fi
else
echo "Failed to parse image '$image'"
exit 1
fi
local token="$(get_token "$registry" "$image")"
LOG "Querying manifest to extract labels for '$registry/$image:$tag"
local manifest="$(curl --silent \
-H "Accept:application/vnd.docker.container.image.v1+json" \
-H "Authorization: Bearer $token" \
"https://$registry/v2/$image/manifests/$tag")"
local labels="$(jq -r '.history[].v1Compatibility' <<< "$manifest" | jq --slurp -r '[.[].config | select(.Labels != null) | .Labels] | add')"
jq <<< "$labels"
}
function get_token {
local registry="$1"
local image="$2"
if [[ ! -z "$REGISTRY_TOKEN" ]] ; then
echo "$REGISTRY_TOKEN"
return
fi
LOG "Retrieving registry token for $registry/$image"
case "$registry" in
registry-1.docker.io)
curl --silent "https://auth.docker.io/token?scope=repository:$image:pull&service=registry.docker.io" \
| jq -r .token
;;
*.azurecr.io)
echo "$REGISTRY_TOKEN"
;;
*.dkr.ecr.*.amazonaws.com)
aws ecr get-authorization-token | jq -r '.authorizationData[0].authorizationToken'
;;
esac
}
function label {
@ -126,6 +168,17 @@ function label {
echo " ** Run 'docker push $image' to push it to your container repository"
}
function _search_layer {
local idmap="$1"
local imagetar="$2"
local layertar="$3"
local search="$4"
# look up digest associated with layer path
local digest="$(jq --arg key "$layertar" -r '.[$key]' <<< "$idmap")"
# extract layer from image | list files in layer | add / prefix | search for file | append =$digest to each found file
tar -f "$imagetar" -x "$layertar" -O | tar -t | sed s_^_/_ | grep -wx "$search" | sed 's_.$_\0='"$digest"'_'
}
function delete_files {
LOG "Cleaning up temp files $@"
rm "$@"