资讯详情

资讯详情

【基于 Jenkins Pipeline 的容器化 CI/CD 流水线设计与实现】

提示本文原创作品良心制作干货为主简洁清晰一看就会文章目录前言一、pipeline介绍1.1 pipeline是什么1.2 pipeline语法1.3 插件下载二、基于 GitLabWebhookJenkinsHarbor 的容器化 CI/CD 流水线搭建页面定义 Pipeline2.1 环境介绍2.2 编写 Pipeline 流水线代码2.3 配置 Git 参数化构建2.4 配置 Webhook 触发器2.5 执行流水线项目三、基于 Jenkinsfile 的 Pipeline 流水线实现3.1 编写 Jenkinsfile 文件3.2 推送项目代码至远程仓库3.3 Jenkins Web 页面任务配置3.4 运行并验证流水线前言随着 DevOps 理念持续落地CI/CD 流水线能够自动化完成代码拉取、镜像构建、仓库推送与应用部署有效提升项目迭代效率。Jenkins Pipeline 作为流水线即代码的实现方式提供两种配置方案一是在 Jenkins 网页端直接编写流水线脚本二是使用 Jenkinsfile 将流水线定义随项目代码一同托管。本文以 GitLab、Jenkins、Harbor 为核心工具搭建容器化 CI/CD 流水线分别实现网页定义 Pipeline 与 Jenkinsfile 流水线两种方案对比两种实现方式的配置流程完成参数化构建、Webhook 自动触发等功能验证流水线自动构建、部署与版本回滚能力一、pipeline介绍1.1 pipeline是什么Jenkins Pipeline 是基于 Groovy 语言实现的持续流水线通过 Jenkinsfile 将拉取代码、构建、打包、镜像推送、应用部署等 CI/CD 流程代码化支持版本管理与阶段化执行相比自由风格项目Pipeline 将 CI/CD 流程代码化可纳入版本管理可读性、可复用性更强1.2 pipeline语法分为脚本式Scripted和声明式Declarative# 脚本式结构不常用node{...}# 声明式结构流行款pipeline{...}声明式核心pipeline为根包含全局配置stages存放多个stage阶段steps写执行命令post为后置处理具体结构如下1.3 插件下载这里需要下载三个插件pipeline我之前下过、pipeline stage view、blue ocean二、基于 GitLabWebhookJenkinsHarbor 的容器化 CI/CD 流水线搭建页面定义 Pipeline2.1 环境介绍主机名IP地址运行服务作用gitlab192.168.13.136GitLab托管 Git 仓库为 developer 提供推送为 Jenkins 提供源码developer192.168.13.144Git、Maven、JDK 17模拟开发者编写代码并推送到 GitLabjenkins192.168.13.143DockerDocker-Compose Jenkins容器UI 8080版本2.516.2拉代码、构建镜像、推送 Harbor、SSH 部署到 backendharbor192.168.13.138HarborHTTP 80项目 myapptest私有镜像仓库存储/分发镜像backend1192.168.13.139Docker拉取镜像运行 myapp 容器80→8080对外提供服务backend2192.168.13.140Docker拉取镜像运行 myapp 容器80→8080对外提供服务自由风格项目https://blog.csdn.net/m0_63756214/article/details/167388905在上文中我创建了一个自由风格的项目来实现jenkins CI/CD现在我打算把自由风格转化成pipeline首先根据指定参数默认main分支从 GitLab 拉取源码接着利用代码库中的多阶段 Dockerfile 构建 Docker 镜像并登录 Harbor 私有仓库分别推送带有构建号Tag和latest标签的镜像随后通过 SSH 插件并行将新镜像部署到 backend1 和 backend2 两台后端服务器上执行拉取最新镜像、销毁旧容器、启动新容器宿主机 80 端口映射容器 8080 端口以及清理悬空镜像的操作最后无论流水线是成功、失败还是被手动取消都会通过curl调用企业微信机器人的 Webhook 地址发送包含任务名、构建编号、目标分支、构建状态及耗时的 Markdown 格式通知2.2 编写 Pipeline 流水线代码这里我创建了一个项目“pipeline-integrated”pipeline{agent any environment{// Harbor 配置 HARBOR_ADDR 192.168.13.138:80 PROJECT_NAME myapptest APP_NAME pipeline-integrated IMAGE ${HARBOR_ADDR}/${PROJECT_NAME}/${APP_NAME} // GitLab 配置 GIT_URL http://192.168.13.136/root/myapp.git GIT_CRED_ID gitlab-http}stages{stage(拉取源码){steps{script{// 注意这里使用的是 params.tag请确保你 Jenkins 的参数名是 tagdef targetBranch params.tag?.trim() ? params.tag.trim():mainecho 准备拉取分支/提交:${targetBranch} checkout([$class:GitSCM,branches:[[name:targetBranch]],userRemoteConfigs:[[url:${env.GIT_URL},credentialsId:${env.GIT_CRED_ID}]]])}sh git log-1--oneline}}stage(构建与推送镜像){steps{withCredentials([usernamePassword(credentialsId:harbor-cred,usernameVariable:HARBOR_USER,passwordVariable:HARBOR_PASS)]){sh set-e echo 1. 登录 Harbor echo $HARBOR_PASS|docker login $HARBOR_ADDR-u $HARBOR_USER--password-stdin echo 2. 构建镜像 (利用多阶段 Dockerfile) docker build-t $IMAGE:$BUILD_NUMBER-f Dockerfile . echo 3. 推送镜像 docker push $IMAGE:$BUILD_NUMBER echo 4. 同时打 latest 标签并推送 docker tag $IMAGE:$BUILD_NUMBER $IMAGE:latest docker push $IMAGE:latest echo 5. 登出 Harbor docker logout $HARBOR_ADDRecho 构建并推送完成:$IMAGE:$BUILD_NUMBER }}}stage(并行部署到后端){parallel{stage(部署 backend1){steps{sshPublisher(publishers:[sshPublisherDesc(configName:backend1,transfers:[sshTransfer(execCommand: echo 开始部署 backend1 docker pull ${IMAGE}:${BUILD_NUMBER}docker rm-f ${APP_NAME}||true docker run-d--restart always--name ${APP_NAME}-p 80:8080 ${IMAGE}:${BUILD_NUMBER}docker image prune-f echo backend1 部署完成 )])])}}stage(部署 backend2){steps{sshPublisher(publishers:[sshPublisherDesc(configName:backend2,transfers:[sshTransfer(execCommand: echo 开始部署 backend2 docker pull ${IMAGE}:${BUILD_NUMBER}docker rm-f ${APP_NAME}||true docker run-d--restart always--name ${APP_NAME}-p 80:8080 ${IMAGE}:${BUILD_NUMBER}docker image prune-f echo backend2 部署完成 )])])}}}}}post{success{echo 流水线执行成功应用已成功部署至两台后端。 script{def branch params.tag ?:mainsh curl-s https://qyapi.weixin.qq.com/cgi-bin/webhook/send?keyb1dc849f-d727-46a1-9e54-c1ea17f373ff \\-H Content-Type:application/json \\-d {msgtype:markdown,markdown:{content:### Jenkins 流水线通知\\n**任务名称**${env.JOB_NAME}**构建编号**[#${env.BUILD_NUMBER}](${env.BUILD_URL})**目标版本**${branch}**构建状态**font color\\info\\构建成功/font**构建耗时**${currentBuild.durationString.replace( and counting,)}}} }}failure{echo 流水线执行失败请往上翻查看具体报错信息。 script{def branch params.tag ?:mainsh curl-s https://qyapi.weixin.qq.com/cgi-bin/webhook/send?keyb1dc849f-d727-46a1-9e54-c1ea17f373ff \\-H Content-Type:application/json \\-d {msgtype:markdown,markdown:{content:### Jenkins 流水线通知\\n**任务名称**${env.JOB_NAME}**构建编号**[#${env.BUILD_NUMBER}](${env.BUILD_URL})**目标版本**${branch}**构建状态**font color\\warning\\构建失败/font**构建耗时**${currentBuild.durationString.replace( and counting,)}}} }}aborted{echo 流水线被手动取消。 script{def branch params.tag ?:mainsh curl-s https://qyapi.weixin.qq.com/cgi-bin/webhook/send?keyb1dc849f-d727-46a1-9e54-c1ea17f373ff \\-H Content-Type:application/json \\-d {msgtype:markdown,markdown:{content:### Jenkins 流水线通知\\n**任务名称**${env.JOB_NAME}**构建编号**[#${env.BUILD_NUMBER}](${env.BUILD_URL})**目标版本**${branch}**构建状态**font color\\comment\\构建已取消/font**构建耗时**${currentBuild.durationString.replace( and counting,)}}} }}}}2.3 配置 Git 参数化构建2.4 配置 Webhook 触发器在gitlab中添加webhook2.5 执行流水线项目测试会自动构建项目并且顶部会显示状态码“200”效果如下pipeline构建项目演示构建成功后企微会收到消息我的pipeline还配置了参数化构建支持手动选择版本进行构建。当线上版本出现故障时可快速回滚至上一稳定版本三、基于 Jenkinsfile 的 Pipeline 流水线实现3.1 编写 Jenkinsfile 文件Jenkinsfile 内无需配置 GitLab 项目地址该信息在 Jenkins 项目的 Web 页面中进行配置rootdevelop:~/myapp# vim Jenkinsfilepipeline{agent any // 因为你的截图里分支配置了 ${tag}所以需要在脚本里声明这个参数 parameters{string(name:tag,defaultValue:main,description:请输入要构建的分支名或 Tag)}environment{// Harbor 配置 HARBOR_ADDR 192.168.13.138:80 PROJECT_NAME myapptest APP_NAME pipeline-integrated IMAGE ${HARBOR_ADDR}/${PROJECT_NAME}/${APP_NAME}}stages{stage(环境确认){steps{script{// 在 SCM 模式下代码已经拉好了直接打印一下当前拉取的信息即可echo 当前触发构建的分支/Tag:${params.tag ?:main}}sh git log-1--oneline}}stage(构建与推送镜像){steps{withCredentials([usernamePassword(credentialsId:harbor-cred,usernameVariable:HARBOR_USER,passwordVariable:HARBOR_PASS)]){sh set-e echo 1. 登录 Harbor echo $HARBOR_PASS|docker login $HARBOR_ADDR-u $HARBOR_USER--password-stdin echo 2. 构建镜像 (利用多阶段 Dockerfile) docker build-t $IMAGE:$BUILD_NUMBER-f Dockerfile . echo 3. 推送镜像 docker push $IMAGE:$BUILD_NUMBER echo 4. 同时打 latest 标签并推送 docker tag $IMAGE:$BUILD_NUMBER $IMAGE:latest docker push $IMAGE:latest echo 5. 登出 Harbor docker logout $HARBOR_ADDRecho 构建并推送完成:$IMAGE:$BUILD_NUMBER }}}stage(并行部署到后端){parallel{stage(部署 backend1){steps{sshPublisher(publishers:[sshPublisherDesc(configName:backend1,transfers:[sshTransfer(execCommand: echo 开始部署 backend1 docker pull ${IMAGE}:${BUILD_NUMBER}docker rm-f ${APP_NAME}||true docker run-d--restart always--name ${APP_NAME}-p 80:8080 ${IMAGE}:${BUILD_NUMBER}docker image prune-f echo backend1 部署完成 )])])}}stage(部署 backend2){steps{sshPublisher(publishers:[sshPublisherDesc(configName:backend2,transfers:[sshTransfer(execCommand: echo 开始部署 backend2 docker pull ${IMAGE}:${BUILD_NUMBER}docker rm-f ${APP_NAME}||true docker run-d--restart always--name ${APP_NAME}-p 80:8080 ${IMAGE}:${BUILD_NUMBER}docker image prune-f echo backend2 部署完成 )])])}}}}}post{success{echo 流水线执行成功应用已成功部署至两台后端。 script{def branch params.tag ?:mainsh curl-s https://qyapi.weixin.qq.com/cgi-bin/webhook/send?keyb1dc849f-d727-46a1-9e54-c1ea17f373ff \\-H Content-Type:application/json \\-d {msgtype:markdown,markdown:{content:### Jenkins 流水线通知\\n**任务名称**${env.JOB_NAME}**构建编号**[#${env.BUILD_NUMBER}](${env.BUILD_URL})**目标版本**${branch}**构建状态**font color\\info\\构建成功/font**构建耗时**${currentBuild.durationString.replace( and counting,)}}} }}failure{echo 流水线执行失败请往上翻查看具体报错信息。 script{def branch params.tag ?:mainsh curl-s https://qyapi.weixin.qq.com/cgi-bin/webhook/send?keyb1dc849f-d727-46a1-9e54-c1ea17f373ff \\-H Content-Type:application/json \\-d {msgtype:markdown,markdown:{content:### Jenkins 流水线通知\\n**任务名称**${env.JOB_NAME}**构建编号**[#${env.BUILD_NUMBER}](${env.BUILD_URL})**目标版本**${branch}**构建状态**font color\\warning\\构建失败/font**构建耗时**${currentBuild.durationString.replace( and counting,)}}} }}aborted{echo 流水线被手动取消。 script{def branch params.tag ?:mainsh curl-s https://qyapi.weixin.qq.com/cgi-bin/webhook/send?keyb1dc849f-d727-46a1-9e54-c1ea17f373ff \\-H Content-Type:application/json \\-d {msgtype:markdown,markdown:{content:### Jenkins 流水线通知\\n**任务名称**${env.JOB_NAME}**构建编号**[#${env.BUILD_NUMBER}](${env.BUILD_URL})**目标版本**${branch}**构建状态**font color\\comment\\构建已取消/font**构建耗时**${currentBuild.durationString.replace( and counting,)}}} }}}}3.2 推送项目代码至远程仓库使用 Jenkinsfile 管理 Pipeline 时需提前将带有 Jenkinsfile 的项目目录推送到远程仓库# 项目目录rootdevelop:~/myapp# pwd/root/myapp rootdevelop:~/myapp# lsDockerfile Jenkinsfile pom.xml README.md src# 把有jenkinsfile的项目推送到gitlab中rootdevelop:~/myapp# git add .rootdevelop:~/myapp# git commit -m version1rootdevelop:~/myapp# git tag version1rootdevelop:~/myapp# git push -u originrootdevelop:~/myapp# git push origin version13.3 Jenkins Web 页面任务配置这里我新建了一个项目设置分支配置gitlab项目拉取地址3.4 运行并验证流水线构建项目展示效果jenkinsfile项目效果展示同时企微也收到消息访问后端服务器网页成功注文中若有疏漏欢迎大家指正赐教。本文为100%原创转载请务必标注原创作者尊重劳动成果。求赞、求关注、求评论你的支持是我更新的最大动力评论区等你
觉得有用,分享给同行:

为您的企业打造数字门面

稳重轻奢商务风格,端正雅致视觉,长效耐看不易过时。

立即咨询 →