Deployment是kubernetes在1.2版本中引入的新概念,用於更好的解決Pod的編排問題,為此,Deployment在內部使用了ReplicaSet來實現目的,我們可以把Deployment理解為ReplicaSet的一次升級,兩者的相似度超過90%

Deployment的使用場景有以下幾個:
- 創建一個Deployment對象來生成對應的ReplicaSet並完成Pod副本的創建
- 檢查Deployment的狀態來看部署動作是否完成(Pod副本數量是否達到了預期的值)
- 更新Deployment以創建新的Pod(比如鏡像升級)
- 如果當前Deployment不穩定,可以回滾到一個早先的Deployment版本
- 暫停Deployment以便於一次性修改多個PodTemplateSpec的配置項,之后在恢復Deployment,進行新的發布
- 擴展Deployment以應對高負載
- 查看Deployment的狀態,以此作為發布是否成功的標志
- 清理不在需要的舊版本ReplicaSet
詳細信息
kubectl explain deploy
kubectl explain deploy.spec
kubectl explain deploy.spec.template.spec
部署
deploymentdemo.yml
apiVersion: apps/v1
kind: Deployment
metadata:
name: deploymentdemo1
labels:
app: deploymentdemo1
spec:
replicas: 10
template:
metadata:
name: deploymentdemo1
labels:
app: deploymentdemo1
spec:
containers:
- name: deploymentdemo1
image: nginx:1.17.10-alpine
imagePullPolicy: IfNotPresent
ports:
- containerPort: 80
restartPolicy: Always
selector:
matchLabels:
app: deploymentdemo1
運行
kubectl apply -f deploymentdemo.yml
查看deployment
kubectl get rs
查看rs:deployment名稱+hashcode碼組成
查看pod
kubectl get pod
鏡像更新升級
命令行方式
升級nginx鏡像版本為1.18.0
kubectl set image deployment deploymentdemo1 deploymentdemo1=nginx:1.18.0-alpine
查看pod升級情況
kubectl get pods -w
進去某一個pod內部,查看nginx升級版本信息
kubectl exec -it deploymentdemo1-df6bc5d4c-flc7b sh
nginx -v
exit
yml文件方式
升級nginx鏡像版本為1.19.2-alpine
kubectl edit deployments.apps deploymentdemo1
查看pod升級情況
kubectl get pods -w
進去某一個pod內部,查看nginx升級版本信息
kubectl exec -it deploymentdemo1-584f6b54dd-4l62t sh
nginx -v
exit
Deployment擴容
命令行方式
kubectl scale deployment deploymentdemo1 --replicas=15
kubectl get pods
yml文件方式
kubectl edit deployments.apps deploymentdemo1
kubectl get pods
滾動更新
微服務部署:藍綠部署、滾動部署、灰度發布、金絲雀發布
- 藍綠部署是不停老版本,部署新版本然后進行測試,確認OK,將流量切到新版本,然后老版本同時也升級到新版本。 藍綠部署無需停機,並且風險較小。
- 滾動發布:一般是取出一個或者多個服務器停止服務,執行更新,並重新將其投入使用。周而復始,直到集群中所有的實例都更新成新版本。 這種部署方式相對於藍綠部署,更加節約資源,它不需要運行兩個集群、兩倍的實例數。我們可以部分部署,例如每次只取出集群的20%進行升級。
- 灰度發布是指在黑與白之間,能夠平滑過渡的一種發布方式。AB test就是一種灰度發布方式,讓一部分用戶繼續用A,一部分用戶開始用B,如果用戶對B沒有什么反對意見,那么逐步擴大范圍,把所有用戶都遷移到B上面來。灰度發布可以保證整體系統的穩定,在初始灰度的時候就可以發現、調整問題,以保證其影響度,而我們平常所說的金絲雀部署也就是灰度發布的一種方式。
- 金絲雀發布:Deployment控制器支持自定義控制更新過程中的滾動節奏,如“暫停(pause)”或“繼續(resume)”更新操作。比如等待第一批新的Pod資源創建完成后立即暫停更新過程,此時,僅存在一部分新版本的應用,主體部分還是舊的版本。然后,再篩選一小部分的用戶請求路由到新版本的Pod應用,繼續觀察能否穩定地按期望的方式運行。確定沒問題之后再繼續完成余下的Pod資源滾動更新,否則立即回滾更新操作。這就是所謂的金絲雀發布(Canary Release)
更新deployment的nginx:1.18.0-alpine版本,並配置暫停deployment
kubectl set image deployment deploymentdemo1 deploymentdemo1=nginx:1.18.0-alpine && kubectl rollout pause deployment deploymentdemo1
觀察更新狀態
kubectl rollout status deployments deploymentdemo1
監控更新的過程,可以看到已經新增了一個資源,但是並未按照預期的狀態去刪除一個舊的資源,就是因為使用了pause暫停命令
kubectl get pods -l app=deploymentdemo1 -w
確保更新的pod沒問題了,繼續更新
kubectl rollout resume deploy deploymentdemo1
查看最后的更新情況
kubectl get pods -l app=deploymentdemo1 -w
進去某一個pod內部,查看nginx更新版本信息
kubectl exec -it deploymentdemo1-df6bc5d4c-flc7b sh
nginx -v
Deployment版本回退
默認情況下,kubernetes 會在系統中保存前兩次的 Deployment 的 rollout 歷史記錄,以便可以隨時回退(可以修改 revision history limit 來更改保存的revision數)。
注意:只要 Deployment 的 rollout 被觸發就會創建一個 revision。也就是說當且僅當Deployment 的 Pod template(如.spec.template )被更改,例如更新template 中的 label 和容器鏡像時,就會創建出一個新的 revision。
其他的更新,比如擴容 Deployment 不會創建 revision,因此可以很方便的手動或者自動擴容。這意味着當回退到歷史 revision時,只有 Deployment 中的 Pod template 部分才會回退。
rollout常見命令
| 子命令 | 功能說明 |
|---|---|
| history | 查看rollout操作歷史 |
| pause | 將提供的資源設定為暫停狀態 |
| restart | 重啟某資源 |
| resume | 將某資源從暫停狀態恢復正常 |
| status | 查看rollout操作狀態 |
| undo | 回滾前一rollout |
history操作
kubectl rollout history deployment deploymentdemo1
status操作
kubectl rollout status deployment deploymentdemo1
undo操作
回滾版本信息
kubectl rollout undo deployment deploymentdemo1
查看pod回滾情況
kubectl get pods -w
進去某一個pod內部,查看nginx回滾版本信息
kubectl exec -it deploymentdemo1-df6bc5d4c-flc7b sh
nginx -v
Deployment 更新策略
Deployment 可以保證在升級時只有一定數量的 Pod 是 down 的。默認的,它會確保至少有比期望的Pod數量少
一個是up狀態(最多一個不可用)
Deployment 同時也可以確保只創建出超過期望數量的一定數量的 Pod。默認的,它會確保最多比期望
的Pod數量多一個的 Pod 是 up 的(最多1個 surge )
Kuberentes 版本v1.17.5中,從1-1變成25%-25%
kubectl describe deployments.apps deploymentdemo1
查看到屬性:
RollingUpdateStrategy: 25% max unavailable, 25% max surge
總結
Deployment為Pod和Replica Set(下一代Replication Controller)提供聲明式更新。只需要在 Deployment 中描述想要的目標狀態是什么,Deployment controller 就會幫您將 Pod 和ReplicaSet 的實際狀態改變到您的目標狀態。也可以定義一個全新的 Deployment 來創建 ReplicaSet或者刪除已有的 Deployment 並創建一個新的來替換。
Replicas(副本數量):
.spec.replicas 是可以選字段,指定期望的pod數量,默認是1。
Selector(選擇器):
.spec.selector是可選字段,用來指定 label selector ,圈定Deployment管理的pod范圍。如果被指定, .spec.selector 必須匹配 .spec.template.metadata.labels,否則它將被API拒絕。如果.spec.selector 沒有被指定, .spec.selector.matchLabels 默認是.spec.template.metadata.labels。
在Pod的template跟.spec.template不同或者數量超過了.spec.replicas規定的數量的情況下,Deployment會殺掉label跟selector不同的Pod。
Pod Template(Pod模板):
.spec.template 是 .spec中唯一要求的字段。
.spec.template 是 pod template. 它跟 Pod有一模一樣的schema,除了它是嵌套的並且不需要apiVersion 和 kind字段。
另外為了划分Pod的范圍,Deployment中的pod template必須指定適當的label(不要跟其他controller重復了,參考selector)和適當的重啟策略。
.spec.template.spec.restartPolicy 可以設置為 Always , 如果不指定的話這就是默認配置。
strategy(更新策略):
.spec.strategy 指定新的Pod替換舊的Pod的策略。 .spec.strategy.type 可以是"Recreate"或者是"RollingUpdate"。"RollingUpdate"是默認值。
-
Recreate: 重建式更新,就是刪一個建一個。類似於ReplicaSet的更新方式,即首先刪除現有的Pod對象,然后由控制器基於新模板重新創建新版本資源對象。
-
rollingUpdate:滾動更新,簡單定義 更新期間pod最多有幾個等。可以指定 maxUnavailable和 maxSurge 來控制 rolling update 進程。
-
maxSurge:
.spec.strategy.rollingUpdate.maxSurge是可選配置項,用來指定可以超過期望的Pod數量的最大個數。該值可以是一個絕對值(例如5)或者是期望的Pod數量的百分比(例如10%)。當 MaxUnavailable 為0時該值不可以為0。通過百分比計算的絕對值向上取整。默認值是1。例如,該值設置成30%,啟動rolling update后新的ReplicatSet將會立即擴容,新老Pod的總數不能超過期望的Pod數量的130%。舊的Pod被殺掉后,新的ReplicaSet將繼續擴容,舊的ReplicaSet會進一步縮容,確保在升級的所有時刻所有的Pod數量和不會超過期望Pod數量的130%。
-
maxUnavailable:
.spec.strategy.rollingUpdate.maxUnavailable是可選配置項,用來指定在升級過程中不可用Pod的最大數量。該值可以是一個絕對值(例如5),也可以是期望Pod數量的百分比(例如10%)。通過計算百分比的絕對值向下取整。 如果 .spec.strategy.rollingUpdate.maxSurge 為0時,這個值不可以為0。默認值是1。例如,該值設置成30%,啟動rolling update后舊的ReplicatSet將會立即縮容到期望的Pod數量的70%。新的Pod ready后,隨着新的ReplicaSet的擴容,舊的ReplicaSet會進一步縮容確保在升級的所有時刻可以用的Pod數量至少是期望Pod數量的70%。
rollbackTo:
.spec.rollbackTo 是一個可以選配置項,用來配置Deployment回退的配置。設置該參數將觸發回退操作,每次回退完成后,該值就會被清除。
- revision:
.spec.rollbackTo.revision是一個可選配置項,用來指定回退到的revision。默認是0,意味着回退到上一個revision。
progressDeadlineSeconds:
.spec.progressDeadlineSeconds 是可選配置項,用來指定在系統報告Deployment的failed progressing——表現為resource的狀態中 type=Progressing 、 Status=False 、
Reason=ProgressDeadlineExceeded 前可以等待的Deployment進行的秒數。Deployment controller會繼續重試該Deployment。未來,在實現了自動回滾后, deployment controller在觀察到這種狀態時就會自動回滾。
如果設置該參數,該值必須大於 .spec.minReadySeconds 。
paused:
.spec.paused 是可以可選配置項,boolean值。用來指定暫停和恢復Deployment。Paused和沒有paused的Deployment之間的唯一區別就是,所有對paused deployment中的PodTemplateSpec的修改都不會觸發新的rollout。Deployment被創建之后默認是非paused。
