如何在GitHub Actions中实现Docker镜像语义化版本并推送至AWS ECR
GitHub Actions + AWS ECR 语义化版本管理工作流示例
下面是一套完整的工作流配置,实现你要的语义化版本管理逻辑:每次推送代码时,自动递增补丁版本号,新镜像打vX.Y.Z-latest标签,同时把上一个带latest标签的镜像重新标记为纯版本号(比如v0.0.1)。
完整工作流代码
name: ECR 镜像语义化构建推送 on: push: branches: [ main ] # 触发分支可根据你的需求修改 jobs: build-and-push: runs-on: ubuntu-latest permissions: id-token: write contents: read steps: - name: 检出代码 uses: actions/checkout@v4 - name: 配置AWS凭证 uses: aws-actions/configure-aws-credentials@v4 with: role-to-assume: arn:aws:iam::你的AWS账号ID:role/你的ECR访问角色 aws-region: 你的AWS区域(比如cn-north-1) - name: 获取ECR仓库登录信息 id: ecr-login run: | aws ecr get-login-password --region ${{ steps.configure-aws-credentials.outputs.region }} | docker login --username AWS --password-stdin 你的AWS账号ID.dkr.ecr.你的AWS区域.amazonaws.com - name: 获取当前latest版本号 id: get-version run: | # 尝试从ECR获取带latest标签的镜像版本 LATEST_TAG=$(aws ecr describe-images --repository-name 你的ECR仓库名 --filter "tagStatus=TAGGED" --query 'sort_by(imageDetails,& imagePushedAt)[-1].imageTags[?contains(@, `latest`) == `true`]' --output text) # 处理初始版本(如果没有任何镜像) if [ -z "$LATEST_TAG" ]; then echo "current_version=v0.0.1" >> $GITHUB_OUTPUT echo "new_version=v0.0.1" >> $GITHUB_OUTPUT else # 提取版本号部分(去掉-latest) CURRENT_VERSION=${LATEST_TAG%-latest} echo "current_version=$CURRENT_VERSION" >> $GITHUB_OUTPUT # 递增补丁号 # 拆分版本号为数组 IFS='.' read -r -a VERSION_PARTS <<< "${CURRENT_VERSION#v}" MAJOR=${VERSION_PARTS[0]} MINOR=${VERSION_PARTS[1]} PATCH=$((VERSION_PARTS[2] + 1)) NEW_VERSION="v$MAJOR.$MINOR.$PATCH" echo "new_version=$NEW_VERSION" >> $GITHUB_OUTPUT fi - name: 重新标记旧latest镜像为纯版本号(如果存在) if: steps.get-version.outputs.current_version != steps.get-version.outputs.new_version run: | # 获取旧latest镜像的imageDigest OLD_DIGEST=$(aws ecr describe-images --repository-name 你的ECR仓库名 --image-ids imageTag=${{ steps.get-version.outputs.current_version }}-latest --query 'imageDetails[0].imageDigest' --output text) # 移除旧的纯版本标签(如果存在) aws ecr batch-delete-image --repository-name 你的ECR仓库名 --image-ids imageTag=${{ steps.get-version.outputs.current_version }} || true # 添加纯版本标签到旧镜像 aws ecr put-image --repository-name 你的ECR仓库名 --image-tag ${{ steps.get-version.outputs.current_version }} --image-digest $OLD_DIGEST - name: 构建Docker镜像 run: | docker build -t 你的AWS账号ID.dkr.ecr.你的AWS区域.amazonaws.com/你的ECR仓库名:${{ steps.get-version.outputs.new_version }}-latest . - name: 推送新镜像到ECR run: | docker push 你的AWS账号ID.dkr.ecr.你的AWS区域.amazonaws.com/你的ECR仓库名:${{ steps.get-version.outputs.new_version }}-latest
关键步骤说明
- 版本号计算逻辑:通过AWS CLI查询ECR中最新的
-latest标签镜像,提取版本号后自动递增补丁位;如果是第一次构建,直接使用v0.0.1-latest。 - 旧标签重标记:先获取旧
latest镜像的摘要(Digest),然后给它打上不带latest的纯版本标签,同时删除可能存在的旧纯版本标签(避免冲突)。 - AWS权限配置:确保你使用的IAM角色拥有
ecr:DescribeImages、ecr:BatchDeleteImage、ecr:PutImage、ecr:GetAuthorizationToken等权限。
注意事项
- 替换代码中所有占位符:比如
你的AWS账号ID、你的ECR仓库名、你的AWS区域、你的ECR访问角色ARN。 - 如果需要递增主版本或次版本,可以修改版本拆分后的逻辑(比如触发条件改成打特定tag时递增MAJOR/MINOR)。
- 测试时可以先手动推送一个初始镜像
v0.0.1-latest到ECR,再触发工作流验证版本递增和标签重标记逻辑。
内容的提问来源于stack exchange,提问作者Math
相关产品推荐
相关产品推荐

