一安寺、概述
最近在研究基于k8s實(shí)現(xiàn)一套devops流程凡壤,由于搭建一套k8s集群比較麻煩勺远,所有打算使用minikube
在我本地的windows上面實(shí)現(xiàn)整套devops流程橙喘,在這里記錄一下整個(gè)實(shí)踐過程,希望對(duì)需要的同學(xué)提供一些參考胶逢,也便于自己以后查閱厅瞎。
minikube官方地址:https://minikube.sigs.k8s.io/docs/start/
運(yùn)行環(huán)境
windows 10
minikube 1.18.1
kubernetes 1.20.2
二、安裝minikube
minikube
是本地的Kubernetes初坠,致力于使Kubernetes易于學(xué)習(xí)和開發(fā)和簸。
你需要的只是Docker(或類似兼容)容器或虛擬機(jī)環(huán)境,只需一個(gè)命令即可: minikube start
即可在本地啟動(dòng)一個(gè)kubernetes集群碟刺。
1. 運(yùn)行minikube的條件
- 2個(gè)或更多CPU
- 2GB的可用內(nèi)存
- 20GB的可用磁盤空間
- 網(wǎng)絡(luò)連接
- 容器或虛擬機(jī)管理器锁保,例如:Docker,Hyperkit半沽,Hyper-V爽柒,KVM,Parallels者填,Podman浩村,VirtualBox或VMWare
說明:minikube 提供了跨平臺(tái)搭建k8s的能力,支持mac 占哟,linux 心墅,windows平臺(tái),每一個(gè)平臺(tái)上也支持多種驅(qū)動(dòng)架構(gòu)榨乎,windows 支持docker嗓化,Hyper-V,virtualBox等谬哀,由于win10已經(jīng)內(nèi)置了Hyper-V刺覆,這里選擇Hyper-V。
2. 在windows中開啟Hyper-V
Hyper-V是內(nèi)置于現(xiàn)代Microsoft Windows版本中的本機(jī)虛擬機(jī)管理程序史煎,需要是Windows 10企業(yè)版谦屑,專業(yè)版或教育版的64位版本系統(tǒng)才能開啟,我這里使用的是windows 10 專業(yè)版系統(tǒng)篇梭,通過如下方式開啟Hyper-V氢橙。
以管理員身份打開PowerShell控制臺(tái),然后運(yùn)行以下命令:
Enable-WindowsOptionalFeature -Online -FeatureName Microsoft-Hyper-V -All
如果Hyper-V先前未處于活動(dòng)狀態(tài)恬偷,則需要重新啟動(dòng)悍手。我這里已經(jīng)開啟了,所以如下圖所示,顯示online 坦康,并且不需要重新竣付。
3. 下載minikube
下載并運(yùn)行Windows安裝程序
安裝完成后,搜索cmd并以管理員身份打開
4. 啟動(dòng)minikube
使用如下命令啟動(dòng)minikube會(huì)導(dǎo)致有的鏡像無法拉取滞欠,接著往下面看成功的運(yùn)行命令
minikube start --driver=hyperv --registry-mirror=https://registry.docker-cn.com,https://shraym0v.mirror.aliyuncs.com --embed-certs=true --image-mirror-country=cn --image-repository=registry.cn-hangzhou.aliyuncs.com/google_containers
參數(shù)說明
可以通過minikube start --help
查看其它參數(shù)的詳細(xì)說明古胆,這里說明上面使用的參數(shù)
-
minikube start
:啟動(dòng)一個(gè)本地單節(jié)點(diǎn)kubernetes集群。 -
--driver=hyperv
:指定驅(qū)動(dòng)為hyperv筛璧,默認(rèn)為自動(dòng)檢測(virtualbox, vmwarefusion, hyperv, vmware, docker, ssh)中的一個(gè)逸绎。 -
--registry-mirror=https://registry.docker-cn.com
:使用國內(nèi)的鏡像地址來提高拉取鏡像的速度,可以設(shè)置多個(gè)用,
分割即可夭谤。 -
--embed-certs=true
: 如果為true棺牧,將在kubeconfig中嵌入證書,默認(rèn)為false朗儒,在kubeconfig中將以絕對(duì)路徑的方式讀取證書文件陨帆。 -
--image-mirror-country=cn
:需要使用的鏡像的國家/地區(qū)代碼,留空以使用全球代碼采蚀,對(duì)于中國大陸用戶疲牵,請(qǐng)將其設(shè)置為 cn。 -
--image-repository=registry.cn-hangzhou.aliyuncs.com/google_containers
:設(shè)置用來拉取 Kubernetes 集群所需鏡像的倉庫榆鼠,如果無法訪問gcr.io
可以設(shè)置為 "auto" 讓minikube 為你自動(dòng)選擇可以訪問的鏡像倉庫纲爸。對(duì)于中國大陸用戶可以設(shè)置registry.cn-hangzhou.aliyuncs.com/google_containers
,但是我設(shè)置此參數(shù)導(dǎo)致有的鏡像無法拉取妆够。
說明:通過上面的命令啟動(dòng)minikube识啦,會(huì)出現(xiàn)有的鏡像無法拉取的問題,也就是說
registry.cn-hangzhou.aliyuncs.com/google_containers
鏡像倉庫很多鏡像不存在神妹,經(jīng)過不斷的測試颓哮,使用如下命令就可以正常啟動(dòng)并拉取鏡像,所有我們不需要設(shè)置這兩個(gè)參數(shù):--image-mirror-country=cn
和--image-repository=registry.cn-hangzhou.aliyuncs.com/google_containers
成功啟動(dòng)minikube的命令如下:
minikube start --driver=hyperv --registry-mirror=https://registry.docker-cn.com,https://shraym0v.mirror.aliyuncs.com --embed-certs=true
5. 驗(yàn)證minikube
使用如下命令查看minikube的狀態(tài)
C:\WINDOWS\system32>minikube status
minikube
type: Control Plane
host: Running
kubelet: Running
apiserver: Running
kubeconfig: Configured
timeToStop: Nonexistent
# 這里會(huì)自動(dòng)下載kubectl工具
C:\WINDOWS\system32>minikube kubectl get node
NAME STATUS ROLES AGE VERSION
minikube Ready control-plane,master 11m v1.20.2
部署一個(gè)nginx鸵荠,快速體驗(yàn)minikube
C:\WINDOWS\system32>kubectl create deployment nginx --image=nginx
deployment.apps/nginx created
C:\WINDOWS\system32>kubectl get pod
NAME READY STATUS RESTARTS AGE
nginx-6799fc88d8-z7xzh 1/1 Running 0 33s
C:\WINDOWS\system32>kubectl expose deployment nginx --type=NodePort --port=80
service/nginx exposed
C:\WINDOWS\system32>minikube service nginx
|-----------|-------|-------------|----------------------------|
| NAMESPACE | NAME | TARGET PORT | URL |
|-----------|-------|-------------|----------------------------|
| default | nginx | 80 | http://172.23.130.60:31593 |
|-----------|-------|-------------|----------------------------|
* 正通過默認(rèn)瀏覽器打開服務(wù) default/nginx...
C:\WINDOWS\system32>
會(huì)自動(dòng)打開默認(rèn)瀏覽器冕茅,如下圖所示:
使用如下命令啟動(dòng)k8s的dashboard
C:\WINDOWS\system32>minikube dashboard
* 正在開啟 dashboard ...
- Using image kubernetesui/dashboard:v2.1.0
- Using image kubernetesui/metrics-scraper:v1.0.4
* 正在驗(yàn)證 dashboard 運(yùn)行情況 ...
* Launching proxy ...
* 正在驗(yàn)證 proxy 運(yùn)行狀況 ...
* Opening http://127.0.0.1:61589/api/v1/namespaces/kubernetes-dashboard/services/http:kubernetes-dashboard:/proxy/ in your default browser...
如下圖所示:
三、安裝jenkins
我這里使用yaml
的方式部署jenkins蛹找,并且創(chuàng)建pv和pvc來持久化jenkins的數(shù)據(jù)姨伤,所有創(chuàng)建三個(gè)文件:
-
jenkins-pvc.yaml
:設(shè)置jenkins數(shù)據(jù)持久化方式。 -
jenkins-rbac.yaml
:設(shè)置jenkins用戶訪問權(quán)限庸疾。 -
jenkins-deploy.yaml
:創(chuàng)建jenkins的deployment 和 service乍楚。
jenkins-pvc.yaml
文件內(nèi)容如下:
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: jenkins-pvc
namespace: devops
spec:
accessModes:
- ReadWriteMany
# 如果集群中有一個(gè)默認(rèn)的storageClass能滿足需求,這里可以不用配置storageClass
storageClassName: standard
resources:
requests:
storage: 5Gi
說明:因?yàn)槭褂胢inikube創(chuàng)建的k8s集群默認(rèn)已經(jīng)創(chuàng)建了一個(gè)基于
hostpath
的storageClass
届慈,通過如下命令查看C:\windows\system32>kubectl get sc NAME PROVISIONER RECLAIMPOLICY VOLUMEBINDINGMODE >ALLOWVOLUMEEXPANSION AGE standard (default) k8s.io/minikube-hostpath Delete Immediate false 98m
storageClass會(huì)自動(dòng)創(chuàng)建pv徒溪,并將pv和pvc進(jìn)行綁定忿偷,所以我們無需自己創(chuàng)建pv。
jenkins-rbac.yaml
文件內(nèi)容如下:
apiVersion: v1
kind: ServiceAccount
metadata:
name: jenkins-sa
namespace: devops
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
name: jenkins-cr
rules:
- apiGroups: ["extensions", "apps"]
resources: ["deployments"]
verbs: ["create", "delete", "get", "list", "watch", "patch", "update"]
- apiGroups: [""]
resources: ["services"]
verbs: ["create", "delete", "get", "list", "watch", "patch", "update"]
- apiGroups: [""]
resources: ["pods"]
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"]
verbs: ["get"]
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
name: jenkins-crd
roleRef:
kind: ClusterRole
name: jenkins-cr
apiGroup: rbac.authorization.k8s.io
subjects:
- kind: ServiceAccount
name: jenkins-sa
namespace: devops
jenkins-deploy.yaml
文件內(nèi)容如下:
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: jenkins
namespace: devops
spec:
replicas: 1
selector:
matchLabels:
app: jenkins
template:
metadata:
labels:
app: jenkins
spec:
terminationGracePeriodSeconds: 10
serviceAccount: jenkins-sa
containers:
- name: jenkins
image: jenkins/jenkins:latest
imagePullPolicy: IfNotPresent
env:
- name: JAVA_OPTS
value: -Duser.timezone=Asia/Shanghai
ports:
- containerPort: 8080
name: web
protocol: TCP
- containerPort: 50000
name: agent
protocol: TCP
resources:
limits:
cpu: 1000m
memory: 1Gi
requests:
cpu: 500m
memory: 512Mi
livenessProbe:
httpGet:
path: /login
port: 8080
initialDelaySeconds: 60
timeoutSeconds: 5
failureThreshold: 12
readinessProbe:
httpGet:
path: /login
port: 8080
initialDelaySeconds: 60
timeoutSeconds: 5
failureThreshold: 12
volumeMounts:
- name: jenkinshome
mountPath: /var/jenkins_home
volumes:
- name: jenkinshome
persistentVolumeClaim:
claimName: jenkins-pvc
---
apiVersion: v1
kind: Service
metadata:
name: jenkins
namespace: devops
labels:
app: jenkins
spec:
selector:
app: jenkins
type: NodePort
ports:
- name: web
port: 8080
targetPort: web
---
apiVersion: v1
kind: Service
metadata:
name: jenkins-agent
namespace: devops
labels:
app: jenkins
spec:
selector:
app: jenkins
type: ClusterIP
ports:
- name: agent
port: 50000
targetPort: agent
使用下面的命令部署jenkins
- 創(chuàng)建devops命名空間
C:\WINDOWS\system32>kubectl create namespace devops
namespace/devops created
- 執(zhí)行下面的命令啟動(dòng)jenkins
kubectl apply -f jenkins-pvc.yaml
kubectl apply -f jenkins-rbac.yaml
kubectl apply -f jenkins-deploy.yaml
- 使用minikube service命令提供瀏覽器訪問地址
C:\WINDOWS\system32>minikube service jenkins -n devops
|-----------|---------|-------------|----------------------------|
| NAMESPACE | NAME | TARGET PORT | URL |
|-----------|---------|-------------|----------------------------|
| devops | jenkins | web/8080 | http://172.23.130.60:30002 |
|-----------|---------|-------------|----------------------------|
* 正通過默認(rèn)瀏覽器打開服務(wù) devops/jenkins...
- 使用如下命令查看登錄jenkins的初始密碼
C:\WINDOWS\system32>kubectl get pod -n devops
NAME READY STATUS RESTARTS AGE
jenkins-6bb66dcf88-2c4tv 1/1 Running 0 9m59s
C:\WINDOWS\system32>kubectl logs -f jenkins-6bb66dcf88-2c4tv -n devops
查看jenkins初始密碼如下圖:
選擇自定義插件安裝臊泌,因?yàn)榛厝ス倬W(wǎng)下載插件鲤桥,下載比較慢,而且很多插件我們不需要
取消推薦插件的選擇
創(chuàng)建一個(gè)管理員賬號(hào)
開始使用jenkins
安裝如下插件
四缺虐、在jenkins中配置k8s實(shí)現(xiàn)CI/CD
1. k8s相關(guān)配置
-
選擇 [節(jié)點(diǎn)管理] -> [Configure Clouds]
-
安裝了kubernetes插件就可看到下圖所示,添加一個(gè)kubernetes的cloud
-
配置連接k8s的api server
-
創(chuàng)建pod template
-
添加第一個(gè)容器 jnlp(jnlp-slave)
-
添加第二個(gè)容器 docker(因?yàn)橐趐ipeline中構(gòu)建鏡像礁凡,需要使用docker客戶端高氮,此鏡像提供了docker客戶端)
-
添加第三個(gè)容器 maven (這里使用的鏡像為:registry.cn-beijing.aliyuncs.com/acs-sample/jenkins-slave-maven:3.3.9-jdk-8-alpine, 也可以使用自定義的maven鏡像)
pod 模板的數(shù)據(jù)卷的設(shè)置顷牌,如下圖所示:
創(chuàng)建docker推送鏡像到私用倉庫的secret
命令如下:kubectl create secret generic my-secret --from-file=/root/.docker/config.json
注意: 這里不是
kubectl create secret docker-registry my-secret --docker-server=DOCKER_REGISTRY_SERVER --docker-username=DOCKER_USER --docker-password=DOCKER_PASSWORD --docker-email=DOCKER_EMAIL
這里遇到一個(gè)問題剪芍,docker 無法推送鏡像,報(bào)錯(cuò)顯示docker沒有登錄私有倉庫窟蓝,查詢?cè)虬l(fā)現(xiàn)因?yàn)槲沂褂胐ocker-registry創(chuàng)建了my-secret罪裹,當(dāng)我改為generic就可以了,詳細(xì)信息可以查看k8s的secret說明文檔运挫。
-
[Manage Credentials] -> [jenkins] -> [全局憑據(jù)] -> [添加憑據(jù)]
配置訪問k8s的kubeconfig状共,在pipeline中使用kubernetesDeploy
的時(shí)候會(huì)使用到
-
[Manage Credentials] -> [jenkins] -> [全局憑據(jù)] -> [添加憑據(jù)]
設(shè)置登錄私有鏡像倉庫的用戶名和密碼
五、使用jenkins CI/CD demo演示
-
新建一個(gè)任務(wù) devops-demo
-
devops-demo任務(wù)配置如下:
1谁帕、指定docker私有倉庫地址
2峡继、指定項(xiàng)目名稱
3、指定要部署的命名空間
4匈挖、選擇構(gòu)建的分支
5碾牌、任務(wù)流水線配置
說明: 這里使用的倉庫代碼示例地址如下:https://gitee.com/peterwd/devops-demo.git
在倉庫中需要添加三個(gè)文件才能實(shí)現(xiàn)此devops流程:Jenkinsfile、Dockerfile儡循、deployment.yaml
文件的內(nèi)容可以點(diǎn)擊到倉庫中查看舶吗。
-
保存配置并構(gòu)建如下圖所示
-
構(gòu)建成功的效果如下
這里打包階段用時(shí)比較長,那是因?yàn)槊看螛?gòu)建都需要下載依賴择膝,因?yàn)閟lave運(yùn)行完成就會(huì)被銷毀誓琼,默認(rèn)下載的依賴就在slave容器中,會(huì)隨著slave容器的銷毀而消失肴捉,所以我們應(yīng)該把下載的依賴持久化下來踊赠,下面介紹如何實(shí)現(xiàn):
1、將下載的依賴持久化到宿主機(jī)每庆,使用如下方式配置:
在maven容器中筐带,默認(rèn)將依賴包放在/root/.m2/repository
目錄下面,所以我們可以將宿主機(jī)的指定目錄掛載到此目錄中:
再次構(gòu)建可以通過如下方式登錄到宿主機(jī)查看下載的依賴已經(jīng)持久化到宿主機(jī)對(duì)應(yīng)的目錄中:
# 登錄到minikube節(jié)點(diǎn)中
C:\windows\system32>minikube ssh
_ _
_ _ ( ) ( )
___ ___ (_) ___ (_)| |/') _ _ | |_ __
/' _ ` _ `\| |/' _ `\| || , < ( ) ( )| '_`\ /'__`\
| ( ) ( ) || || ( ) || || |\`\ | (_) || |_) )( ___/
(_) (_) (_)(_)(_) (_)(_)(_) (_)`\___/'(_,__/'`\____)
$ cd /tmp/maven/repository/
$ ls -al
total 0
drwxr-xr-x 16 root root 320 Mar 15 10:25 .
drwxr-xr-x 3 root root 60 Mar 15 10:21 ..
drwxr-xr-x 3 root root 60 Mar 15 10:24 backport-util-concurrent
drwxr-xr-x 3 root root 60 Mar 15 10:22 ch
drwxr-xr-x 3 root root 60 Mar 15 10:23 classworlds
drwxr-xr-x 5 root root 100 Mar 15 10:24 com
drwxr-xr-x 3 root root 60 Mar 15 10:23 commons-cli
drwxr-xr-x 3 root root 60 Mar 15 10:25 commons-codec
drwxr-xr-x 3 root root 60 Mar 15 10:25 commons-lang
drwxr-xr-x 4 root root 80 Mar 15 10:25 commons-logging
drwxr-xr-x 8 root root 160 Mar 15 10:22 io
drwxr-xr-x 3 root root 60 Mar 15 10:22 jakarta
drwxr-xr-x 3 root root 60 Mar 15 10:23 junit
drwxr-xr-x 3 root root 60 Mar 15 10:24 log4j
drwxr-xr-x 3 root root 60 Mar 15 10:25 net
drwxr-xr-x 13 root root 260 Mar 15 10:23 org
$
2缤灵、使用pvc 持久化mave的依賴包伦籍,進(jìn)行如下圖所示配置:
-
持久化maven依賴包蓝晒,再次構(gòu)建耗時(shí)對(duì)比如下:
遇到的問題
1. minikube啟動(dòng)失敗
* 正在 Docker 20.10.3 中準(zhǔn)備 Kubernetes v1.20.2…| E0313 13:19:52.379165 33644 start.go:99] Unable to get host IP: No virtual switch found
X Exiting due to GUEST_START: Failed to setup kubeconfig: No virtual switch found
如下圖所示:
出現(xiàn)錯(cuò)誤的原因
第一次由于電腦內(nèi)存不足導(dǎo)致安裝失敗,再次啟動(dòng)minikube時(shí)報(bào)出此錯(cuò)誤帖鸦。
解決方式
執(zhí)行如下命令芝薇,刪除所有minikube集群,再重新啟動(dòng)即可恢復(fù)正常:
minikube delete --all
2. jenkins插件下載失敗
部分插件由于缺少依賴無法加載作儿。要恢復(fù)這些插件提供的功能洛二,需要修復(fù)這些問題并重啟 Jenkins。
Dependency errors:
SSH Credentials Plugin (1.18.2)
Jenkins (2.282) or higher required
由于一個(gè)或者多個(gè)上面的錯(cuò)誤導(dǎo)致這些插件無法加載攻锰。修復(fù)后插件將會(huì)再次加載晾嘶。
解決方式
升級(jí)jenkins版本為提示的版本,可以直接修改
jenkins-deploy.yaml
文件中的image: jenkins/jenkins:latest
為image: jenkins/jenkins:2.283
參考文章
minikube快速搭建k8s
kubernetes中部署Jenkins并簡單使用
Jenkins 和 Kubernetes -云上的神秘代理
k8s學(xué)習(xí)筆記之StorageClass+NFS