Uploaded image for project: 'Jenkins'
  1. Jenkins
  2. JENKINS-48050

Replace Declarative Docker agent directive with new implementation

    • Declarative - 1.2, Pipeline - December, Pipeline - April 2018

      Goals

      • We want to have a new implementation for running steps inside a Docker container that is transparent to the Pipeline author
      • We want to ensure that as this developed that we start making changes that allow us to swap out the implementation in the future (e.g. docker, k8, etc)
      • We want customers to try this new implementation without having to use patched plugins or special builds from a branch

      Scope

      • Declarative Docker agent directive can be used to run steps for a stage or for the whole pipeline
      • The new implementation can be enabled by specifying Pipeline->Options->dockerPipelineVersion = 2
      • Must be able to use an off the shelf docker container without modifying it so it works with Jenkins
      • Honour the entry point of the container
      • Sharing the workspace from the top level agent to a per stage Docker agent (and back again!)

      Out of scope

      • Declarative Docker agent directive that specifies a Dockerfile
      • Scripted docker.inside
      • Scripted docker.build
      • Building containers
      • Linked containers
      • Caching directories

      Acceptance criteria
      The following steps should work using the new implementation (even if modifications are needed to these steps):

      • withMaven()
      • dir()
      • withCredentials

      The following functionality should work:

      • Tool installers
      • Config File Provider

      Examples
      Per stage

      pipeline {
        options {
          dockerPipelineVersion(2)
        }
        agent none // Will not reuse workspace
        stages {
           stage (‘build’) {
              agent { docker ‘maven3’ } 
              steps { 
      	   sh ‘mvn clean test’
              } 
           }
        }
      }
      

      Whole Pipeline

      pipeline {
        options {
          dockerPipelineVersion(2)
        }
        agent { docker ‘maven3’ } // will reuse workspace for all stages unless specified
        stages {
           stage (‘build’) {
              steps { 
      	   sh ‘mvn clean test’
              } 
           }
        }
      }
      

          [JENKINS-48050] Replace Declarative Docker agent directive with new implementation

          weakcamel this is uncertain so far, as this issue is more about balancing what we'd like to get and what is feasible . Typically

          • we'd like to be able to run arbitrary docker image but jenkins require a JVM for it's agent
          • we'd like to be able to share workspace between steps running in containers, but then the uid/gid issue will come back 
          • etc ... always with but xx at some point

          IMHO we need to define a fresh new pipeline approach for docker usage that would not try to hack docker container. Working on a proposal on this purpose

           

          Nicolas De Loof added a comment - weakcamel this is uncertain so far, as this issue is more about balancing what we'd like to get and what is feasible . Typically we'd like to be able to run arbitrary docker image but  jenkins require a JVM for it's agent we'd like to be able to share workspace between steps running in containers,  but then the uid/gid issue will come back  etc ... always with  but xx at some point IMHO we need to define a fresh new pipeline approach for docker usage that would not try to hack docker container. Working on a proposal on this purpose  

          Waldek M added a comment -

          ndeloof sure, I hear what you're saying. There's a lot of features Jenkins users take for granted (which they wouldn't like to use) and general design of agents stand in the way too.

          I've had a couple of discussions with my colleagues on the subject of sharing files between a host and a container and the bottom line was: the alternatives may be inconvenient (or complicated, or come  with performance trade-off), but using a simple volume mount just isn't clean and versatile enough and

          IMO the only clean way to transfer files back and forth is some sort of RPC (as nicolaw has suggested in JENKINS-47026), be it directly via SSH/SFTP/what have you or e.g. https://github.com/vieux/docker-volume-sshfs..] otherwise the design is always going to make assumptions on the image or Docker host setup. Just my £0.02.

          Waldek M added a comment - ndeloof sure, I hear what you're saying. There's a lot of features Jenkins users take for granted (which they wouldn't like to use) and general design of agents stand in the way too. I've had a couple of discussions with my colleagues on the subject of sharing files between a host and a container and the bottom line was: the alternatives may be inconvenient (or complicated, or come  with performance trade-off), but using a simple volume mount just isn't clean and versatile enough and IMO the only clean way to transfer files back and forth is some sort of RPC (as nicolaw has suggested in JENKINS-47026 ), be it directly via SSH/SFTP/what have you or e.g. https://github.com/vieux/docker-volume-sshfs. .] otherwise the design is  always going to make assumptions on the image or Docker host setup. Just my £0.02.

          weakcamel yes indeed, I'd prefer we enforce use of pipeline `squash` for file sharing, and get rid of the uid/gid ownership constraint

          Nicolas De Loof added a comment - weakcamel yes indeed, I'd prefer we enforce use of pipeline `squash` for file sharing, and get rid of the uid/gid ownership constraint

          Some update on this issue:

          we'd like to introduce some "version:2" in declarative pipeline so changing behaviour to this new agent design would be opt-in only and we wouldn't break existing pipelines.

          docker-plugin do support `dockerNode` pipeline DSL keyword to provision a full jenkins node within a pipeline. This sounds like a nice candidate for docker agent implementation in declarative, as we would then get a full agent to fully honour Jenkins APIs and expectations (wrappers, env, path, etc).

          A major issue to remain is the way docker.inside to let one access workspace from higher level agent. This introduce filesystem permission issues, so forced user to run in container. To get rid of this, safer option seems imho to not keep this behaviour for nested agents, and only support use of `stash` to share files between agents.

          Nicolas De Loof added a comment - Some update on this issue: we'd like to introduce some "version:2" in declarative pipeline so changing behaviour to this new agent design would be opt-in only and we wouldn't break existing pipelines. docker-plugin do support `dockerNode` pipeline DSL keyword to provision a full jenkins node within a pipeline. This sounds like a nice candidate for docker agent implementation in declarative, as we would then get a full agent to fully honour Jenkins APIs and expectations (wrappers, env, path, etc). A major issue to remain is the way docker.inside to let one access workspace from higher level agent. This introduce filesystem permission issues, so forced user to run in container. To get rid of this, safer option seems imho to not keep this behaviour for nested agents, and only support use of `stash` to share files between agents.

          Code changed in jenkins
          User: Nicolas De Loof
          Path:
          pom.xml
          src/main/groovy/io/jenkins/docker/pipeline/DockerAgentScript.groovy
          src/main/java/io/jenkins/docker/pipeline/DockerAgent.java
          src/main/java/io/jenkins/docker/pipeline/DockerAgentScript.groovy
          http://jenkins-ci.org/commit/docker-plugin/a8240b9a147153a9c2c772bcc8df4acdd8798d19
          Log:
          JENKINS-48050 declarative « container » agent

          Compare: https://github.com/jenkinsci/docker-plugin/compare/6acd9e848f61^...a8240b9a1471

          SCM/JIRA link daemon added a comment - Code changed in jenkins User: Nicolas De Loof Path: pom.xml src/main/groovy/io/jenkins/docker/pipeline/DockerAgentScript.groovy src/main/java/io/jenkins/docker/pipeline/DockerAgent.java src/main/java/io/jenkins/docker/pipeline/DockerAgentScript.groovy http://jenkins-ci.org/commit/docker-plugin/a8240b9a147153a9c2c772bcc8df4acdd8798d19 Log: JENKINS-48050 declarative « container » agent Compare: https://github.com/jenkinsci/docker-plugin/compare/6acd9e848f61 ^...a8240b9a1471

          Code changed in jenkins
          User: Nicolas De Loof
          Path:
          pom.xml
          src/main/groovy/io/jenkins/docker/pipeline/DockerAgentScript.groovy
          src/main/java/io/jenkins/docker/pipeline/DockerAgent.java
          http://jenkins-ci.org/commit/docker-plugin/65dce18da936fbeea34d89245595d085866dd725
          Log:
          JENKINS-48050 declarative « container » agent

          Signed-off-by: Nicolas De Loof <nicolas.deloof@gmail.com>

          SCM/JIRA link daemon added a comment - Code changed in jenkins User: Nicolas De Loof Path: pom.xml src/main/groovy/io/jenkins/docker/pipeline/DockerAgentScript.groovy src/main/java/io/jenkins/docker/pipeline/DockerAgent.java http://jenkins-ci.org/commit/docker-plugin/65dce18da936fbeea34d89245595d085866dd725 Log: JENKINS-48050 declarative « container » agent Signed-off-by: Nicolas De Loof <nicolas.deloof@gmail.com>

          Code changed in jenkins
          User: Nicolas De Loof
          Path:
          pom.xml
          src/main/groovy/io/jenkins/docker/pipeline/DockerAgentScript.groovy
          src/main/java/io/jenkins/docker/pipeline/DockerAgent.java
          http://jenkins-ci.org/commit/docker-plugin/2e2c79fc3aba672e6a19d812d47ac55b2c7a418b
          Log:
          JENKINS-48050 declarative « container » agent

          Signed-off-by: Nicolas De Loof <nicolas.deloof@gmail.com>

          SCM/JIRA link daemon added a comment - Code changed in jenkins User: Nicolas De Loof Path: pom.xml src/main/groovy/io/jenkins/docker/pipeline/DockerAgentScript.groovy src/main/java/io/jenkins/docker/pipeline/DockerAgent.java http://jenkins-ci.org/commit/docker-plugin/2e2c79fc3aba672e6a19d812d47ac55b2c7a418b Log: JENKINS-48050 declarative « container » agent Signed-off-by: Nicolas De Loof <nicolas.deloof@gmail.com>

          Code changed in jenkins
          User: Nicolas De Loof
          Path:
          pom.xml
          src/main/groovy/io/jenkins/docker/pipeline/DockerAgentScript.groovy
          src/main/java/io/jenkins/docker/pipeline/DockerAgent.java
          http://jenkins-ci.org/commit/docker-plugin/3cea7e1a5c49d069be4aeea1b027210101ce4bac
          Log:
          JENKINS-48050 declarative « container » agent

          Signed-off-by: Nicolas De Loof <nicolas.deloof@gmail.com>

          SCM/JIRA link daemon added a comment - Code changed in jenkins User: Nicolas De Loof Path: pom.xml src/main/groovy/io/jenkins/docker/pipeline/DockerAgentScript.groovy src/main/java/io/jenkins/docker/pipeline/DockerAgent.java http://jenkins-ci.org/commit/docker-plugin/3cea7e1a5c49d069be4aeea1b027210101ce4bac Log: JENKINS-48050 declarative « container » agent Signed-off-by: Nicolas De Loof <nicolas.deloof@gmail.com>

          Jesse Glick added a comment -

          Alternate simpler approach: docker PR 681

          Jesse Glick added a comment - Alternate simpler approach: docker PR 681

          Liam Newman added a comment -

          Liam Newman added a comment - I've added a link to some work done for this https://github.com/jenkinsci/pipeline-model-definition-plugin/pull/255

            Unassigned Unassigned
            jamesdumay James Dumay
            Votes:
            14 Vote for this issue
            Watchers:
            41 Start watching this issue

              Created:
              Updated: