本地及GitHub Action可构建Docker镜像,Google Cloud Build失败
问题
我有一个Golang项目,尝试部署至Google Cloud Run。本地及GitHub Action环境下构建Docker镜像均正常,但推送代码至Cloud Run时部署失败。Cloud Build历史报错如下:
Removing intermediate container d76fa08a24bd ---> 264891a391d2 Step 7/10 : RUN go run github.com/99designs/gqlgen generate ---> Running in 7282b9df5a6c unable to open schema: open schema.graphql: no such file or directory exit status 1 The command '/bin/sh -c go run github.com/99designs/gqlgen generate' returned a non-zero code: 1 ERROR ERROR: build step 0 "gcr.io/cloud-builders/docker" failed: step exited with non-zero status: 1
用ls -R确认该文件确实存在,且我并未配置任何cloudbuild.yaml,疑惑为何本地和GitHub Action能正常构建,Cloud Build却不行?
我的Dockerfile
# syntax=docker/dockerfile:1 FROM golang:1.20-alpine WORKDIR /app # Copy only the go mod and sum files to leverage Docker cache COPY go.mod go.sum ./ # Download dependencies RUN go mod download # Copy the rest of the application COPY . ./ #RUN ls -R #for showing if everything is copied correclty. # Generate code. ===HERE IS WHERE IT FAILS ON CLOUD BUILD=== RUN go run github.com/99designs/gqlgen generate # Build the application RUN CGO_ENABLED=0 GOOS=linux go build -o /wonder EXPOSE 8080 CMD [ "/wonder" ]
GitHub Action配置
name: Docker Build Test on: #workflow_dispatch: push: branches: - main env: PROJECT_ID: my-project SERVICE: wonder REGION: europe-west1 jobs: build: name: Test Docker Build runs-on: ubuntu-latest permissions: contents: 'read' id-token: 'write' steps: - name: Checkout repository uses: 'actions/checkout@v4' - id: 'auth' name: 'Authenticate to GCP' uses: 'google-github-actions/auth@v2' with: create_credentials_file: 'true' workload_identity_provider: 'projects/987654321/locations/global/workloadIdentityPools/action-pool/providers/action-oidc' service_account: 'wonder-g-diployer@my-project.iam.gserviceaccount.com' - name: Test Docker build working-directory: ./server run: | docker-compose up -d docker build -t wonder . docker run -d \ -e "DB_HOST=localhost" \ -e "DB_PORT=5434" \ -e "DB_NAME=wonder" \ -e "DB_PASSWORD=password" \ --net=host \ wonder - name: Check if server is running run: | sleep 10 # Wait for the server to start (you can adjust this if needed) if curl -sSf "http://localhost:8080/status" > /dev/null; then echo "Server is running." exit 0 else echo "Server is not running or endpoint is not accessible." exit 1 fi - name: Deploy to Cloud Run id: deploy uses: 'google-github-actions/deploy-cloudrun@v2' with: service: ${{ env.SERVICE }} region: ${{ env.REGION }} source: ./server/ # If required, use the Cloud Run url output in later steps - name: Show Output run: echo ${{ steps.deploy.outputs.url }}
原因分析与解决方案
核心原因
本地和GitHub Action能正常构建,是因为构建上下文为server子目录:
- GitHub Action里
docker build是在working-directory: ./server下执行的,COPY . ./会复制server目录下的所有文件(包括schema.graphql)到镜像的/app目录。 - 而直接推送代码触发Cloud Run部署时,Cloud Build默认使用仓库根目录作为构建上下文,
COPY . ./复制的是根目录内容,schema.graphql不在根目录,因此镜像里找不到该文件。
解决方案
方案1:调整Cloud Run的构建上下文路径
如果是直接推送代码触发Cloud Run部署:
- 打开Cloud Run服务详情页,进入「编辑 & 部署新修订版」
- 在「构建」区域,选择你的代码仓库后,指定「目录」为
server - 保存并重新部署
方案2:修改Dockerfile适配根目录上下文
如果希望Dockerfile在根目录上下文也能正常工作,修改COPY指令的源路径:
# 替换原有的COPY . ./ COPY server/ ./
方案3:优化GitHub Action的部署配置
如果是通过GitHub Action部署失败,确保部署时明确指定Dockerfile路径,避免上下文混淆:
- name: Deploy to Cloud Run id: deploy uses: 'google-github-actions/deploy-cloudrun@v2' with: service: ${{ env.SERVICE }} region: ${{ env.REGION }} source: ./server/ dockerfile: ./server/Dockerfile
排查辅助步骤
可以临时在Dockerfile中添加RUN ls -R指令,查看镜像内/app目录的文件结构,确认schema.graphql是否被正确复制:
COPY . ./ RUN ls -R # 临时添加,排查后可删除
内容的提问来源于stack exchange,提问作者Kateile
相关产品推荐
相关产品推荐

