[关闭]
@eric1989 2017-03-15T12:19:00.000000Z 字数 2840 阅读 912

jenkins,maven,docker 持续集成

1. 背景

在开发过程中,需要不间断进行集成测试。同时为了提高测试效率,需要将通过单元测试的版本打包成docker镜像以提供给测试部门。
同时,在集成测试的过程中。为了避免不同的测试项目对测试环境的并发竞争而导致测试失败,希望在单元测试阶段可以让不同的项目运行运行于各自的干净的测试环境中。而Jenkins的Master/Slave模型恰好可以满足这种需求。

2. 拓扑结构

首先我们看下Jenkins的Master/Slave的拓扑结构
mark
Master
执行任务调度。按照预先设定的规则将任务分发至指定的Slave节点。并收集执行结果用作展示以及后续的镜像打包流程等。
Slave
执行具体的集成任务。主要为编译,测试等较为消耗资源的任务。每个Slave都是一个Docker容器。并且一个Slave只与一个项目进行绑定。这样的好处在于该项目的编译和测试环境都是纯粹的。不会因为项目的并发干扰造成测试失败等问题。

3. 相关配置

作为一切开始的基础前提。首先应该有一个部署在物理主机上的Jenkins作为Master节点。因为需要执行Docker镜像打包这样的行为,所以必须得是物理主机。否则就要配置类似"Docker in Docker"的方式,而这并不是被推荐的实践。
配置Slave节点
首先的第一个环节就是配置Slave节点。在Jenkins中,进入到系统管理->管理节点->新建节点。进入如下页面mark
填写Slave节点名称点击确认。推荐使用"项目名称-Slave"的形式。
mark
在启动方法处选择Launch agent via Java Web Start.
此时回到管理节点界面,会看到刚才配置的节点。点击节点,进入具体信息。则可以得到用于通讯的jnlpUrl。到了这里,配置就算完成。
markmark
启动Slave节点
此时准备启动Slave节点。前面说到,Slave节点其实是一个Docker容器。该容器的镜像已经存放于公司的私有镜像仓库。拉取命令是docker pull 192.168.10.60:5002/jenkins-slave/jenkins-slave:latest.该镜像内置了jdk和maven环境。并且maven配置也指向了公司的私服地址。属于开箱即用的镜像。镜像的启动命令为docker run -d --name slave1 -e "JNLP_CRENDIENTIALS=jenkins用户名:密码" -e "JNLP_URL=上文得到的jnlpUrl" 192.168.10.60:5002/jenkins-slave/jenkins-slave:latest。由于该节点不需要对外提供服务,因此无需暴露端口。
当Slave节点启动后,回到Master节点的节点管理页面,可以看到Slave节点的状态已经正常,处于连接中。

4. 编写pipeline脚本

Jenkins2 带了pipeline流水线概念。通过pipeline脚本,几乎可以完成所有复杂的编译发布流程。但是pipeline脚本是groovy语言,有一定的上手门槛。有鉴于日常的维护性工作不多,实际上脚本的常用语句也很少。因此这边给出一个范本用于参考。

  1. //建立一个阶段
  2. stage('checkout and test')
  3. {
  4. //使用节点slave执行下面的操作
  5. node("slave")
  6. {
  7. //从git上获取数据,需要给出git的用户信息和url。其中用户信息在jenkins中配置完毕
  8. git(credentialsId: '52d0ccee-5512-4092-b14a-9ca1876737a2',url: 'git@192.168.10.60:platform/eventsource-ticketcenter.git', branch: 'master')
  9. //执行maven命令
  10. sh "mvn -f eventsource-ticketcenter-core/pom.xml clean package"
  11. //发布junit测试报告
  12. junit '**/target/surefire-reports/TEST-*.xml'
  13. //不同的阶段会使用不同的工作空间,无法共享数据。所以这里要暂存文件内容,为下阶段使用准备。
  14. stash includes: '**', name: 'collect'
  15. }
  16. }
  17. stage('publish jacoco')
  18. {
  19. node("master")
  20. {
  21. //还原暂存的文件内容
  22. unstash 'collect'
  23. //使用测试数据,发布Jacoco测试覆盖率报告
  24. step([$class: 'JacocoPublisher'])
  25. }
  26. }
  27. //进入创建阶段
  28. stage('build')
  29. {
  30. node("master")
  31. {
  32. git(credentialsId: '52d0ccee-5512-4092-b14a-9ca1876737a2',url: 'git@192.168.10.60:linbin/testjenkins.git', branch: 'master')
  33. //先进行maven编译,这里需要忽略测试以减少耗时。因为上面的阶段已经完成了测试
  34. sh "mvn clean install -Dmaven.test.skip=true"
  35. //从git上获得编写好的Dockerfile文件
  36. git(credentialsId: '52d0ccee-5512-4092-b14a-9ca1876737a2',url: 'git@192.168.10.60:linbin/dockertest.git', branch: 'master')
  37. //进行docker打包
  38. sh "docker build -t 192.168.10.60:5002/testdocker/test:latest ."
  39. //推送打包后的镜像到镜像仓库
  40. sh "docker push 192.168.10.60:5002/testdocker/test:latest"
  41. //推送完毕删除本地镜像副本,节省空间
  42. sh "docker rm 192.168.10.60:5002/testdocker/test:latest"
  43. }
  44. }
  45. }catch(err)
  46. {
  47. //如果执行阶段发生错误,则发出邮件通知对应管理人员
  48. node("master")
  49. {
  50. emailext body: 'Check console output at $BUILD_URL to view the results.', subject: '$PROJECT_NAME - Build # $BUILD_NUMBER - FAIL!', to: '495561397@qq.com'
  51. }
  52. return
  53. }
  54. //阶段执行完毕,发出通知邮件
  55. node("master")
  56. {
  57. emailext body: 'Check console output at $BUILD_URL to view the results.', subject: '$PROJECT_NAME - Build # $BUILD_NUMBER - SUCCESS!', to: '495561397@qq.com'
  58. }
添加新批注
在作者公开此批注前,只有你和作者可见。
回复批注