- 文档/教程
【免费下载链接】90DaysOfDevOps
This repository started out as a learning in public project for myself and has now become a structured learning map for many in the community. We have 3 years under our belt covering all things DevOps, including Principles, Processes, Tooling and Use Cases surrounding this vast topic.
Jenkins 是現代 DevOps 環境中最具代表性的持續整合(Continuous Integration,CI)工具之一,本篇文章以 90DaysOfDevOps 挑戰第 71 天的學習筆記為主軸,完整介紹 Jenkins 的定位、兩種程式碼整合方式、核心特性、Pipeline 概念與七步驟架構運作流程,並結合本倉庫2022/Days/CICD/Jenkins/目錄下的實際部署配置,說明如何在 minikube + Kubernetes 環境中透過 Helm Chart 安裝 Jenkins。讀完本篇,你將能清楚掌握 Jenkins 為何被視為 CI/CD 工具鏈的樞紐,以及從「程式碼提交」到「生產環境釋出」的完整自動化循環。
什麼是 Jenkins?
Jenkins 是一個持續整合(Continuous Integration)工具,它讓新寫好的程式碼可以持續地進行開發、測試與部署。簡單來說,Jenkins 作為一台CI 伺服器(CI Server),負責接管程式碼提交之後的測試與建置流程,將過去需要人工作業的整合過程自動化。
在 第 70 天:CI/CD 管線總覽 中,我們已經從宏觀角度認識了 CI/CD Pipeline 是現代 DevOps 環境的骨幹,它透過自動化建置、測試與部署,填補了開發與維運之間的鴻溝。而 Day 71 則正式進入工具層面,把目光聚焦在 Jenkins 這套具體的 CI 工具上。
要達成程式碼的持續整合,主要有兩種做法:
做法一:夜間建置(Nightly Builds)——傳統整合方式
開發人員在白天各自開發手上的任務,到了設定的時間點,把變更全部推送到原始碼儲存庫(Source Code Repository);接著在夜間執行單元測試與軟體建置。
這種「先各自開發、再集中整合」的方式,被視為整合所有程式碼的舊方法:問題通常要等到隔天早上才會被發現,回饋週期長、風險集中。
做法二:持續開發(Continuous Development)——推薦做法
開發人員仍然隨時把變更提交(Commit)到原始碼儲存庫,但差別在於:一旦程式碼提交完成,建置流程便會立刻被觸發,形成持續不斷的整合循環。
以上兩種方法背後的核心訴求是:當開發團隊分散在全球各地時,不應該存在一個「每天必須停止提交程式碼」的固定時間點。此時 Jenkins 便扮演 CI 伺服器的角色,統一控制這些測試與建置流程,讓任何時刻的提交都能被驗證。
為什麼是 Jenkins?——其他 CI 工具的比較
第 71 天的筆記同時整理了其他幾套 CI 工具作為對照,有助於理解 Jenkins 為何被視為最普遍的選擇,以及各家工具的差異:
- TravisCI:一套託管式(hosted)、分散式的持續整合服務,用於建置與測試託管在 GitHub 上的軟體專案。
- Bamboo:可平行執行多個建置以加快編譯速度,內建連接儲存庫的功能,並提供 Ant、Maven 的建置任務。
- Buildbot:開放原始碼的自動化框架,用於自動化軟體的建置、測試與釋出流程;以 Python 撰寫,支援跨平台、分散式與平行執行任務。
- Apache Gump:專門針對 Java 專案設計,目標是每晚建置並測試這些 Java 專案,確保所有專案在 API 與功能層面上彼此相容。
相較之下,Jenkins 與上述工具一樣是開放原始碼,但它是一套以 Java 撰寫的自動化伺服器(Automation Server),用於透過持續整合自動化軟體開發流程,並促成持續交付(Continuous Delivery)。
Jenkins 的核心特性
Jenkins 的特性橫跨許多面向,第 71 天的筆記重點整理出以下五項:
- 安裝容易(Easy Installation):Jenkins 是自包含(self-contained)的 Java 應用程式,提供 Windows、macOS 與 Linux 的安裝套件,下載後即可執行。
- 設定容易(Easy Configuration):透過 Web 介面即可輕鬆設定與配置,介面內建錯誤檢查(error checks)與內建說明(built-in help),大幅降低上手門檻。
- 外掛生態(Plug-ins):在 Update Centre 中提供大量外掛,可與 CI/CD 工具鏈中的許多工具整合(例如 Git、Docker、Kubernetes 等)。
- 可擴展(Extensible):除了現成外掛,Jenkins 本身可透過外掛架構持續擴展,幾乎提供無限的使用可能。
- 分散式(Distributed):Jenkins 可輕鬆將工作分散到多台機器執行,加速跨平台的建置、測試與部署。
Jenkins Pipeline:從提交到部署的自動化流程
「Pipeline(管線)」這個詞在 CI/CD 的宏觀討論中我們已經見過多次,但在 Day 71 開始進入具體工具層面:你把程式碼提交給 Jenkins,Jenkins 會建置你的應用程式、執行所有自動化測試,並在每個步驟完成後釋出與部署程式碼——Jenkins 正是讓這個過程自動化的關鍵。
這一條管線本質上涵蓋了 CI(建置 + 測試)與 CD(釋出 + 部署)兩個階段,Jenkins 在其中充當編排者(Orchestrator),串起整條工具鏈。
Jenkins 架構:從 commit 到 production 的七個步驟
Jenkins 可以安裝在許多不同的作業系統上(Windows、Linux、macOS),也支援以 Docker 容器方式部署,甚至可以在 Kubernetes 內執行。Day 71 的筆記特別預告:後續會嘗試在minikube 叢集中安裝 Jenkins,模擬部署到 Kubernetes 的情境(這也正是本倉庫2022/Days/CICD/Jenkins/目錄下配置文件的由來)。
接下來把下方架構圖拆解成七個步驟來理解:
- Step 1:開發人員把變更提交到原始碼儲存庫。
- Step 2:Jenkins 定期檢查儲存庫,拉取任何新程式碼。
- Step 3:建置伺服器把程式碼建置成可執行檔——在此例中使用Maven作為知名的建置伺服器(這也是一個值得深入的主題)。
- Step 4:若建置失敗,回饋(Feedback)會送回給開發人員。
- Step 5:Jenkins 將建置好的應用程式部署到測試伺服器——在此例中使用Selenium作為知名的測試伺服器(同樣值得另闢主題)。
- Step 6:若測試失敗,回饋會傳遞給開發人員。
- Step 7:若測試成功,則可釋出到生產環境(Production)。
這個循環是持續不斷的,正是這種自動化循環讓應用程式可以在「幾分鐘」內完成更新,而不是耗費數小時、數天、數月甚至數年!
Master-Slave 架構與企業級版本
Jenkins 的架構遠不止於此:它具備Master-Slave(主從)能力,讓 Master 可以把任務分配(distribute)給 Slave 的 Jenkins 環境執行,這正是前述「分散式(Distributed)」特性的底層支撐。
此外,由於 Jenkins 是開放原始碼專案,許多需要商業支援的企業會尋求CloudBees這套 Jenkins 的企業版——它為付費企業客戶帶來技術支援以及其他可能的功能。筆記中以Bosch(博世)作為實際客戶案例的參考。
在本專案中的實戰:minikube 上的 Jenkins 部署
Day 71 筆記預告了「在 minikube 叢集中安裝 Jenkins 模擬 Kubernetes 部署」的計畫,而本倉庫的 2022/Days/CICD/Jenkins/ 目錄恰好保留了這套完整部署的實作配置,可以作為理解 Jenkins 架構的絕佳佐證。
部署步驟一覽
2022/Days/CICD/Jenkins/steps.md 記錄了完整的部署步驟(以下為整理後的精簡命令序列):
- 啟動本機叢集:
minikube start - 建立命名空間:
kubectl create namespace jenkins或kubectl create -f jenkins-namespace.yml - 確認命名空間:
kubectl get namespaces - 加入官方 Helm Chart 儲存庫:
helm repo add jenkinsci https://charts.jenkins.io與helm repo update - 套用持久化儲存與服務帳號:
kubectl apply -f jenkins-volume.yml、kubectl apply -f jenkins-sa.yml - 透過 Helm 安裝:
helm install jenkins -n jenkins -f jenkins-values.yml $chart - 修正 PV 目錄權限:
minikube ssh後執行sudo chown -R 1000:1000 /data/jenkins-volume - 重啟 Pod 使權限生效:
kubectl delete pod jenkins-0 -n jenkins,接著kubectl get pods -n jenkins -w觀察啟動 - 取得管理員密碼:
kubectl exec --namespace jenkins -it svc/jenkins -c jenkins -- /bin/cat /run/secrets/chart-admin-password - 開放本機存取:
kubectl --namespace jenkins port-forward svc/jenkins 8080:8080 - 開啟瀏覽器登入
http://localhost:8080,執行外掛更新
配套的 Kubernetes 資源檔
這套部署並非單一命令,而是由多個 YAML 資源共同組成,各自扮演架構圖中的一環:
- jenkins-namespace.yml:建立名為
jenkins的獨立 Namespace,讓 Jenkins 及其 Agent 與叢集其他資源隔離。 - jenkins-volume.yml:定義一個 20Gi 的 PersistentVolume(
storageClassName: jenkins-pv、accessModes: ReadWriteOnce、persistentVolumeReclaimPolicy: Retain),透過 hostPath 掛載到節點的/data/jenkins-volume/。這保證 Jenkins 的$JENKINS_HOME(預設/var/jenkins_home)在 Pod 重建後仍能保留組態與 Job 資料,呼應架構中「建置資料需要持久化」的需求。 - jenkins-sa.yml:建立 ServiceAccount、ClusterRole 與 ClusterRoleBinding,授予 Jenkins 對 pods、deployments、statefulsets、configmaps、secrets、persistentvolumeclaims 等資源的完整操作權限。這正是 Jenkins 能在 Kubernetes 內部動態調度 Agent Pod 的權限基礎,也是「Master 把任務分配給 Slave」架構在 K8s 上的具體實現。
- jenkins-values.yml:Jenkins Helm Chart 的自訂值檔,重點包含:
controller.image: "jenkins/jenkins"、tagLabel: jdk11、servicePort/targetPort: 8080、serviceType: ClusterIP(minikube 情境可改 NodePort);runAsUser: 1000與fsGroup: 1000,以非 root 的jenkins使用者執行(對應到jenkins/jenkins官方映像內建的使用者);installPlugins預先安裝kubernetes:1.31.3、workflow-aggregator:2.6、git:4.10.2、configuration-as-code:1.55.1等外掛,佐證了筆記中「外掛生態豐富、可與 CI/CD 工具鏈整合」的特性;JCasC.securityRealm以 Configuration-as-Code 方式定義本地使用者(admin / chart-admin-password),體現「設定容易、Web 介面 + 聲明式配置」的設計;persistence.storageClass: jenkins-pv、size: "8Gi",與前面手動建立的 PV 對應;agent區塊定義 Agent 映像jenkins/inbound-agent:4.11.2-4與資源限制,呼應 Master-Slave / 分散式執行架構。
一份真實的 Jenkins Pipeline 範例
目錄下的 2022/Days/CICD/Jenkins/Pipeline/Jenkinsfile 是一份可直接對照筆記概念的 Declarative Pipeline:
podTemplate(yaml: ''' apiVersion: v1 kind: Pod spec: containers: - name: maven image: maven:3.8.1-jdk-8 command: ["sleep"] args: ["99d"] - name: kaniko image: gcr.io/kaniko-project/executor:debug command: ["sleep"] args: ["9999999"] volumeMounts: - name: kaniko-secret mountPath: /kaniko/.docker restartPolicy: Never volumes: - name: kaniko-secret secret: secretName: dockercred items: - key: .dockerconfigjson path: config.json ''') { node(POD_LABEL) { stage('Clone Repository') { git url: 'https://github.com/MichaelCade/Jenkins-HelloWorld.git', branch: 'main' container('maven') { stage('Build Image') { sh '''echo "Tests passed"''' } } } stage('Test Image') { container('kaniko') { stage('Build Hello World App') { sh ''' /kaniko/executor --context `pwd` --destination michaelcade1/helloworld:1.0 ''' } } } } }從這份檔案可以清楚看到 Jenkins Pipeline 的實際樣貌:它透過podTemplate定義一個包含Maven(建置)與Kaniko(建置 Docker 映像)兩個容器的 Agent Pod,然後以stage劃分「Clone Repository → Build Image → Test Image → Build Hello World App」等階段——這正是 Day 71 架構圖中「建置伺服器(Maven)」與「測試/打包」環節在真實專案中的落地。配套的 Pipeline/Dockerfile(一個基於 busybox 的簡易 HTTP 伺服器映像,預設埠 8000,提供 Hello World 頁面)與 Pipeline/index.html 則是這個被建置與部署的示範應用程式本身。
總結
第 71 天的重點可以歸納為:
- Jenkins 是 CI 工具與自動化伺服器:用於持續開發、測試與部署新寫的程式碼,讓分散在全球的開發團隊不必受制於固定的提交時間。
- 兩種整合方式:夜間建置(舊方法)vs 提交即觸發的持續開發(推薦做法),Jenkins 正是後者落地執行的 CI 伺服器。
- 特色鮮明:安裝容易、Web 介面配置、外掛生態豐富、可擴展、分散式執行。
- 七步驟架構循環:commit → Jenkins 拉取 → Maven 建置 → 失敗回饋 → Selenium 測試 → 失敗回饋 → 成功釋出至生產,讓應用程式得以在分鐘級完成更新。
- 可延伸的部署模型:支援 Master-Slave 分散架構,也可透過 minikube + Helm 在 Kubernetes 內部署;本倉庫 2022/Days/CICD/Jenkins/ 目錄保留了完整的部署步驟、Kubernetes 資源檔與 Pipeline 範例,可供後續章節與其他工具(如 ArgoCD、GitHub Actions)串接演練。
下一步將在第 72 天 繼續深入 Jenkins 的實作環節。
- 文档/教程
【免费下载链接】90DaysOfDevOps
This repository started out as a learning in public project for myself and has now become a structured learning map for many in the community. We have 3 years under our belt covering all things DevOps, including Principles, Processes, Tooling and Use Cases surrounding this vast topic.
相关推荐
90DaysOfDevOps 第 71 天:什么是 Jenkins?CI 服务器原理与架构拆解
90DaysOfDevOps 第 71 天:什么是 Jenkins?CI 服务器原理与架构拆解 导读:本文是 90DaysOfDevOps 学习路线图中 CI/
文档/教程90DaysOfDevOps 第 71 天:认识 Jenkins——开源的持续集成与持续交付自动化服务器
90DaysOfDevOps 第 71 天:认识 Jenkins——开源的持续集成与持续交付自动化服务器 本文是 90DaysOfDevOps 学习路线中 CI
文档/教程90DaysOfDevOps 第 71 天:什么是 Jenkins?——从 CI 工具定位到 Kubernetes 集群部署实战
90DaysOfDevOps 第 71 天:什么是 Jenkins?——从 CI 工具定位到 Kubernetes 集群部署实战 本篇文章以 90DaysOfD
文档/教程
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考