【问题标题】:Jenkins Pipeline Build with Docker, Google Registry, and Google Auth Plugin使用 Docker、Google Registry 和 Google Auth Plugin 构建 Jenkins Pipeline
【发布时间】:2023-07-14 11:47:02
【问题描述】:

我正在使用 Jenkins 管道(使用 JHipster 自动生成的管道脚本)构建 Docker 映像。我想将最终的 docker 镜像推送到 Google Container Registry。

这是我所做的:

  1. 我已经安装了 CloudBees Docker Custom Build Environment Plugin 和 Google Container Registry Auth Plugin。
  2. 我已经按照here 上的说明在 Jenkins 中设置了 Google 身份验证凭据
  3. 我已将构建步骤配置为使用 Google 注册表标记格式,如下所示:docker.build('us.gcr.io/[my-project-id]/[my-artifact-id]', 'target/docker')
  4. 我在推送步骤中引用了我的 Google Auth 凭据的 ID:

(嗯。在项目符号后需要额外的文本行才能正确格式化)

docker.withRegistry('https://us.gcr.io', '[my-credential-id]') {
    dockerImage.push 'latest'
}

但构建失败:

ERROR: Could not find credentials matching [my-credential-id] 
Finished: FAILURE

我基本上相信这些插件在管道世界中不起作用,但我想我想问问是否有人已经完成了这一点并可以给我一些指导。

【问题讨论】:

    标签: docker jenkins-pipeline google-container-registry


    【解决方案1】:

    尝试在您的凭据 ID 前加上“gcr:”。

    您的凭据 ID 看起来像“gcr:[my-credential-id]”。

    完整的工作示例:

    stage('Build image') {
      app = docker.build("[id-of-your-project-as-in-google-url]/[name-of-the-artifact]")
    }
    stage('Push image') {
      docker.withRegistry('https://eu.gcr.io', 'gcr:[credentials-id]') {
        app.push("${env.BUILD_NUMBER}")
        app.push("latest")
      }
    }
    

    请注意图片的名称。即使使用有效的凭据,我也一直在努力推动图像,直到我用 [id-of-your-project-as-in-google-url]/[name-of-the-artifact] 表示法命名图像。

    当您收到需要启用 Google....... API 的消息时,您的 [id-of-your-project-as-in-google-url] 可能有误。

    图像现在可以与 eu.gcr.io/[id-of-your-project-as-in-google-url]/[name-of-the-artifact]:47 的 url 一起成功使用。

    LZ

    【讨论】:

    • 这当然有帮助。我不再收到“找不到凭据”错误,但我遇到了 unauthorized: Not Authorized 错误。谢谢指点!
    • 在我写完该评论后不久,我尝试清除我的 .docker/config.json 中的所有内容,这似乎有所帮助。
    • 写完我的回复几个小时后,我最终找到了可行的解决方案。我已经更新了答案以反映解决方案。
    • 在构建阶段,我使用三部分名称:“us.gcr.io/[project-name]/[artifact-name]”。但是,如果两部分名称对您有用,那就太好了!
    • @u-phoria:gcr: 前缀假定您在 Jenkins 服务器中安装了 Google Container Registry Auth 插件。
    【解决方案2】:

    以前的答案似乎不再适合我了。这是适合我的语法:

    stage('Push Image') {
            steps {
                script {
                    docker.withRegistry('https://gcr.io', 'gcr:my-credential-id') {
                        dockerImage.push()
                    }
                }
            }
        }
    

    【讨论】:

      【解决方案3】:

      设置谷歌云注册表的其他方式可以如下,您使用 withCredentials 插件并使用文件凭据类型。

      withCredentials([file(credentialsId: 'gcr-private-repo-reader', variable: 'GC_KEY')]){
                      sh '''
                          chmod 600 $GC_KEY
                          cat $GC_KEY | docker login -u _json_key --password-stdin https://eu.gcr.io
      
                          docker ps
                          docker pull eu.gcr.io/<reponame>/<image>
                      '''
                      }
      

      【讨论】:

        【解决方案4】:

        检查您是否安装了https://plugins.jenkins.io/google-container-registry-auth/ 插件。

        插件安装后使用gcr:credential-id synthax

        【讨论】:

          【解决方案5】:

          以下答案以前没有完全有效,现在显然已弃用。出于历史原因,我将文本留在这里。

          我最终绕过了这个问题,使用 gcloud 脚本阶段代替了 docker 管道阶段,如下所示:

          stage('publish gcloud') {
              sh "gcloud docker -- push us.gcr.io/[my-project-id]/[my-artifact-id]"
          }
          

          gcloud 命令能够找到在 Jenkins 服务器的命令行上使用 gcloud init 设置的身份验证凭据。

          【讨论】:

          • 我已经看到 gcloud 命令返回“未授权”一连串。也许授权超时?
          • 是的,gcloud 命令会很快丢失其授权信息。这不是一个可行的持续解决方案。
          • This question 建议了另一种方法。
          • 现在在较新的 gcloud 中已弃用。