如何在 jenkins docker 插件中引用已经 运行 docker 的容器?

How to reference an already running docker container in jenkins docker plugin?

我有一个使用 :

的 Jenkins 构建
stage("Build docker images and start containers") {
    steps {
        sh "docker-compose build "
        sh "docker-compose up -d"
    }
}

docker 组合文件有很多容器、网络和卷,通常很难维护和集成到 docker based pipeline.

另一方面,docker Jenkins 中的对象提供了一些不错的功能,我也想从中受益。

但无论我尝试什么,我都不可能在管道中创建一个引用已经 existing/running docker 容器的 docker 对象。 例如我试过(为了这个问题的最小例子):

node {
    checkout scm

    def runningContainer = docker.build("my-image:${env.BUILD_ID}")

    runningContainer.inside {
        sh 'make test'
    }
}

但在这种情况下,它会从头开始构建映像,然后 运行 执行命令。 我也试过:

node {
    checkout scm
    docker.image('mysql:5').withRun('-p 3306:3306') {
        /* do things */
    }
}

但在这种情况下也是一样的。图片是created/used 然后代码是运行.

有什么方法可以从现有的 docker 容器创建对象,例如:

node {
    checkout scm
    runningContainer = docker.reference('already_running_container_name')
    runningContainer.inside {
        sh 'make test'
    }
    
}

提前感谢您的帮助!

您可以在此处使用的两个工具是 docker.image().withRun() 可以采用任意额外的 docker run 选项,并且您可以 sh 'docker ...' 到 运行 任意命令来执行操作不支持标准 Jenkins Docker 集成。它还可以帮助您使用 Compose 创建具有可预测(或手动设置)名称的普通 Docker 对象。

相反,如果您从 docker.image().inside() { ... } 命令查看 Jenkins 日志,您可以看到它注入了 lot 设置;足够的绑定安装和环境变量,容器内的环境看起来或多或少像容器外的环境。我不会尝试在其他地方重现它,也不会尝试合并 Compose 和 Jenkins 容器设置。

实际上,我希望您从 Compose 中需要的大部分是它的 default 网络。您通常不需要挂载卷,因为 Jenkins 会挂载工作区目录。当您 运行 测试它时,可以忽略您从 Compose 获得的其他配置。

所以 Jenkinsfile 可能看起来像(脚本管道语法):

// Assign a unique (and known) Compose project name
def projectName = env.BUILD_TAG

try {
  // Start up the Compose stack
  sh "docker-compose -p ${projectName} up --build -d"
  // (Consider limiting to dependencies only, without --build)
  // sh "docker-compose -p ${projectName} up -d mysql redis"

  // Build an image out of the service we're testing
  def image = docker.build("my-image:${env.BUILD_ID}")

  // Run the integration tests, attached to the Compose-provided network
  // (This is the `docker run --network` option)
  image.inside("--network ${projectName}_default") {
    sh 'make test'
  }
} finally {
  // Tear down the Compose stack
  sh "docker-compose -p ${projectName} down"
}

原则上你可以 sh 'docker-compose exec ...',但你不会有任何 Jenkins-provided 卷安装,相应地你很难得到像 JUnit-format 测试报告这样的东西.