寫在前面
在這用XMind畫了一張導圖記錄Redis的學習筆記和一些面試解析(原始檔對部分節點有詳細備註和參考資料,歡迎關注我的公眾號:阿風的架構筆記 後臺傳送【導圖】拿下載連結, 已經完善更新):
前言
在上一篇文章中介紹了K8S的基礎架構流程,以及核心的元件;這篇文章繼續K8S的相關的概念。
上篇介紹到了NodePort Service解決了外部請求K8S內部的應用的問題。下面我們看看如何搭建應用服務叢集的?
應用叢集
在傳統應用中,我們一般利用nginx反向代理,通過配置域名指向多個IP地址,從而實現了應用的叢集。如果需要增加應用或減少應用,都需要調整nginx的配置;還是相當繁瑣的。
那K8S是如何實現應用叢集的呢?
副本集ReplicaSet
上一篇文章中介紹了利用NodePort Service 的Selector 選擇Label標籤,路由到後端的其中一個Pod。
上圖中由3個Pod組成的應用叢集,那如何保證Pod叢集的高可用呢?如果其中一個Pod掛了,被刪除了,K8S會怎麼處理?
K8S有個Replica Set元件,從字面上面來看就是副本集意思;它的作用就是用來保證Pod的高可用,如果我們在Replica Set中定義了應用數量為3,那麼它會保證應用數量;即使一個pod掛了,它會自動會啟動1個,始終保證pod應用數量為3。
編寫yaml
apiVersion: extensions/v1beta1 #指定api版本
kind: ReplicaSet #指定建立資源的角色/型別
metadata:
name: mc-user
spec:
replicas: 3 #副本集數量
template: #pod模板
metadata: #資源的後設資料/屬性
labels: #標籤定義
app: mc-user #標籤值
spec: # 指定該資源的內容
containers: #容器定義
- name: mc-user #容器的名字
image: rainbow/mc-user:1.0.RELEASE #容器映象
上面就是定義了 mc-user的pod,副本集數始終為3。Service的yaml和之前一樣,注意Selector的Label,可提供給外部訪問埠31001
apiVersion: v1
kind: Service
metadata:
name: mc-user
spec:
ports:
- name: http
port: 8080
targetPort: 8080
nodePort: 31001
selector:
app: mc-user
type: NodePort
執行kubectl apply -f 命令,啟動ReplicaSet和Service
我們可以試著檢視啟動的3個pod,並選擇其中一個pod將它刪除。
# kubectl get all
# kubectl delete po mc-user-6adfw
我們再檢視pod
kubectl get all
還是有3個pod,可以看出即使刪除了一個pod;ReplicaSet會又幫我們啟動了一個pod。
這個就是ReplicaSet的自愈能力,自我恢復能力。
滾動釋出Rolling Update
我們先來談談什麼是滾動釋出?滾動釋出是一種高階釋出策略,按批次依次替換老版本,逐步升級到新版本。釋出過程中,應用不中斷,使用者體驗平滑。
現在Pod中是V1的版本,現在我們想升級到V2版本,整個流程是什麼樣子呢?
先刪除其中一個V1的pod
然後釋出V2的Pod
再刪除一個V1的pod
再啟動一個V2的Pod
再刪除最後一個V1的pod
最終升級完成。
我們可以發現滾動釋出的特點,就是老版本和新版本會共存一段時間。所以此種釋出方式適用版本相容的應用。也可以支援滾動回退。我們來看看和藍綠髮布的區別
滾動釋出抽象Deployment
之前介紹的ReplicaSet 其實是對Pod的一次包裝,Deployment又在基礎上面對ReplicaSet的又一次包裝。
注意點:ReplicaSet 和 Deployment是一個軟體概念,它是沒有具體的元件的;是抽象出來的名詞,方便大家理解
上圖就是描述了deployment滾動釋出的架構;Deployment的滾動釋出,對使用者請求以及Service是透明的,無感知。
Deployment的yaml
apiVersion: apps/v1 #指定api版本,此值必須在kubectl apiversion中
kind: Deployment #指定建立資源的角色/型別
metadata:
name: mc-user
spec:
selector: #此deployment選擇哪個標籤進行滾動的釋出
matchLabels: #滾動釋出pod的標籤,要跟下面template中的labels一致
app: mc-user
minReadySeconds: 10 #最小10s等待就緒時間,可以方便看到滾動釋出流程
replicas: 3 #副本集數量
template: #pod模板
metadata: #資源的後設資料/屬性
labels: #標籤定義
app: mc-user #標籤值
spec: #指定該資源的內容
containers: #容器定義
- name: mc-user #容器的名字
image: rainbow/mc-user:1.0.RELEASE #容器映象
上面的yaml和ReplicaSet很類似,需要注意的
selector: #此deployment選擇哪個標籤進行滾動的釋出
matchLabels: #滾動釋出pod的標籤,要跟下面template中的labels一致
app: mc-user
定義deployment管理哪個標籤pod
Service的yaml
Service的yaml沒有變化,需要定義selector,選擇標籤就行了
apiVersion: v1
kind: Service
metadata:
name: mc-user
spec:
ports:
- name: http
port: 8080
targetPort: 8080
nodePort: 31000
selector:
app: mc-user
type: NodePort
我們用kubectl apply -f命令執行 deployment和service
我們再用kubectl get all獲取執行情況,我們就可以發現有兩個型別
deployment.apps/mc-user 以及 replicaset.apps/mc-user-4345afaa
要升級的時候,只需要更改deployment中的image名稱,再執行apply
image: rainbow/mc-user:1.1.RELEASE #容器映象
我們用kubectl get all檢視,就會發現replicaset 有2個;一個是老版本的,一個是新版本的。 老版本的pod數逐漸減少,新版本的pod數量逐漸增加,一直到新版本為3,老版本為0。
回退版本
如果發現版本有問題,我們可以回退版本,可以使用下面命令
kubectl rollout undo deployment/mc-user
這個我們就回退到V1.0的老版本了。
ConfigMap配置
在我們日常業務過程中,需要會配置一些配置引數,如:一次性的靜態配置(資料庫連線字串,使用者名稱,密碼),以及可以執行過程中的動態配置(如:限購數量)等;那K8S中的Pod如何獲得外部的配置資訊呢?
上圖中,K8S提供了ConfigMap這個功能,提供使用者在外部進行配置,然後K8S把ConfigMap以環境變數的方式提供給Pod中的容器或者也可以通過Volume檔案持久化的方式提供給Pod容器。
共享配置
因為我們會有很多服務的配置是相同的,那實現微服務之間共享一份配置資訊,如下圖
一份ConfigMap可以提供給多個服務使用,ConfigMap會把配置資訊以env方式存在於每個服務的環境變數中。
ConfigMap的yaml
apiVersion: v1 #指定api版本,此值必須在kubectl apiversion中
kind: ConfigMap #指定建立資源的角色/型別
metadata:
name: mc-user-config
data: #定義配置資訊
DATASOURCE_URL: jdbc:mysql://mysql/mc-user
DATASOURCE_USERNAME: root
DATASOURCE_PASSWORD: 123456
修改Deployment配置檔案
增加envFrom屬性
apiVersion: apps/v1 #指定api版本,此值必須在kubectl apiversion中
kind: Deployment #指定建立資源的角色/型別
metadata:
name: mc-user
spec:
selector: #此deployment選擇哪個標籤進行滾動的釋出
matchLabels: #滾動釋出pod的標籤,要跟下面template中的labels一致
app: mc-user
minReadySeconds: 10 #最小10s等待就緒時間,可以方便看到滾動釋出流程
replicas: 3 #副本集數量
template: #pod模板
metadata: #資源的後設資料/屬性
labels: #標籤定義
app: mc-user #標籤值
spec: #指定該資源的內容
containers: #容器定義
- name: mc-user #容器的名字
image: rainbow/mc-user:1.0.RELEASE #容器映象
envFrom: #環境變數來源
- configMapRef: #容器應用的configmap引用
name: mc-user-config #configMap的名稱
envFrom中的configMapRef配置引用名稱;這樣我們就可以在pod容器中獲取到configmap的配置資訊了。我們可以用
kubectl exec mc-user-34wrwq-3423 printenv | grep DATASOURCE_NAME
獲得pod容器中的環境變數。
configMap變更
如果服務已經執行中,我們更新了ConfigMap的配置資訊,那麼POD中的容器會即時獲得新的配置資訊嗎?
很不幸,更新了configMap;再用kubectl apply -f 重新發布configmap;之前的pod容器是不會獲得最新的配置資訊的。
那如何讓pod容器用最新的ConfigMap配置值呢?我們可以刪除pod,因為replicaset會保證pod數量,會自動重啟,那新的pod就會應用新的配置資訊了。
總結
今天介紹K8S的副本集ReplicaSet、滾動釋出Deployment、配置ConfigMap的概念;下一篇會介紹網路相關的模型。謝謝!!!
看完三件事❤️
如果你覺得這篇內容對你還蠻有幫助,我想邀請你幫我三個小忙:
- 點贊,轉發,有你們的 『點贊和評論』,才是我創造的動力。
- 關注公眾號 『 阿風的架構筆記 』,不定期分享原創知識。
- 同時可以期待後續文章ing?
- 關注後回覆【666】掃碼即可獲取架構進階學習資料包