k8s平台基於Jenkins構建微服務發布平台-1


實驗架構說明: 根據上篇文章 <<6、微服務容器化遷移>> 環境進行操作

(1) nfs存儲
(2) harbor鏡像倉庫
(3) gitlab代碼倉庫
(4) ingress-nginx
(5) nfs-subdir-external-provisioner

發布流程設計: image-20220209145255750

基於kubernetes完整的DevOps流程: 基於kubernetes完整的DevOps流程

1 部署Jenkins

1.1 配置說明
1 Jenkins是一款開源的CI&CD系統,用於自動化各種任務,包括構建、測試和部署。
2 Jenkins官方提供了鏡像"https://hub.docker.com/r/jenkins/jenkins"。
3 在"default"命名空間下使用"Deployment"方式來部署這個鏡像,"kind: Service"使用"type: NodePort"暴露端口,Web內部訪問端口80,
Web外部訪問端口30006,Slave內部通信端口5000,容器啟動后Jenkins數據存儲在"/var/jenkins_home"目錄,所以需要將該目錄使用PV持久化
存儲。
1.2 Jenkins.yml配置文件
 
           
[root@k8s-master1 ms_jenkins]# cat jenkins.yml
apiVersion: apps/v1
kind: Deployment 
metadata:
  name: jenkins
  labels:
    name: jenkins
spec:
  replicas: 1
  selector:
    matchLabels:
      name: jenkins 
  template:
    metadata:
      name: jenkins
      labels:
        name: jenkins
    spec:
      terminationGracePeriodSeconds: 10
      serviceAccountName: jenkins
      containers:
        - name: jenkins
          image: jenkins/jenkins
          imagePullPolicy: Always
          ports:
            - containerPort: 8080
            - containerPort: 50000
          resources:
            limits:
              cpu: 1
              memory: 1Gi
            requests:
              cpu: 0.2
              memory: 200Mi
          env:
            - name: JAVA_OPTS
              value: -Xmx1g 
          volumeMounts:
            - name: jenkins-home
              mountPath: /var/jenkins_home
      securityContext:
        fsGroup: 1000
        runAsUser: 0
      volumes:
        - name: jenkins-home
          persistentVolumeClaim:
            claimName: jenkins-home
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: jenkins-home
spec:
  storageClassName: "managed-nfs-storage"
  accessModes: ["ReadWriteOnce"]
  resources:
    requests:
      storage: 5Gi
---
apiVersion: v1
kind: Service
metadata:
  name: jenkins
spec:
  selector:
    name: jenkins
  type: NodePort
  ports:
    - name: http
      port: 80
      targetPort: 8080
      protocol: TCP
      nodePort: 30006
    - name: agent
      port: 50000
      protocol: TCP
---
apiVersion: v1
kind: ServiceAccount
metadata:
  name: jenkins

---
kind: Role
apiVersion: rbac.authorization.k8s.io/v1
metadata:
  name: jenkins
rules:
- apiGroups: [""]
  resources: ["pods","events"]
  verbs: ["create","delete","get","list","patch","update","watch"]
- apiGroups: [""]
  resources: ["pods/exec"]
  verbs: ["create","delete","get","list","patch","update","watch"]
- apiGroups: [""]
  resources: ["pods/log"]
  verbs: ["get","list","watch"]
- apiGroups: [""]
  resources: ["secrets","events"]
  verbs: ["get"]

---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: jenkins
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: Role
  name: jenkins
subjects:
- kind: ServiceAccount
  name: jenkins
[root@k8s-master1 ms_jenkins]#

1.3 部署Jenkins
# kubectl apply -f jenkins.yml
# kubectl get pod -l name=jenkins -n default
# kubectl get svc/jenkins -n default
# kubectl get ep/jenkins -n default
#
# kubectl get pv
# kubectl get pvc -n default

圖示: image-20220209141209853

1.4 Jenkins UI界面安裝步驟
1 獲取Jenkins初始化安裝密碼
# kubectl logs -f pod/jenkins-578b57ddcb-dzn7n -n default
......(省略的內容)
Jenkins initial setup is required. An admin user has been created and a password generated.
Please use the following password to proceed to installation:

72c0bc4c4a6748aba3fa39b0797eb08c

This may also be found at: /var/jenkins_home/secrets/initialAdminPassword
......(省略的內容)

2 解鎖Jenkins

http://172.16.1.81:30006/ image-20220209142841067

3 選擇插件來安裝

圖示: image-20220209143056008

4 不安裝任何的插件

圖示: image-20220209143304983

5 創建管理員

圖示: image-20220209143804755

6 Jenkins URL

圖示: image-20220209144011945

7 Jenkins安裝完成

圖示: image-20220209144218742

8 Jenkins首頁

圖示: image-20220209144424351

1.5 安裝插件
Manage Jenkins -> System Configuration -> Manage Plugins -> Available -> 分別搜索 
Chinese/Git/Git Parameter/Pipeline/kubernetes/Config File Provider/Extended Choice Parameter -> 選中后點擊
Install without restart

1 Chinese # 中文字體
2 Git # 拉取代碼
3 Git Parameter # Git參數化構建
4 Pipeline # 流水線
5 kubernetes # 連接Kubernetes動態創建Slave代理
6 Config File Provider # 存儲配置文件
7 Extended Choice Parameter # 擴展選擇框參數,支持多選

插件安裝完成后必須重啟Jenkins,否則安裝的插件無法正常使用,重啟Jenkins的方法為: http://172.16.1.81:30006/restart

提示: Jenkins的UI界面上可能會提示Jenkins版本升級和一些警告信息,忽略即可。

圖示: image-20220210102701446

2 Jenkins在kubernetes中動態創建代理

2.1 Jenkins主從架構介紹
1 Jenkins Master/Slave架構
Master(Jenkins本身)提供Web頁面讓用戶來管理項目和從節點(Slave),項目任務可以運行在Master本機或者分配到從節點運行,一個Master可以關聯多個Slave,這樣的好處是可以讓Slave分擔Master工作壓力和隔離構建環境。

Jenkins Master/Slave架構圖: image-20220209170545295

2 當觸發Jenkins任務時,Jenkins會調用Kubernetes API創建Slave Pod,Pod啟動后會連接Jenkins,接受任務並處理。

圖示: image-20220209173620420

2.2 kubernetes插件配置
1 kubernetes插件介紹
Kubernetes插件用於Jenkins在Kubernetes集群中運行動態代理,插件介紹"https://github.com/jenkinsci/kubernetes-plugin"。

2 配置插件
系統管理 -> 系統配置 -> 節點管理 -> Configure Clouds -> 配置集群 -> Add a new cloud -> Kubernetes ->
Kubernetes Cloud details
(1) Jenkins連接k8s配置

圖示: image-20220210110135542

(2) jenkins slave連接jenkins master配置

圖示: image-20220210113028929

2.3 自定義Jenkins Slave鏡像
1 編排 jenkins slave 鏡像所需的配置文件
[root@k8s-master1 ms_jenkins]# mkdir -p jenkins-slave/
[root@k8s-master1 ms_jenkins]# cd jenkins-slave/

(1) Dockerfile
# cat Dockerfile
FROM centos:7
LABEL maintainer lc

RUN yum install -y java-1.8.0-openjdk maven curl git libtool-ltdl-devel && \
yum clean all && \
rm -rf /var/cache/yum/* && \
mkdir -p /usr/share/jenkins

COPY agent.jar /usr/share/jenkins/agent.jar
COPY jenkins-agent /usr/bin/jenkins-agent
COPY settings.xml /etc/maven/settings.xml
RUN chmod +x /usr/bin/jenkins-agent
COPY helm kubectl /usr/bin/

ENTRYPOINT ["jenkins-agent"]

(2) helm
下載地址: https://get.helm.sh/helm-v3.4.2-linux-amd64.tar.gz
# chmod +x helm

(3) jenkins-agent
github開源地址: https://github.com/jenkinsci/docker-inbound-agent
下載代碼庫: https://github.com/jenkinsci/docker-inbound-agent/archive/refs/heads/master.zip
使用 "jenkins-agent" shell 腳本文件。

(4) kubectl
# cp -a /usr/bin/kubectl /root/ms_jenkins/jenkins-slave/
# chmod +x /root/ms_jenkins/jenkins-slave/kubectl

(5) settings.xml
下載地址: http://archive.apache.org/dist/maven/maven-3/3.5.0/binaries/apache-maven-3.5.0-bin.tar.gz

配置文檔: https://developer.aliyun.com/article/512821
在 setttins.xml 文件中找到 <mirrors></mirrors> 標簽對,添加如下內容:
<mirror>
<id>nexus-aliyun</id>
<mirrorOf>*</mirrorOf>
<name>Nexus aliyun</name>
<url>http://maven.aliyun.com/nexus/content/groups/public</url>
</mirror>

(6) agent.jar
# wget http://172.16.1.81:30006/jnlpJars/agent.jar

2 編排 jenkins slave 鏡像所需的配置文件說明
[root@k8s-master1 jenkins-slave]# ls -l
total 81428
-rw-r--r-- 1 root root 1522173 Feb 10 10:00 agent.jar # jenkins agent 程序,接受 master 下發的任務
-rw-r--r-- 1 root root 423 Feb 10 17:02 Dockerfile # jenkins slave 鏡像編排文件
-rwxr-xr-x 1 root root 41603072 Dec 9 2020 helm # helm 二進制文件,客戶端工具
-rw-r--r-- 1 root root 5390 Feb 10 17:16 jenkins-agent # shell 腳本用於啟動 agent.jar
-rwxr-xr-x 1 root root 40230912 Dec 9 2020 kubectl # kubectl 二進制文件,客戶端工具
-rw-r--r-- 1 root root 10406 Feb 10 17:36 settings.xml # maven 配置文件

3 構建 jenkins slave 鏡像並推送到鏡像倉庫
說明: 構建的 jenkins slave 鏡像作為中間件鏡像使用,因此將其放到公開項目 library 下
(1) 構建鏡像
[root@k8s-master1 jenkins-slave]# docker build -t 172.16.1.61/library/jenkins-slave-jdk:1.8 .

(2) 推送到鏡像倉庫
[root@k8s-master1 jenkins-slave]# docker push 172.16.1.61/library/jenkins-slave-jdk:1.8

(3) 查看推送的鏡像

圖示: image-20220210183255565

2.4 測試Jenkins主從架構

  
  
  
          
1 新建項目 -> 項目名(jenkins-slave-test) -> 流水線 -> Pipeline script -> 生成示例[Declarative(Kubernetes)]

2 生成示例[Declarative(Kubernetes)]
pipeline {
    agent {
        kubernetes {
            // 定義pod名稱的前綴,如果不定義,pod名稱的前綴為項目名
            label "jenkins-agent"
            yaml '''
apiVersion: v1
kind: Pod
spec:
  containers:
  # 這里容器名必須定義為jnlp
  - name: jnlp
    image: 172.16.1.61/library/jenkins-slave-jdk:1.8
'''
        }
    }
    stages {
        stage('Main') {
            steps {
                sh 'hostname'
            }
        }
    }
}

3 查看構建輸出
pipeline 項目在執行的過程中會在 k8s 集群中創建 Jenkins slave pod,pipeline 項目運行結束后會自動銷毀創建的 pod。 
[root@k8s-master1 ~]# kubectl get pod -n default
NAME                                      READY   STATUS    RESTARTS   AGE
jenkins-578b57ddcb-6lfbw                  1/1     Running   0          3h30m
jenkins-agent-bddp0-q5pnh                 1/1     Running   0          9s

圖示: image-20220213225954842

3 Jenkins Pipeline流水線

3.1 Pipeline介紹
Jenkins Pipeline是一套運行工作流框架,將原本獨立運行單個或者多個節點的任務鏈接起來,實現單個任務難以完成的復雜流程編排和可視化。
1 Jenkins Pipeline 是一套插件,支持在 Jenkins 中實現持續集成和持續交付。
2 Pipeline 通過特定語法對簡單到復雜的傳輸管道進行建模。
3 Jenkins Pipeline 的定義被寫入一個文本文件,稱為Jenkinsfile。

圖示: image-20220214092905306

3.2 Pipeline語法
pipeline 語法包括聲明式和腳本式兩種。
1 聲明式
支持大部分Groovy,具有豐富的語法特性,易於編寫和設計,pipeline {}

圖示: image-20220214093948315

2 腳本式
遵循與Groovy相同的語法,node {}

圖示: image-20220214094041154

3.3 Pipeline示例
1 jenkins example
pipeline {
    agent any
    
    stages {
        stage('Build') {
            steps {
                echo 'build......'
            }
        }
        
        stage('Test') {
            steps {
                echo 'Test......'
            }
        }
        
        stage('Deploy') {
            steps {
                echo 'deploy......'
            }
        }
        
    }
}

2 參數說明
(1) "stages" 是 Pipeline 中最主要的組成部分,Jenkins 將會按照 stages 中描述的順序從上往下的執行。

(2) "stage"  是一個 Pipeline 可以划分為若干個 stage,每個 stage 代表一組操作,比如: Build、Test、Deploy。

(3) "steps"  步驟,steps 是最基本的操作單元,可以是打印一句話,也可以是構建一個 Docker 鏡像,由各類 Jenkins
插件提供,比如命令: sh 'mvn',就相當於我們平時 shell 終端中執行 mvn 命令一樣。

4 流水線自動發布微服務項目

4.1 發布需求
1 將微服務項目自動化部署到K8s平台的需求
(1) 盡量完全自動化部署,無需過多人工干預。
(2) 可以選擇升級某個、某些微服務。
(3) 在部署、升級微服務時,可對微服務某些特性做配置,例如命名空間、副本數量。

2 發布過程
拉取代碼 -> 代碼編譯 -> 構建鏡像 -> 部署到 kubernetes -> 測試

圖示: image-20220214111334922

image-20220214111423522

圖示: image-20220227194259163

4.2 實現思路
在微服務架構中,會涉及幾個、幾十個微服務,如果每個服務都創建一個item,會增加維護的成本,因此需要編寫一個通用的Pipeline腳本,將這些
微服務部署差異化的部分使用Jenkins參數化,然后由人工交互確認發布微服務、環境配置等。但這只是解決了用戶的交互層面,在K8s實際部署項目
時用YAML創建對應的資源,現在的問題是如何接收用戶的交互參數,自動化生成 YAML 文件,這就會用到 Helm 完成 YAML 文件的高效復用和微服
務部署。
4.3 gitlab、harbor認證添加
1 啟用 Harbor 的 Chart 倉庫服務
[root@k8s_harbor ~]# cd /usr/local/harbor/
[root@k8s_harbor harbor]# ./install.sh --with-chartmuseum
# 啟用后,默認創建的項目就帶有 helm charts 功能了,不需要重啟 harbor 服務。

Helm Charts插件: image-20220227193442139

上傳Charts代碼包: image-20220227211449095

2 推送微服務代碼到 gitlab 的 microservice 倉庫
[root@k8s-master1 ms_jenkins]# unzip simple-microservice.zip
[root@k8s-master1 ms_jenkins]# cd simple-microservice/
[root@k8s-master1 simple-microservice]# git config --global user.name "Administrator"
[root@k8s-master1 simple-microservice]# git config --global user.email "admin@example.com"
[root@k8s-master1 simple-microservice]# git init
Initialized empty Git repository in /root/ms_jenkins/simple-microservice/.git/
[root@k8s-master1 simple-microservice]# git remote add origin http://172.16.1.62:9999/dev/microservice.git
[root@k8s-master1 simple-microservice]# git add .
[root@k8s-master1 simple-microservice]# git commit -m "Initial commit"
[root@k8s-master1 simple-microservice]# git push -u origin master
Username for 'http://172.16.1.62:9999': root
Password for 'http://root@172.16.1.62:9999': # 密碼: 12345678

圖示: image-20220227185541834

3 將 gitlab 認證和 harbor 認證保存到 Jenkins 憑據
系統管理 -> 安全 -> 管理憑據 -> Jenkins -> 全局憑據(添加憑據) -> 類型(Username with password)
分別添加連接 gitlab 和 harbor 的用戶名、密碼到 Jenkins 憑據,然后獲取該憑據 ID 替換到腳本中 git_auth 和
docker_registry_auth 變量的值。

圖示(gitlab認證): image-20220227195708153

圖示(harbor認證): image-20220227200102825 gitlab、harbor全局憑證ID:

gitlab ID: 26abeef4-acf8-4ba8-8e4e-454bc8a77513
harbor ID: a87872af-6fd5-45ed-a6b3-fb59ce0bcbf4

image-20220227200237164

4 將 kubeconfig 存儲在 Jenkins,用於 slave 鏡像里 kubectl 連接 k8s 集群
系統管理 -> 系統配置 -> Managed files -> Add a new Config -> Custom file -> Next -> Content字段(填寫內容是
kubeconfig,kubeadm 部署 k8s 默認路徑在 master 節點 "/root/.kube/config",如果是二進制部署,需要自己生成),然后
復制 ID 替換腳本中 k8s_auth 變量的值。

說明: 將 kubectl、helm 工具封裝到 Slave 鏡像中,並通過 Config File Provider 插件存儲連接 K8s 集群的 kubeconfig 認證
文件,然后掛載到 slave 容器中,這樣就能使用 "kubectl apply deploy.yaml --kubeconfig=config" 命令管理 K8s 應用了,為
提高安全性,kubeconfig 文件可分配權限。

圖示(k8s認證):

k8s_auth ID: 1f58f4c8-720f-4126-91c7-b4d919655737

image-20220227210330859

注: 剩余內容請查看文章"基於Jenkins構建微服務發布平台-2"



免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM