рд╡рд┐рд╡рд░рдг
рдЬрдм 10 рд╕реЗ рдЕрдзрд┐рдХ рдЪрд┐рддреНрд░ рд╣реЛрддреЗ рд╣реИрдВ, рддреЛ рд╣рдо рдбреЙрдХрд░ рд╣рдм рдкрд░ рдбреЙрдХрд░ рдирд┐рдЬреА рднрдВрдбрд╛рд░ рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд░рддреЗ рд╣реИрдВред
рд╣рдо рдбреЛрдХрд░ рд╣рдм рдкрд░ рдирд┐рд░реНрдорд┐рдд рдФрд░ рд╡рд░реНрддрдорд╛рди рдореЗрдВ рдкреНрд░рд╕реНрддреБрдд рдЫрд╡рд┐рдпреЛрдВ рдХреА рддреБрд▓рдирд╛ рдХрд░рдиреЗ рдореЗрдВ рд╕рдХреНрд╖рдо рд╣реЛрдиреЗ рдХреЗ рд▓рд┐рдП рдбреЙрдХрд░ рд╣рдм рд╕реЗ рдбреЙрдХрд░ рдЫрд╡рд┐рдпреЛрдВ рдХреА рдЬрд╛рдирдХрд╛рд░реА рдкреНрд░рд╛рдкреНрдд рдХрд░рдирд╛ рдЪрд╛рд╣рддреЗ рд╣реИрдВред
рдореИрдВ Google рдореЗрдВ рдорд┐рд▓рдиреЗ рд╡рд╛рд▓реЗ рдЖрджреЗрд╢реЛрдВ рдХреЛ рдЪрд▓рд╛рдХрд░ рдСрде рдЯреЛрдХрди рдкреНрд░рд╛рдкреНрдд рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП рдХрд░реНрд▓ рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд░рдиреЗ рдХрд╛ рдкреНрд░рдпрд╛рд╕ рдХрд░рддрд╛ рд╣реВрдВред
рдРрд╕рд╛ рд▓рдЧ рд░рд╣рд╛ рд╣реИ:
UNAME="exampleuser"
UPASS="examplepass"
PRODUCT="examplecompany"
REPOSITORY="$PRODUCT"
SERVICE="exampleservice"
рдореИрдВ рдирд┐рдореНрдирд▓рд┐рдЦрд┐рдд рддрд░реАрдХреЛрдВ рд╕реЗ рдЯреЛрдХрди рдкреНрд░рд╛рдкреНрдд рдХрд░рдиреЗ рдХрд╛ рдкреНрд░рдпрд╛рд╕ рдХрд░рддрд╛ рд╣реВрдВ:
TOKEN=$(curl -u $UNAME:$UPASS "https://auth.docker.io/token?service=registry.docker.io&scope=repository:$REPOSITORY:pull&account=$UNAME" | jq -r .token)
TOKEN=$(curl -u $UNAME:$UPASS "https://auth.docker.io/token?service=index.docker.io&scope=repository:$REPOSITORY:pull&account=$UNAME" | jq -r .token)
TOKEN=$(curl -u $UNAME:$UPASS "https://auth.docker.io/token?service=registry.docker.io&scope=repository:$REPOSITORY:pull&account=$UNAME&offline_token=true" | jq -r .token)
TOKEN=$(curl -u $UNAME:$UPASS "https://auth.docker.io/token?service=registry.docker.io&scope=repository:$REPOSITORY:$SERVICE:pull&account=$UNAME&offline_token=true" | jq -r .token)
TOKEN=$(curl -u $UNAME:$UPASS "https://auth.docker.io/token?service=registry.docker.io&scope=repository:$REPOSITORY:$SERVICE&account=$UNAME&offline_token=true" | jq -r .token)
рд╕рднреА рдорд╛рдорд▓реЛрдВ рдореЗрдВ рдореБрдЭреЗ рдХреБрдЫ рдЯреЛрдХрди рдорд┐рд▓рддреЗ рд╣реИрдВ, рдирд┐рдореНрдирд▓рд┐рдЦрд┐рдд рддрд░реАрдХреЛрдВ рд╕реЗ рдореЗрд░реЗ рдирд┐рдЬреА рднрдВрдбрд╛рд░ рд╕реЗ рдкреНрд░рдХрдЯ рд╣реЛрдиреЗ рдХрд╛ рдкреНрд░рдпрд╛рд╕ рдХрд░реЗрдВ:
1.
REPO="$PRODUCT/$SERVICE"
TAG=latest
REGISTRY=https://registry-1.docker.io/v2
URI="$REGISTRY/$REPO/manifests/$TAG"
echo URI=$URI
MANIFEST="`curl -skL -o /dev/null -D- $URI`"
CHALLENGE="`grep "Www-Authenticate" <<<"$MANIFEST"`"
if [[ CHALLENGE ]]; then
IFS=\" read _ REALM _ SERVICE _ SCOPE _ <<<"$CHALLENGE"
echo REALM is $REALM
echo SERVICE is $SERVICE
echo SCOPE is $SCOPE
TOKEN="`curl -skL "$REALM?service=$SERVICE&scope=$SCOPE"`"
IFS=\" read _ _ _ TOKEN _ <<<"$TOKEN"
echo TOKEN is $TOKEN
MANIFEST="`curl -isk -X GET -H "Authorization: Bearer $TOKEN" $URI`"
echo "RESPONSE is $MANIFEST"
fi
2.
curl -s -D - -H "Authorization: Bearer ${TOKEN}" -H "Accept: application/vnd.docker.distribution.manifest.v2+json" https://index.docker.io/v2/repositories/$PRODUCT/$SERVICE/manifests/latest
рд╣рдореЗрд╢рд╛ рдкреНрд░рд╛рдкреНрдд рдХрд░реЗрдВ
RESPONSE is HTTP/1.1 401 Unauthorized
Content-Type: application/json; charset=utf-8
Docker-Distribution-Api-Version: registry/2.0
Www-Authenticate: Bearer realm="https://auth.docker.io/token",service="registry.docker.io",scope="examplecompany/exampleservice:pull",error="insufficient_scope"
Date: Wed, 15 Mar 2017 16:15:52 GMT
Content-Length: 155
Strict-Transport-Security: max-age=31536000
{"errors":[{"code":"UNAUTHORIZED","message":"authentication required","detail":[{"Type":"repository","Class":"","Name":"examplecompany/exampleservice","Action":"pull"}]}]}
рдбреЙрдХрд░ рд╣рдм рд╕реЗ рдореЗрд░реЗ рд▓рд┐рдП рд╕рднреА рдЖрд╡рд╢реНрдпрдХ рдЬрд╛рдирдХрд╛рд░реА рдХреИрд╕реЗ рдареАрдХ рдХрд░реЗрдВ?
рдЬрдм рдореИрдВ рдЯреИрдЧ рдкреНрд░рд╛рдкреНрдд рдХрд░рдиреЗ рдХрд╛ рдкреНрд░рдпрд╛рд╕ рдХрд░рддрд╛ рд╣реВрдВ
REPO_LIST=$(curl -s -H "Authorization: JWT ${TOKEN}" https://hub.docker.com/v2/repositories/${PRODUCT}/?page_size=10000 | jq -r '.results|.[]|.name')
рдореБрдЭреЗ рдХреЛрдИ рд╕рдорд╕реНрдпрд╛ рдирд╣реАрдВ рд╣реИред
рдЗрд╕рдХреЗ рдЕрд▓рд╛рд╡рд╛, рдореИрдВ рдЬреЛ рдЪрд╛рд╣рддрд╛ рд╣реВрдВ рдЙрд╕реЗ рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП рдореБрдЭреЗ рдХреЛрдИ рдХрд╛рдо рдирд╣реАрдВ рдорд┐рд▓ рд░рд╣рд╛ рд╣реИред
рд╕рдорд╕реНрдпрд╛ рдХреЛ рдкреБрди: рдкреЗрд╢ рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП рдХрджрдо:
рдЖрдкрдХреЛ рдкреНрд░рд╛рдкреНрдд рдкрд░рд┐рдгрд╛рдореЛрдВ рдХрд╛ рд╡рд░реНрдгрди рдХрд░реЗрдВ:
{"errors":[{"code":"UNAUTHORIZED","message":"authentication required","detail":[{"Type":"repository","Class":"","Name":"examplecompany/exampleservice","Action":"pull"}]}]}
рдЖрдкрдХреЗ рджреНрд╡рд╛рд░рд╛ рдЕрдкреЗрдХреНрд╖рд┐рдд рдкрд░рд┐рдгрд╛рдореЛрдВ рдХрд╛ рд╡рд░реНрдгрди рдХрд░реЗрдВ:
Json рдЬрд┐рд╕рдореЗрдВ рд╡рд░реНрддрдорд╛рди рдореЗрдВ рдбреЙрдХрд░ рд╣рдм рдЫрд╡рд┐рдпреЛрдВ рдкрд░ рдкреНрд░рд╕реНрддреБрдд рдХреА рдЧрдИ рдЬрд╛рдирдХрд╛рд░реА рд╣реИред
https://github.com/docker/docker/issues/29257#issuecomment -266121974 рдкрд░ рдЪрд░реНрдЪрд╛ рд╢рд╛рдпрдж рдпрд╣рд╛рдВ рд╕рдВрдмрдВрдзрд┐рдд рд╣реИ
рдЕрд░реЗ @westsouthnight , рд╢рд╛рдпрдж рдпрд╣ рд╕реНрдХреНрд░рд┐рдкреНрдЯ рдЖрдкрдХреА рдорджрдж рдХрд░ рд╕рдХрддреА рд╣реИ: https://gist.github.com/cirocosta/fb6b90cb7651ff21eda4838a73e3710b ред
рдпрд╣ рдЯреЛрдХрди рдкреБрдирд░реНрдкреНрд░рд╛рдкреНрдд рдХрд░рддреЗ рд╕рдордп рдореВрд▓ рдкреНрд░рдорд╛рдгреАрдХрд░рдг рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП -u
рдХрд╛ рдЙрдкрдпреЛрдЧ рдирд╣реАрдВ рдХрд░рддрд╛ рд╣реИ, рд▓реЗрдХрд┐рди рдореИрдВрдиреЗ рдПрдХ рдирд┐рдЬреА рднрдВрдбрд╛рд░ рдХреЗ рд╕рд╛рде рдкрд░реАрдХреНрд╖рдг рдХрд┐рдпрд╛ рдФрд░ -u
рд╕реЗ get_token() {
рд╡рд╛рд╕реНрддрд╡ рдореЗрдВ рдХрд╛рдо рдХрд░рддрд╛ рд╣реИ: рдПрдХ рдирд┐рдЬреА рд░рдЬрд┐рд╕реНрдЯреНрд░реА рдХреЗ рд╕рд╛рде I -u
рдХрд╛ рдЙрдкрдпреЛрдЧ рд╣реЛрдиреЗ рдкрд░ рд╣реА рд░рдЬрд┐рд╕реНрдЯреНрд░реА рдХреЛ рдкреБрдирдГ рдкреНрд░рд╛рдкреНрдд рдХрд░ рд╕рдХрддреЗ рд╣реИрдВред
curl \
-u user:pass \
--silent \
"https://auth.docker.io/token?scope=repository:$image:pull&service=registry.docker.io" \
| jq -r '.token'
рдореБрдЭреЗ рдмрддрд╛рдПрдВ рдХрд┐ рдХреНрдпрд╛ рдЗрд╕рд╕реЗ рдорджрдж рдорд┐рд▓рддреА рд╣реИ
рдореБрдЭреЗ рдЗрд╕ рдореБрджреНрджреЗ рдХреЛ рдмрдВрдж рдХрд░рдиреЗ рджреЗрдВ, рдХреНрдпреЛрдВрдХрд┐ GitHub рдореБрджреНрджрд╛ рдЯреНрд░реИрдХрд░ рд╡рд╛рд╕реНрддрд╡ рдореЗрдВ рдПрдХ рд╕рд╛рдорд╛рдиреНрдп рд╕рдорд░реНрдерди рдордВрдЪ рдХреЗ рд░реВрдк рдореЗрдВ рдЕрднрд┐рдкреНрд░реЗрдд рдирд╣реАрдВ рд╣реИ,
рд▓реЗрдХрд┐рди рдмрдЧ рдФрд░ рдлреАрдЪрд░ рдЕрдиреБрд░реЛрдзреЛрдВ рдХреА рд░рд┐рдкреЛрд░реНрдЯ рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдПред рдЕрдиреНрдп рдкреНрд░рдХрд╛рд░ рдХреЗ рдкреНрд░рд╢реНрдиреЛрдВ рдХреЗ рд▓рд┐рдП, рдЗрдирдореЗрдВ рд╕реЗ рдХрд┐рд╕реА рдПрдХ рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд░рдиреЗ рдкрд░ рд╡рд┐рдЪрд╛рд░ рдХрд░реЗрдВ;
рдпрд╣ рдкреНрд░рд╢реНрди рднреА рд╕реАрдзреЗ рдЗрд╕ рднрдВрдбрд╛рд░ рдореЗрдВ рд╕реНрд░реЛрдд рдХреЛрдб рд╕реЗ рд╕рдВрдмрдВрдзрд┐рдд рдирд╣реАрдВ рд╣реИ, рдмрд▓реНрдХрд┐ рдбреЙрдХрд░ рд╣рдм (рдФрд░ рд╡рд╣рд╛рдВ рдкреНрд░рдпреБрдХреНрдд рдкреНрд░рдорд╛рдгреАрдХрд░рдг) рд╕реЗ рд╕рдВрдмрдВрдзрд┐рдд рд╣реИред рд▓реЗрдХрд┐рди рдмреЗрдЭрд┐рдЭрдХ рдмрд╛рддрдЪреАрдд рдЬрд╛рд░реА рд░рдЦреЗрдВ