this post was submitted on 10 May 2024
96 points (94.4% liked)

Programmer Humor

19650 readers
2678 users here now

Welcome to Programmer Humor!

This is a place where you can post jokes, memes, humor, etc. related to programming!

For sharing awful code theres also Programming Horror.

Rules

founded 1 year ago
MODERATORS
 

I had to go full Rube Goldberg to clean up old image tags from closed PRs, while still leaving deletion of untagged image to the ECR repo's own lifecycle policy. Never go full Rube Goldberg:

name: ECR Retention Policy

on:
  pull_request:
    types:
      - closed
  workflow_call:
  workflow_dispatch:

jobs:
  clean-unused-ecr:
    name: Delete unused container images
    runs-on: runs-on,runner=2cpu-linux-x64,run-id=${{ github.run_id }},image=ecr_login_image
    steps:
      - name: Configure AWS credentials
        uses: aws-actions/configure-aws-credentials@v4
        with:
          aws-region: ${{ env.RUNS_ON_AWS_REGION }}
      - name: AWS ECR Login
        id: login-ecr
        uses: aws-actions/amazon-ecr-login@v2
      - name: AWS ECR Info
        shell: bash
        run: |
          echo "ECR_REGISTRY=${{ steps.login-ecr.outputs.registry }}" >> $GITHUB_ENV
          echo "ECR_REPO=$(basename ${{ github.repository }})" >> $GITHUB_ENV
      - name: Docker meta
        id: docker_meta
        uses: docker/metadata-action@v5
        with:
          images: ${{ env.ECR_REGISTRY }}/${{ env.ECR_REPO }}
          flavor: suffix=-
          tags: type=raw,value=${{ github.head_ref || github.ref_name }}
      # NOTE: This is convoluted because AWS ECR has no simple way to untag image without deletion
      # given we want to leave deletion of untagged image to the ECR repo's own lifecycle policy
      # https://stackoverflow.com/questions/70065254/remove-ecr-image-tag-despite-imagereferencedbymanifestlist-error
      # https://github.com/aws/containers-roadmap/issues/1567
      - name: AWS ECR Cleanup
        shell: bash
        run: |
          REPO_EXISTS=$(aws ecr describe-repositories --repository-names $ECR_REPO 2>&1 || true)
          if echo "${REPO_EXISTS}" | grep -q 'RepositoryNotFoundException'; then
            echo "Repository not found, skipping cleanup."
            exit 0
          fi
          IMAGE_TAGS=$(aws ecr list-images --repository-name $ECR_REPO --query 'imageIds[*].imageTag' --output text)

          docker pull busybox
          docker tag busybox $ECR_REGISTRY/$ECR_REPO:_
          docker push $ECR_REGISTRY/$ECR_REPO:_

          TEMP_IMAGE=$(
            aws ecr batch-get-image \
                --repository-name $ECR_REPO \
                --image-ids imageTag=_ )
          TEMP_MANIFEST=$(echo $TEMP_IMAGE | jq -r '.images[].imageManifest')
          TEMP_DIGEST=$(echo $TEMP_IMAGE | jq -r '.images[].imageId.imageDigest')

          TAG_PREFIX=$(echo ${{ fromJSON(steps.docker_meta.outputs.json).tags[0] }} | cut -d: -f2)
          for TAG in $IMAGE_TAGS
          do
            if [[ $TAG == $TAG_PREFIX* ]]; then
              docker tag busybox $ECR_REGISTRY/$ECR_REPO:$TAG
              docker push $ECR_REGISTRY/$ECR_REPO:$TAG
              echo "Untaged image $TAG"
            fi
          done

          # Delete the temporary image by digest
          aws ecr batch-delete-image \
            --repository-name $ECR_REPO \
            --image-ids imageDigest=$TEMP_DIGEST
you are viewing a single comment's thread
view the rest of the comments
[–] [email protected] 3 points 6 months ago (1 children)
[–] ruffsl 4 points 6 months ago (1 children)

Tagging an image is simply associating a string value to an image pushed to a container registry, as a human readable identifier. Unlike an image ID or image digest sha, an image tag is only loosely associated, and can be remapped later to another image in the same registry repo, e.g latest. Untagging is simply removing the tag from the registry, but not necessarily the associated image itself.

[–] [email protected] 1 points 6 months ago

So like tags in git, and deleting tags in git. Got it.