GitHub Webhook 实战系列 (三):Jenkins Pipeline CI+CD 完整闭环,Push 代码自动构建、打包、远程服务器一键部署
系列专栏GitHub Webhook 深度实战 前文回顾 系列第一篇讲解 GitHub Webhook 底层原理、密钥校验、事件调试第二篇完成 Webhook 对接 Jenkins 流水线实现代码 Push 自动拉取、单元测试、打包构建完整走完 CI 持续集成流程。本篇作为进阶 CD 持续交付实战基于上一篇现成 Pipeline 改造新增远程服务器自动部署能力打通「提交代码→自动拉取→单元测试→构建产物→远程发布上线」完整自动化链路一套脚本覆盖 CICD适配 Java SpringBoot 项目内网 / 公网服务器均可落地附带完整排坑、服务器免密配置、生产环境安全规范。一、前置准备承接第二篇环境新增 CD 依赖1.1 已有环境沿用第二篇Jenkins 2.300 LTS 稳定版已安装 Git、Maven、GitHub Integration、Pipeline、JUnit 插件GitHub 仓库配置 Webhook可正常触发 Jenkins 流水线 CI 流程项目根目录存在基础 Jenkinsfile能完成代码拉取、测试、打包、产物归档1.2 CD 阶段新增必备配置1.2.1 Jenkins 安装远程发布核心插件进入【管理 Jenkins - 插件管理 - 可选插件】搜索安装SSH Agents Plugin支持 ssh 远程连接服务器执行 shell 脚本Publish Over SSH业界通用远程文件传输、远程执行命令插件本篇主推 安装完成重启 Jenkins 生效。1.2.2 配置服务器 SSH 凭证免密登录核心两种方案推荐方案 1密钥免密生产安全方案 1SSH 公私钥免密推荐Jenkins 服务器生成密钥对ssh-keygen -t rsa一路回车不设置密码将公钥id_rsa.pub内容复制到目标部署服务器~/.ssh/authorized_keysJenkins 全局配置 SSH 服务 管理 Jenkins → 系统 → Publish over SSH → SSH Servers → Add SSH ServerName自定义服务标识prod-serverHostname部署服务器公网 IP / 内网 IPUsername服务器登录账号root / 普通运维账号Remote Directory远程存放 jar 包目录/data/app/demoAdvanced → 勾选 Use Private Key粘贴 Jenkins 私钥完整内容保存方案 2账号密码登录仅测试环境使用生产禁用直接填写服务器账号密码安全性差仅本地演示使用。1.2.3 目标服务器环境提前就绪安装对应 JDK 版本和项目编译 JDK 版本保持一致创建应用目录mkdir -p /data/app/demo /data/app/demo/logs提前编写启停脚本start.sh / stop.sh用于远程一键重启服务/data/app/demo/stop.sh#!/bin/bash pidps -ef | grep demo.jar | grep -v grep | awk {print $2} if [ -n $pid ];then kill -9 $pid echo 旧进程已停止 pid:$pid fi/data/app/demo/start.sh#!/bin/bash nohup java -jar demo.jar --spring.profiles.activeprod logs/run.log 21 echo 服务启动完成 sleep 2 pidps -ef | grep demo.jar | grep -v grep | awk {print $2} echo 运行进程pid:$pid赋予脚本执行权限chmod x start.sh stop.sh二、改造完整版 JenkinsfileCICD 一体化基于第二篇 CI 脚本扩展新增6. 远程传输产物、7. 服务器自动部署两大阶段完整脚本可直接替换仓库根目录 Jenkinsfile适配 Maven SpringBoot 项目。pipeline { agent any environment { // 和Jenkins全局工具配置Maven名称保持一致 MAVEN_HOME tool Maven3 PROJECT_VERSION 1.0.0 // SSH服务名称和Publish over SSH配置名称统一 SSH_SERVER prod-server // 远程服务器应用目录 REMOTE_APP_PATH /data/app/demo // 本地产物路径 LOCAL_JAR target/*.jar } stages { stage(1. 环境初始化) { steps { echo CICD流水线启动初始化环境 sh mvn -v sh git --version } } stage(2. 拉取GitHub最新代码) { steps { echo 清理工作空间拉取远程代码 cleanWs() sh git pull origin main } } stage(3. 单元测试校验质量卡点) { steps { echo 执行单元测试测试失败直接阻断流水线 sh ${MAVEN_HOME}/bin/mvn clean test -Dmaven.test.failure.ignorefalse } post { always { junit allowEmptyResults: true, testResults: **/target/surefire-reports/*.xml } } } stage(4. Maven打包构建产物) { steps { echo 编译打包跳过测试已单独执行测试阶段 sh ${MAVEN_HOME}/bin/mvn clean package -DskipTeststrue } } stage(5. 本地归档构建产物) { steps { echo 归档Jar包Jenkins后台留存历史版本 archiveArtifacts artifacts: target/*.jar, fingerprint: true, onlySuccessful: true } } // 新增CD阶段上传Jar到远程服务器 stage(6. SSH传输产物至部署服务器) { steps { echo 开始将构建好的Jar包上传至生产服务器 sshPublisher(publishers: [ sshPublisherDesc( configName: env.SSH_SERVER, transfers: [ sshTransfer( sourceFiles: env.LOCAL_JAR, remoteDirectory: env.REMOTE_APP_PATH, postTransfers: [ postTransferStep( // 上传完成后先执行停止脚本 transfers: [sshCommand(command: cd ${REMOTE_APP_PATH} sh stop.sh)] ) ] ) ] ) ]) } } // 新增CD阶段远程启动服务完成上线 stage(7. 远程服务器自动部署上线) { steps { echo 执行启动脚本重启后端服务完成CD发布 sshPublisher(publishers: [ sshPublisherDesc( configName: env.SSH_SERVER, transfers: [ sshTransfer( sourceFiles: , remoteDirectory: env.REMOTE_APP_PATH, postTransfers: [ postTransferStep( transfers: [sshCommand(command: cd ${REMOTE_APP_PATH} sh start.sh)] ) ] ) ] ) ]) } } } post { success { echo ✅ CICD全流程完成代码拉取→测试→打包→上传→自动部署上线成功 } failure { echo ❌ 流水线执行失败终止发布检查对应阶段日志排查问题 } always { // 可选对接钉钉/企业微信机器人推送构建结果 } } }脚本核心 CD 逻辑拆解sshPublisher调用全局配置的 SSH 服务器自动建立免密连接sourceFiles指定本地 Jenkins 工作空间打包生成的 jar 文件remoteDirectory远程服务器存放包的应用目录postTransfers文件上传完成后执行远程 shell 命令先停旧服务再启动新版本流水线分层隔离CI 流程测试、打包和 CD 流程传输、部署完全解耦测试失败直接阻断发布避免故障版本上线三、Jenkins 流水线任务配套修改第二篇已创建好 Pipeline 任务仅需两处微小更新流水线脚本路径不变依旧读取仓库根目录Jenkinsfile提交新脚本后自动生效确认【构建触发器】依旧勾选GitHub hook trigger for GITScm polling保证 Push 自动触发可选配置构建超时时间、并发构建禁止避免多人同时推送代码重复部署 流水线配置页面 → 【选项】→ 勾选禁止并发构建防止多任务同时覆盖服务器 Jar 包四、GitHub Webhook 无需改动复用原有配置Payload URL、Content-Type、触发事件、Secret 密钥全部沿用第二篇配置无需修改。 触发链路完整闭环 本地 Git Push 代码 → GitHub 推送 Webhook 请求 → Jenkins 接收事件自动启动 Pipeline 流水线执行链路 环境初始化 → 拉取代码 → 单元测试校验 → 打包 Jar → 本地归档 → SSH 上传至服务器 → 停止旧服务 → 启动新版本 → 发布完成五、全流程完整验证测试本地修改业务代码提交推送 GitHubgit add . git commit -m feat: 测试自动CICD部署 git push origin main立刻刷新 Jenkins 任务页面流水线自动启动逐阶段观察执行状态前 5 个 CI 阶段绿色通过后自动执行 6、7 两个 CD 部署阶段登录目标部署服务器验证/data/app/demo目录存在最新上传的 demo.jarps -ef | grep java能查询到新版本服务进程访问项目接口确认功能更新生效查看 GitHub Webhook 记录显示推送请求绿色成功✅六、高频 CD 部署场景排坑指南问题 1SSH 上传文件失败提示连接拒绝 / 权限不足检查 Jenkins 全局 SSH 配置 IP、账号、密钥是否正确服务器防火墙开放 22 端口安全组放行 Jenkins 服务器出口 IP服务器~/.ssh文件夹权限 700authorized_keys 权限 600权限过宽会拒绝免密登录问题 2远程执行 stop.sh/start.sh 无效果进程未重启脚本缺少执行权限chmod x *.sh脚本路径使用绝对路径避免相对路径导致找不到文件查看服务器 logs 日志排查 Java 启动报错端口占用、配置缺失、JDK 版本不匹配问题 3单元测试报错直接阻断部署属于设计预期测试用例失败不允许发布上线优先修复代码单元测试问题生产环境禁止跳过 test 阶段。问题 4并发推送代码Jar 包覆盖引发服务异常解决方案流水线配置开启【禁止并发构建】上一次发布未完成时新触发任务排队等待。问题 5Jenkins 提示 Publish over SSH 插件方法不存在确认插件安装完成并重启 Jenkins脚本中sshPublisher为该插件专属语法缺少插件直接报错。七、生产环境 CD 优化进阶方案环境区分部署多分支匹配多服务器main 分支部署生产、dev 分支部署测试环境通过 Git 分支判断切换 SSH 服务器配置。版本备份回滚机制上传 Jar 包前将旧包重命名备份新增回滚流水线任务一键切换历史版本。发布结果消息通知CD 部署完成后调用钉钉 / 企业微信机器人推送构建版本、提交记录、部署服务器、运行状态。健康检查卡点新增远程 curl 健康检测脚本启动服务后循环访问健康接口接口正常才算部署成功否则标记流水线失败告警。密钥安全管控禁止明文账号密码统一使用 SSH 密钥Jenkins 凭证使用加密存储不硬编码 IP、账号到 Jenkinsfile。限流与灰度发布多节点集群场景扩展脚本实现分批灰度部署避免全量停机引发业务中断。八、系列整体总结与下一篇预告本系列三篇完整能力汇总第一篇吃透 GitHub Webhook 底层原理、密钥校验、事件调试、接口调试打好自动化基础第二篇Webhook 对接 Jenkins落地完整 CI 持续集成代码拉取、单元测试、产物打包归档第三篇基于 CI 流水线扩展 CD 持续交付打通自动远程服务器部署实现代码 Push 即上线全自动化闭环下一篇预告系列四后续将讲解企业级加固方案Webhook 请求密钥鉴权防恶意攻击、Jenkins 权限分级、流水线分支过滤、多环境 (dev/test/prod) 隔离部署、灰度发布与自动回滚完整实战完善企业生产可用的标准化自动化发布体系。文末总结本篇文章完成 CICD 完整自动化闭环从开发提交代码到服务自动上线全程零人工介入解决传统开发手动打包、手动上传服务器、手动启停服务的低效问题。整套方案基于 GitHub WebhookJenkins Pipeline 实现适配中小型企业 Java 后端项目合规、可复用、易维护所有脚本开箱即用直接落地到测试 / 生产环境。