Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Pushing multiple tags to Amazon ECR #166

Closed
michaelhelmick opened this issue Oct 6, 2020 · 12 comments
Closed

Pushing multiple tags to Amazon ECR #166

michaelhelmick opened this issue Oct 6, 2020 · 12 comments

Comments

@michaelhelmick
Copy link

Troubleshooting

Before sumbitting a bug report please read the Troubleshooting doc.

Behaviour

I'd like to push an image with multiple tags to our ECR.

Steps to reproduce this issue

Expected behaviour

The built docker image should be pushed to our Amazon ECR.

Actual behaviour

If using full registry as a tag:

- name: Build & Push image
  uses: docker/build-push-action@v2
  env:
    DOCKER_BUILDKIT: 1
  with:
    context: .
    file: ./Dockerfile
    push: true
    cache-from: type=local,src=/tmp/.buildx-cache
    cache-to: type=local,dest=/tmp/.buildx-cache
    tags: |
    repo:${{ github.sha }}
    repo:latest

I get this error:

#28 ERROR: server message: insufficient_scope: authorization failed
1294
------
1295
 > exporting to image:
1296
------
1297
failed to solve: rpc error: code = Unknown desc = server message: insufficient_scope: authorization failed
1298
Error: The process '/usr/bin/docker' failed with exit code 1

With full registry:

- name: Build & Push image
  uses: docker/build-push-action@v2
  env:
    DOCKER_BUILDKIT: 1
  with:
    context: .
    file: ./Dockerfile
    push: true
    cache-from: type=local,src=/tmp/.buildx-cache
    cache-to: type=local,dest=/tmp/.buildx-cache
    tags: |
      000000000000.dkr.ecr.nn-nnnn-1.amazonaws.com/repo:${{ github.sha }}
      000000000000.dkr.ecr.nn-nnnn-1.amazonaws.com/repo:latest

Gave me this error

#28 ERROR: unexpected status: 401 Unauthorized
1301
------
1302
 > exporting to image:
1303
------
1304
failed to solve: rpc error: code = Unknown desc = unexpected status: 401 Unauthorized
1305
Error: The process '/usr/bin/docker' failed with exit code 1

I believe the errors were reversed when I didn't use driver-opts: image=moby/buildkit:master

Configuration

- name: Login to ECR
  uses: docker/login-action@v1
  with:
    registry: 000000000000.dkr.ecr.nn-nnnn-1.amazonaws.com
    username: ${{ secrets.AWS_ACCESS_KEY_ID }}
    password: ${{ secrets.AWS_SECRET_ACCESS_KEY }}

- name: Set up Docker Buildx
  uses: docker/setup-buildx-action@v1
  with:
    driver-opts: image=moby/buildkit:master

- name: Cache Docker layers
  uses: actions/cache@v2
  with:
    path: /tmp/.buildx-cache
    key: ${{ runner.os }}-buildx-${{ github.sha }}
    restore-keys: |
      ${{ runner.os }}-buildx-

- name: Build & Push image
  uses: docker/build-push-action@v2
  env:
    DOCKER_BUILDKIT: 1
  with:
    context: .
    file: ./Dockerfile
    push: true
    cache-from: type=local,src=/tmp/.buildx-cache
    cache-to: type=local,dest=/tmp/.buildx-cache
    tags: |
    repo:${{ github.sha }}
    repo:latest

Alternate tags with full registry:

- name: Build & Push image
  uses: docker/build-push-action@v2
  env:
    DOCKER_BUILDKIT: 1
  with:
    context: .
    file: ./Dockerfile
    push: true
    cache-from: type=local,src=/tmp/.buildx-cache
    cache-to: type=local,dest=/tmp/.buildx-cache
    tags: |
      000000000000.dkr.ecr.nn-nnnn-1.amazonaws.com/repo:${{ github.sha }}
      000000000000.dkr.ecr.nn-nnnn-1.amazonaws.com/repo:latest

Logs

Excluding logs because this is a private repo and I don't have time right now to strip secrets.

Referencing #20 so people can see a link if they are searching.

@crazy-max
Copy link
Member

crazy-max commented Oct 6, 2020

@michaelhelmick

If using full registry as a tag:

- name: Build & Push image
  uses: docker/build-push-action@v2
  env:
    DOCKER_BUILDKIT: 1
  with:
    context: .
    file: ./Dockerfile
    push: true
    cache-from: type=local,src=/tmp/.buildx-cache
    cache-to: type=local,dest=/tmp/.buildx-cache
    tags: |
    repo:${{ github.sha }}
    repo:latest

I get this error:

#28 ERROR: server message: insufficient_scope: authorization failed
1294
------
1295
 > exporting to image:
1296
------
1297
failed to solve: rpc error: code = Unknown desc = server message: insufficient_scope: authorization failed
1298
Error: The process '/usr/bin/docker' failed with exit code 1

If you don't specify the registry in your tag it will try to push to DockerHub (default if not defined). See https://docs.docker.com/engine/reference/commandline/tag/

With full registry:

- name: Build & Push image
  uses: docker/build-push-action@v2
  env:
    DOCKER_BUILDKIT: 1
  with:
    context: .
    file: ./Dockerfile
    push: true
    cache-from: type=local,src=/tmp/.buildx-cache
    cache-to: type=local,dest=/tmp/.buildx-cache
    tags: |
      000000000000.dkr.ecr.nn-nnnn-1.amazonaws.com/repo:${{ github.sha }}
      000000000000.dkr.ecr.nn-nnnn-1.amazonaws.com/repo:latest

Gave me this error

#28 ERROR: unexpected status: 401 Unauthorized
1301
------
1302
 > exporting to image:
1303
------
1304
failed to solve: rpc error: code = Unknown desc = unexpected status: 401 Unauthorized
1305
Error: The process '/usr/bin/docker' failed with exit code 1

Looks like permission scope is not enough (no tag pushed from the few log you give me). Are you able to push to the registry from your computer? See Amazon ECR Managed Policies

@michaelhelmick
Copy link
Author

@crazy-max, I updated our deploy policy to be less strict

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "VisualEditor0",
            "Effect": "Allow",
            "Action": [
                "ecs:DiscoverPollEndpoint",
                "ecr:CreateRepository",
                "ecs:CreateCluster",
                "ecr:GetAuthorizationToken",
                "ecs:DeleteService",
                "ecs:DescribeTaskDefinition",
                "ecs:ListServices",
                "ecs:DeregisterTaskDefinition",
                "ecs:UpdateService",
                "iam:PassRole",
                "ecs:CreateService",
                "ecs:ListTaskDefinitionFamilies",
                "ecs:RegisterTaskDefinition",
                "ecs:DescribeServices",
                "ecs:ListTaskDefinitions",
                "ecs:ListClusters"
            ],
            "Resource": "*"
        },
        {
            "Sid": "VisualEditor1",
            "Effect": "Allow",
            "Action": "ecs:*",
            "Resource": [
                "arn:aws:ecs:*:*:task-definition/*:*",
                "arn:aws:ecs:*:*:task/*",
                "arn:aws:ecs:*:*:container-instance/*",
                "arn:aws:ecs:*:*:cluster/*"
            ]
        },
        {
            "Sid": "VisualEditor2",
            "Effect": "Allow",
            "Action": [
                "ecr:*",
                "cloudtrail:LookupEvents"
            ],
            "Resource": "*"
        }
    ]
}

This currently works using:

aws-actions/amazon-ecr-login@v1 uses env vars that are set for key/secret

- name: Login to Amazon ECR
   id: login-ecr
   uses: aws-actions/amazon-ecr-login@v1

- name: Build, tag, and push image to Amazon ECR
  env:
    ECR_REGISTRY: ${{ steps.login-ecr.outputs.registry }}
    ECR_REPOSITORY: repo
    IMAGE_TAG: ${{ github.sha }}
  run: |
    docker build -t $ECR_REGISTRY/$ECR_REPOSITORY:$IMAGE_TAG .
    docker push $ECR_REGISTRY/$ECR_REPOSITORY:$IMAGE_TAG

@crazy-max
Copy link
Member

crazy-max commented Oct 7, 2020

@michaelhelmick Ok I've mode some tests on my own and everything looks good to me.

From what I see, your policy won't be able to push on a registry (missing InitiateLayerUpload, UploadLayerPart, CompleteLayerUpload, PutImage).

Here is my policy:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "ecr:GetAuthorizationToken",
                "ecr:BatchCheckLayerAvailability",
                "ecr:GetDownloadUrlForLayer",
                "ecr:GetRepositoryPolicy",
                "ecr:DescribeRepositories",
                "ecr:ListImages",
                "ecr:DescribeImages",
                "ecr:BatchGetImage",
                "ecr:GetLifecyclePolicy",
                "ecr:GetLifecyclePolicyPreview",
                "ecr:ListTagsForResource",
                "ecr:DescribeImageScanFindings",
                "ecr:InitiateLayerUpload",
                "ecr:UploadLayerPart",
                "ecr:CompleteLayerUpload",
                "ecr:PutImage"
            ],
            "Resource": "*"
        }
    ]
}

Workflow: https://github.com/crazy-max/test-docker-action/blob/89fa31b4a81e9ac5458494ae6efe3e1314d0d0bc/.github/workflows/ecr.yml

name: ecr

on:
  push:

jobs:
  build:
    runs-on: ubuntu-latest
    steps:
      -
        name: Checkout
        uses: actions/checkout@v2.3.1
      -
        name: Set up QEMU
        uses: docker/setup-qemu-action@master
        with:
          platforms: all
      -
        name: Set up Docker Buildx
        uses: docker/setup-buildx-action@master
      -
        name: Available platforms
        run: echo ${{ steps.buildx.outputs.platforms }}
      -
        name: Login to ECR
        uses: docker/login-action@v1
        with:
          registry: ${{ secrets.AWS_ACCOUNT_NUMBER }}.dkr.ecr.${{ secrets.AWS_REGION }}.amazonaws.com
          username: ${{ secrets.AWS_ACCESS_KEY_ID }}
          password: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
      -
        name: Build and push
        uses: docker/build-push-action@v2
        with:
          context: .
          file: ./Dockerfile
          push: true
          tags: |
            ${{ secrets.AWS_ACCOUNT_NUMBER }}.dkr.ecr.${{ secrets.AWS_REGION }}.amazonaws.com/test-docker-action:latest
            ${{ secrets.AWS_ACCOUNT_NUMBER }}.dkr.ecr.${{ secrets.AWS_REGION }}.amazonaws.com/test-docker-action:1.0.0

And result: https://github.com/crazy-max/test-docker-action/runs/1222130192?check_suite_focus=true#step:7:76

image

image

@michaelhelmick
Copy link
Author

I've added those:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "VisualEditor0",
            "Effect": "Allow",
            "Action": [
                "ecr:GetAuthorizationToken",
                "ecr:BatchCheckLayerAvailability",
                "ecr:GetDownloadUrlForLayer",
                "ecr:GetRepositoryPolicy",
                "ecr:DescribeRepositories",
                "ecr:ListImages",
                "ecr:DescribeImages",
                "ecr:BatchGetImage",
                "ecr:GetLifecyclePolicy",
                "ecr:GetLifecyclePolicyPreview",
                "ecr:ListTagsForResource",
                "ecr:DescribeImageScanFindings",
                "ecr:InitiateLayerUpload",
                "ecr:UploadLayerPart",
                "ecr:CompleteLayerUpload",
                "ecr:PutImage",
                "ecs:DiscoverPollEndpoint",
                "ecr:CreateRepository",
                "ecs:CreateCluster",
                "ecr:GetAuthorizationToken",
                "ecs:DeleteService",
                "ecs:DescribeTaskDefinition",
                "ecs:ListServices",
                "ecs:DeregisterTaskDefinition",
                "ecs:UpdateService",
                "iam:PassRole",
                "ecs:CreateService",
                "ecs:ListTaskDefinitionFamilies",
                "ecs:RegisterTaskDefinition",
                "ecs:DescribeServices",
                "ecs:ListTaskDefinitions",
                "ecs:ListClusters"
            ],
            "Resource": "*"
        },
        {
            "Sid": "VisualEditor1",
            "Effect": "Allow",
            "Action": "ecs:*",
            "Resource": [
                "arn:aws:ecs:*:*:task-definition/*:*",
                "arn:aws:ecs:*:*:task/*",
                "arn:aws:ecs:*:*:container-instance/*",
                "arn:aws:ecs:*:*:cluster/*"
            ]
        }
    ]
}

and am still getting:


1282
#28 exporting to image
1283
#28 exporting layers
1284
#28 exporting layers 55.3s done
1285
#28 exporting manifest sha256:462d0b3f95c0f99a56ab1d4d6242971c319aad1af57181fb1abab5456e3cca53 done
1286
#28 exporting config sha256:e68d3daf537a76b1dce9de9684c368a1e99a4aa6d15a98d16ea0abb73ee38586 done
1287
#28 pushing layers 0.1s done
1288
#28 ERROR: unexpected status: 401 Unauthorized
1289
------
1290
 > exporting to image:
1291
------
1292
failed to solve: rpc error: code = Unknown desc = unexpected status: 401 Unauthorized
1293
Error: The process '/usr/bin/docker' failed with exit code 1

:(

Do I need that QEMU step?

@michaelhelmick
Copy link
Author

Update: Even with QEMU, same error.

@crazy-max
Copy link
Member

crazy-max commented Oct 7, 2020

@michaelhelmick

Do I need that QEMU step?

Not required as your image is for the current platform (linux/amd64).

same error.

Can you temporarily try with my policy to make sure it's not an issue with the action please? Thanks.

@michaelhelmick
Copy link
Author

@crazy-max I added it anyways just in case and left it in there for now.

I replaced my entire policy with yours and still got the following.


#27 DONE 0.1s
1282

1283
#28 exporting to image
1284
#28 exporting layers
1285
#28 exporting layers 49.3s done
1286
#28 exporting manifest sha256:a79ab96c02d3d3f26a444699db544a1984c6fa335f07d83f17055a2021c56af8 done
1287
#28 exporting config sha256:c00e82b1af00bfa5aa055890ffd69df6eb515190030412ab21ad02a3c57fb4b7 done
1288
#28 pushing layers 0.1s done
1289
#28 ERROR: unexpected status: 401 Unauthorized
1290
------
1291
 > exporting to image:
1292
------
1293
failed to solve: rpc error: code = Unknown desc = unexpected status: 401 Unauthorized
1294
Error: The process '/usr/bin/docker' failed with exit code 1

Unsure if there's anything more verbose I can grab?

@crazy-max
Copy link
Member

@michaelhelmick

I replaced my entire policy with yours and still got the following.

Can you show me your entire workflow please?

Unsure if there's anything more verbose I can grab?

Follow the troubleshooting guide (buildkitd-flags: --debug and pushing with containerd) and let me know.

@michaelhelmick
Copy link
Author

@crazy-max

Just the deploy:

deploy:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v2

      - uses: actions/download-artifact@v2

      - name: Unzip
        run: unzip -o ./file.zip

      - uses: actions/cache@v2
        id: cache-pip
        with:
          path: ~/.cache/pip
          key: ${{ runner.os }}-pip-${{ hashFiles('./requirements/test.txt') }}
          restore-keys: |
              ${{ runner.os }}-pip-
      - name: Install Python Dependencies
        run: pip install -r ./requirements/test.txt

      - name: Static
        run: make github-static

      - name: Set Staging Environment Variables
        uses: allenevans/set-env@v1.0.0
        with:
          AWS_ACCESS_KEY_ID: ${{ secrets.STAGING_AWS_ACCESS_KEY_ID }}
          AWS_SECRET_ACCESS_KEY: ${{ secrets.STAGING_AWS_SECRET_ACCESS_KEY }}
        if: |
          github.event_name == 'pull_request'

      - name: Configure AWS credentials
        uses: aws-actions/configure-aws-credentials@v1
        with:
          aws-access-key-id: ${{ env.AWS_ACCESS_KEY_ID }}
          aws-secret-access-key: ${{ env.AWS_SECRET_ACCESS_KEY }}
          aws-region: nn-nnnn-n

      - name: Upload to S3
        shell: bash
        run: aws s3 sync dir s3://dir

      - name: Login to ECR
        uses: docker/login-action@v1
        with:
          registry: 00000000000.dkr.ecr.nn-nnnn-n.amazonaws.com
          username: ${{ env.AWS_ACCESS_KEY_ID }}
          password: ${{ env.AWS_SECRET_ACCESS_KEY }}

      - name: Create Sentry Release
        env:
          SENTRY_ORG: org
          SENTRY_AUTH_TOKEN: ${{ secrets.SENTRY_AUTH_TOKEN }}
        run: |
          curl -sL https://sentry.io/get-cli/ | bash
          ...

      - name: Set up QEMU
        uses: docker/setup-qemu-action@master
        with:
          platforms: all

      - name: Set up Docker Buildx
        uses: docker/setup-buildx-action@v1
        with:
          driver-opts: image=moby/buildkit:master

      - name: Cache Docker layers
        uses: actions/cache@v2
        with:
          path: /tmp/.buildx-cache
          key: ${{ runner.os }}-buildx-${{ github.sha }}
          restore-keys: |
            ${{ runner.os }}-buildx-
            
      - name: Build & Push image
        uses: docker/build-push-action@v2
        env:
          DOCKER_BUILDKIT: 1
          ECR_REGISTRY: ${{ steps.login-ecr.outputs.registry }}
          ECR_REPOSITORY: repo
        with:
          context: .
          file: ./Dockerfile
          push: true
          cache-from: type=local,src=/tmp/.buildx-cache
          cache-to: type=local,dest=/tmp/.buildx-cache
          tags: |
            0000000000.dkr.ecr.nn-nnnn-n.amazonaws.com/repo:${{ github.sha }}
            0000000000.dkr.ecr.nn-nnnn-n.amazonaws.com/repo:latest
      
      - name: Deploy > Web
        run: ecs service update
        
      - name: Logout of Amazon ECR
        if: always()
        run: docker logout ${{ steps.login-ecr.outputs.registry }}

Will set flags in a bit

@michaelhelmick
Copy link
Author

michaelhelmick commented Oct 8, 2020

Could ${{ github.sha }} be an issue?

Edit: Editing to 1.0.0 didn't help.

@crazy-max
Copy link
Member

@michaelhelmick You have mixed up authentication methods aws-actions/configure-aws-credentials@v1 and docker/login-action@v1. This could interfer with Docker authentication and I think that's the issue here. As explained in aws-actions/configure-aws-credentials#73 you have to create two separated jobs (one to push to s3 and another to push the docker image). If you need artifacts of the first job, you can pass data between jobs in a workflow.

      env:
          DOCKER_BUILDKIT: 1
          ECR_REGISTRY: ${{ steps.login-ecr.outputs.registry }}
          ECR_REPOSITORY: repo

DOCKER_BUILDKIT will not be used here as this action already uses buildx as default builder. You can also remove ECR_REGISTRY and ECR_REPOSITORY. This will not be used at all by the action.

     - name: Logout of Amazon ECR
        if: always()
        run: docker logout ${{ steps.login-ecr.outputs.registry }}

Remove this step, logout is already triggered by docker/login-action@v1. See https://github.com/docker/login-action#inputs

I am closing this issue because it seems that it does not come from this action as I demonstrated above but feel free to leave a message here when you have applied the pre-requisites suggested by AWS.

@michaelhelmick
Copy link
Author

FWIW, I was pushing to the wrong registry (my account number was for a different environment). Sorry, for all the trouble!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants