You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Shell脚本推送Docker镜像至GCR失败,但终端执行正常求排查

Docker镜像推送到GCR时权限验证失败(脚本执行出错,手动命令正常)

问题描述

我在通过Shell脚本将Docker镜像推送到Google Container Registry(GCR)时,持续收到以下错误:

unauthorized: You don't have the needed permissions to perform this operation, and you may have invalid credentials

但跳过WSL2直接在PowerShell中执行命令docker --debug push gcr.io/PROJECT_ID/IMAGE_NAME:latest时,镜像可以正常推送。奇怪的是,在同一个PowerShell窗口中运行该Shell脚本仍会触发上述错误。我已经按照GCR高级认证文档操作过,但问题依旧。

相关脚本代码如下:

#!/bin/bash

set -e
set -ex

# Define variables
PROJECT_ID="XXXXX"
IMAGE_NAME="XXXXX"
SERVICE_NAME="XXXXX"
REGION="XXXXX"

function load_env_vars() {
  local env_file="$1"
  local env_vars=""

  while IFS="=" read -r key value; do
    env_vars="${env_vars} --set-env-vars ${key}=${value}"
  done < "${env_file}"

  echo "${env_vars}"
}

# Authenticate to GCP
gcloud auth configure-docker

# Build the Docker image
docker build -t gcr.io/${PROJECT_ID}/${IMAGE_NAME} .

# Push the Docker image to Google Container Registry
docker --debug push gcr.io/${PROJECT_ID}/${IMAGE_NAME}:latest

# Load environment variables from .env file
env_vars=$(load_env_vars ".env")

# Deploy the image to Cloud Run
gcloud run deploy ${SERVICE_NAME} \
    --image gcr.io/${PROJECT_ID}/${IMAGE_NAME} \
    --region ${REGION} \
    --platform managed \
    --verbosity=debug \
    --allow-unauthenticated \
    ${env_vars}

可能的原因及解决方法

1. WSL2与PowerShell的Docker上下文不一致

PowerShell中的Docker可能连接的是Windows本地的Docker Desktop守护进程,而WSL2脚本中的Docker可能使用的是WSL2内部的守护进程,导致认证配置未同步。

  • 解决:在WSL2中执行docker context use default切换到与PowerShell一致的上下文;同时确保Docker Desktop已开启"Use the WSL 2 based engine",并勾选对应的WSL发行版。

2. gcloud auth configure-docker配置不完整

脚本中执行的认证命令可能未指定GCR域名,或者WSL2环境下的gcloud账号与PowerShell不一致。

  • 解决:在脚本中明确指定项目并重新配置Docker认证:
    gcloud config set project ${PROJECT_ID}
    gcloud auth configure-docker gcr.io --quiet
    
    同时执行gcloud auth list对比WSL2和PowerShell中的登录账号,确保一致。

3. 环境变量传递问题

PowerShell中的DOCKER_CONFIG环境变量未传递到WSL2脚本中,导致Docker读取的认证配置路径错误。

  • 解决:在脚本开头添加环境变量同步,替换为你的Windows用户目录路径:
    export DOCKER_CONFIG=/mnt/c/Users/你的用户名/.docker
    

4. set -e的隐性退出影响

脚本开启了set -e(出错即退出),可能gcloud auth configure-docker执行时存在隐性错误未被捕获,导致后续push失败。

  • 解决:暂时注释set -e,或给认证命令添加--quiet参数避免交互式提示:
    gcloud auth configure-docker --quiet
    

修改后的脚本参考

#!/bin/bash

set -x

# Define variables
PROJECT_ID="XXXXX"
IMAGE_NAME="XXXXX"
SERVICE_NAME="XXXXX"
REGION="XXXXX"

function load_env_vars() {
  local env_file="$1"
  local env_vars=""

  while IFS="=" read -r key value; do
    # 跳过空行和注释行
    [[ -z "$key" || "$key" =~ ^# ]] && continue
    env_vars="${env_vars} --set-env-vars ${key}=${value}"
  done < "${env_file}"

  echo "${env_vars}"
}

# 同步Windows Docker配置路径(替换为你的实际路径)
export DOCKER_CONFIG=/mnt/c/Users/你的用户名/.docker

# 配置GCP项目及Docker认证
gcloud config set project ${PROJECT_ID}
gcloud auth configure-docker gcr.io --quiet

# 构建镜像(添加版本标签)
docker build -t gcr.io/${PROJECT_ID}/${IMAGE_NAME}:latest .

# 推送镜像到GCR
docker --debug push gcr.io/${PROJECT_ID}/${IMAGE_NAME}:latest

# 加载.env环境变量
env_vars=$(load_env_vars ".env")

# 部署到Cloud Run
gcloud run deploy ${SERVICE_NAME} \
    --image gcr.io/${PROJECT_ID}/${IMAGE_NAME}:latest \
    --region ${REGION} \
    --platform managed \
    --verbosity=debug \
    --allow-unauthenticated \
    ${env_vars}

内容的提问来源于stack exchange,提问作者Victor Valar

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.22 06:10:21