Successfully reported this slideshow.
We use your LinkedIn profile and activity data to personalize ads and to show you more relevant ads. You can change your ad preferences anytime.

Jenkinsfile: friend or foe for GR8conf 2017

401 views

Published on

Jenkins core is undergoing huge product and user experience refactoring. By introducing pipeline-as-code, that is based on Groovy, Jenkins team and community is moving towards having continuous delivery pipelines as first-class citizens inside Jenkins. This transformation is not going as smooth as it could, but it is going forward. The author will try to show some common pitfalls, shortcuts, and tricks for defining your pipelines with the help of Groovy as well as how to write your own pipeline step libraries.

Published in: Technology
  • Be the first to comment

  • Be the first to like this

Jenkinsfile: friend or foe for GR8conf 2017

  1. 1. 01
  2. 2. 02
  3. 3. Let's start! 03
  4. 4. History lesson 04
  5. 5. A bit of history: Hudson Work started in the summer of 2004 at Sun by Kohsuke Kawaguchi. First release: February 2005. In May, 2008, Hudson won the Duke's Choice Award in the Developer Solutions category. In 2010, Sun is acquired by Oracle... discussions, negotiations. Kohsuke Kawaguchi leaves Oracle. • • • • • 05
  6. 6. A bit of history: Jenkins In 2010, majority of Hudson's community votes for forking and name changing. Initial release of Jenkins: 2nd of February, 2011. Oracle still supports and develops Hudson. Around 2010­2011, CloudBees is created and declared Jenkins as its backbone product. • • • • 06
  7. 7. Pipelines in Jenkins 07
  8. 8. Steps 08
  9. 9. Steps 09
  10. 10. Job DSL job(jobName) {   scm {     git("git://github.com/project.git", branchName)   }   steps {     maven("clean test")     maven("install")   } } 01. 02. 03. 04. 05. 06. 07. 08. 09. 10
  11. 11. Gradle + Job DSL 11
  12. 12. Gradle + Job DSL 12
  13. 13. Build flow 13
  14. 14. Build flow 14
  15. 15. Build flow 15
  16. 16. Build flow 16
  17. 17. Build flow 17
  18. 18. Build flow 18
  19. 19. Groovy Postbuild 19
  20. 20. Groovy Postbuild 20
  21. 21. Groovy Postbuild 21
  22. 22. It still works, but... 22
  23. 23. Future ahead! 23
  24. 24. Pipeline­as­ code 24
  25. 25. Jenkinsfile node {   stage('build') {   }   stage('test') {   }   stage('deploy') {   } } 01. 02. 03. 04. 05. 06. 07. 08. 25
  26. 26. Jenkinsfile pipeline {   agent any   stages {     ...   } } 01. 02. 03. 04. 05. 06. 26
  27. 27. Stage view 27
  28. 28. New job types 28
  29. 29. Folder types 29
  30. 30. Pipeline script aka Jenkinfile 30
  31. 31. Questions in 2016 Why not Job DSL? Why not extending Build Flow? Why no integration with existing plug­ins? Why? Why? Why? • • • • 31
  32. 32. Problems in 2016 No good documentation No easy to use examples and tutorials User interface is, well,... puzzling! Missing functionality and unstable DSL/API Lack of plugins and integrations • • • • • 32
  33. 33. BUT... 33
  34. 34. It's improving! 34
  35. 35. Updated documentation 35
  36. 36. Snippet generator 36
  37. 37. Snippet generator 37
  38. 38. DSL examples 38
  39. 39. DSL: read/write files writeFile file: "output/usefulfile.txt",            text: "This file is useful, need to archive it." ... String content = readFile file: "output/usefulfile.txt" 01. 02. 03. 04. 39
  40. 40. DSL: archive archiveArtifacts artifacts: 'output/*.txt',                   excludes: 'output/*.md' archiveArtifacts allowEmptyArchive: true,                   artifacts: "**/build/libs/*.jar",                   fingerprint: true 01. 02. 03. 04. 05. 40
  41. 41. DSL: current directory node {   stage('report') {     dir('tmp') {       sh "mkdir ‐p output"     }     ...   } 01. 02. 03. 04. 05. 06. 07. 41
  42. 42. DSL: withEnv withEnv(['MYTOOL_HOME=/usr/local/mytool']) {   sh '$MYTOOL_HOME/bin/start' } 01. 02. 03. 42
  43. 43. DSL: stashing stash name: "first‐stash", includes: "output/*" ... unstash "first‐stash"  01. 02. 03. 43
  44. 44. DSL: timestamps timestamps {   stage "First echo"   echo "Hey, look, I'm echoing with a timestamp!"   stage "Sleeping"   sleep 30   stage "Second echo"   echo "Wonder what time it is now?" } 01. 02. 03. 04. 05. 06. 07. 08. 44
  45. 45. DSL: junit stage('test') {   try {     sh './gradlew test'   } finally {     junit allowEmptyResults: true,            keepLongStdio: true,            testResults: '**/build/test‐results/**/*.xml'   }     } 01. 02. 03. 04. 05. 06. 07. 08. 09. 45
  46. 46. DSL: listing changes for (def changeSetList : currentBuild.changeSets) {   for (def changeSet : changeSetList) {     println "Message: ${changeSet.comment}"     for (String path: changeSet.affectedPaths) {       println "Affected path: ${path}"     }   } } 01. 02. 03. 04. 05. 06. 07. 08. 46
  47. 47. DSL: control exceptions node { try {     ... } catch (e) {     currentBuild.result = "FAILURE"     throw e } finally {     ... }} 01. 02. 03. 04. 05. 06. 07. 08. 47
  48. 48. DSL: slack notify def buildStatus = currentBuild.result ?: "SUCCESS" def subject = "*build and deployment of testapi*n ${buildStatus}: def summary = "${subject} (https://jenkins/job/${env.JOB_NAME}/${e def color = currentBuild.result == "FAILURE" ? "#D24939" : "#3D732 slackSend(color: color, channel: '#backend', message: summary,            teamDomain: 'jenkins', token: '...') 01. 02. 03. 04. 05. 06. 48
  49. 49. DSL: build wrappers wrap([$class: 'AnsiColorBuildWrapper']) {     // Just some echoes to show the ANSI color.     stage "u001B[31mI'm Redu001B[0m Now not" } 01. 02. 03. 04. 49
  50. 50. DSL: docker docker.image('maven:3.3.3‐jdk‐8').inside {   git 'http://github.com/mysource.git'   sh 'mvn ‐B clean install' } 01. 02. 03. 04. 50
  51. 51. DSL: parallel parallel(   "test": {      sh './gradlew check'   },   "docs": {      sh './gradlew javadoc'   } ) 01. 02. 03. 04. 05. 06. 07. 08. 51
  52. 52. DSL: retry retry(2) {   // Yes, flakey tests are bad!   sh './gradlew test' } 01. 02. 03. 04. 52
  53. 53. Pitfalls Groovy is sandboxed during execution of Jenkinsfile Not all libraries can be used directly Not all plug­ins expose functionality usable in Jenkinsfile • • • 53
  54. 54. Pipeline libraries 54
  55. 55. Library structure 55
  56. 56. Levels Global library Folder library Jenkinsfile • • • 56
  57. 57. Use libraries @Library('somelib') import com.mycorp.pipeline.somelib.Helper int useSomeLib(Helper helper) {    helper.prepare()    return helper.count() } echo useSomeLib(new Helper('some text')) 01. 02. 03.04. 05. 06. 07. 08.09. 57
  58. 58. Use libraries @Library('github.com/fabric8io/' +           'fabric8‐pipeline‐library@master') gitTag {   releaseVersion = '0.0.1' } 01. 02. 03.04. 05. 06. 58
  59. 59. Blue ocean 59
  60. 60. Blue ocean Jenkins UI redesign effort Can be installed as a plugin to Jenkins 2.x Reached v1.0 in 2017 • • • 60
  61. 61. Install 61
  62. 62. Contributions 62
  63. 63. Dashboard 63
  64. 64. Pipeline view 64
  65. 65. Create pipeline 65
  66. 66. Edit pipeline 66
  67. 67. Save pipeline 67
  68. 68. Success screen 68
  69. 69. Failure screen 69
  70. 70. Conclusion 70
  71. 71. Take­aways Jenkins is still a friend! Jenkins is evolving and changing! It will take some time... Just be patient :)! • • • • 71
  72. 72. References https://jenkins.io/doc/book/pipeline/ https://jenkins.io/doc/pipeline/steps/ https://jenkins.io/doc/pipeline/examples/ • • • 72
  73. 73. That's all! 73
  74. 74. Thank you! 74
  75. 75. 75

×