摘要:被設(shè)計為這樣一種方式,父進(jìn)程必須明確地等待子進(jìn)程終止,以便收集它的退出狀態(tài)。會完成的刪除,將優(yōu)雅退出的時間設(shè)置為表示立即刪除。
SIGINT SIGTERM SIGKILL區(qū)別
三者都是結(jié)束/終止進(jìn)程運行。
1.SIGINT SIGTERM區(qū)別前者與字符ctrl+c關(guān)聯(lián),后者沒有任何控制字符關(guān)聯(lián)。
前者只能結(jié)束前臺進(jìn)程,后者則不是。
前者可以被阻塞、處理和忽略,但是后者不可以。KILL命令的默認(rèn)不帶參數(shù)發(fā)送的信號就是SIGTERM.讓程序有好的退出。因為它可以被阻塞,所以有的進(jìn)程不能被結(jié)束時,用kill發(fā)送后者信號,即可。即:kill-9 進(jìn)程號。
docker stop與docker kill docker stop當(dāng)我們用docker stop命令來停掉容器的時候,docker默認(rèn)會允許容器中的應(yīng)用程序有10秒的時間用以終止運行。
在docker stop命令執(zhí)行的時候,會先向容器中PID為1的進(jìn)程(main process)發(fā)送系統(tǒng)信號SIGTERM,然后等待容器中的應(yīng)用程序終止執(zhí)行,如果等待時間達(dá)到設(shè)定的超時時間,或者默認(rèn)的10秒,會繼續(xù)發(fā)送SIGKILL的系統(tǒng)信號強(qiáng)行kill掉進(jìn)程。在容器中的應(yīng)用程序,可以選擇忽略和不處理SIGTERM信號,不過一旦達(dá)到超時時間,程序就會被系統(tǒng)強(qiáng)行kill掉,因為SIGKILL信號是直接發(fā)往系統(tǒng)內(nèi)核的,應(yīng)用程序沒有機(jī)會去處理它。
docker kill默認(rèn)情況下,docker kill命令不會給容器中的應(yīng)用程序有任何gracefully shutdown的機(jī)會。它會直接發(fā)出SIGKILL的系統(tǒng)信號,以強(qiáng)行終止容器中程序的運行。
與docker stop命令不一樣的地方在于,docker kill沒有任何的超時時間設(shè)置,它會直接發(fā)送SIGKILL信號,以及用戶通過signal參數(shù)指定的其他信號。
關(guān)于pid為1的進(jìn)程docker stop命令,更類似于Linux系統(tǒng)中的kill命令,二者都是發(fā)送系統(tǒng)信號SIGTERM。而docker kill命令,更像是Linux系統(tǒng)中的kill -9或者是kill -SIGKILL命令,用來發(fā)送SIGKILL信號,強(qiáng)行終止進(jìn)程。
process ID為1的進(jìn)程,通常是UNIX init進(jìn)程, 在操作系統(tǒng)中有重要的作用:每當(dāng)一個進(jìn)程退出了,如果它還有子進(jìn)程存在,則該子進(jìn)程變成了孤兒進(jìn)程,init進(jìn)程過來接管。Unix被設(shè)計為這樣一種方式,父進(jìn)程必須明確地“等待”子進(jìn)程終止,以便收集它的退出狀態(tài)。
子進(jìn)程在結(jié)束后,內(nèi)核仍然會為其維護(hù)一個基本的結(jié)構(gòu),保存其pid, 退出原因和狀態(tài)等信息,父進(jìn)程通過waitpid系統(tǒng)調(diào)用,可以獲得這些信息。如果父進(jìn)程沒有調(diào)用waitpid,這些狀態(tài)信息會一直保留,變成所謂僵尸進(jìn)程。如果子進(jìn)程后于父進(jìn)程結(jié)束,一般來說, init進(jìn)程會負(fù)責(zé)這些孤兒進(jìn)程。
根據(jù)一般一個容器只運行一個進(jìn)程的原則,對于一個web服務(wù),它在容器中運行時的pid是1,假設(shè)它調(diào)用了bash的cgi腳本,而這個腳本又調(diào)用了grep,一段時間后,cgi腳本因為某種原因超時,web服務(wù)開始嘗試殺死它,但是grep卻并未受到影響,因此變成了孤兒進(jìn)程。這時,pid=1的web服務(wù)應(yīng)該能接管,但是絕大多數(shù)的web服務(wù)并沒有init那樣的能力,所以grep就變成了僵尸進(jìn)程。
kubernetes的pod關(guān)閉機(jī)制pod代表著一個集群中節(jié)點上運行的進(jìn)程,讓這些進(jìn)程不再被需要,優(yōu)雅的退出是很重要的(與粗暴的用一個KILL信號去結(jié)束,讓應(yīng)用沒有機(jī)會進(jìn)行清理操作)。用戶應(yīng)該能請求刪除,并且在室進(jìn)程終止的情況下能知道,而且也能保證刪除最終完成。當(dāng)一個用戶請求刪除pod,系統(tǒng)記錄想要的優(yōu)雅退出時間段,在這之前Pod不允許被強(qiáng)制的殺死,TERM信號會發(fā)送給容器主要的進(jìn)程。一旦優(yōu)雅退出的期限過了,KILL信號會送到這些進(jìn)程,pod會從API服務(wù)器其中被刪除。如果在等待進(jìn)程結(jié)束的時候,Kubelet或者容器管理器重啟了,結(jié)束的過程會帶著完整的優(yōu)雅退出時間段進(jìn)行重試。
一個示例流程:
1.用戶發(fā)送一個命令來刪除Pod,默認(rèn)的優(yōu)雅退出時間是30秒
2.API服務(wù)器中的Pod更新時間,超過該時間Pod被認(rèn)為死亡
3.在客戶端命令的的里面,Pod顯示為"Terminating(退出中)"的狀態(tài)
4.(與第3同時)當(dāng)Kubelet看到Pod標(biāo)記為退出中的時候,因為第2步中時間已經(jīng)設(shè)置了,它開始pod關(guān)閉的流程
4.1如果該Pod定義了一個停止前的鉤子,其會在pod內(nèi)部被調(diào)用。如果鉤子在優(yōu)雅退出時間段超時仍然在運行,第二步會意一個很小的優(yōu)雅時間斷被調(diào)用
4.2進(jìn)程被發(fā)送TERM的信號
5.(與第三步同時進(jìn)行)Pod從service的列表中被刪除,不在被認(rèn)為是運行著的pod的一部分。緩慢關(guān)閉的pod可以繼續(xù)對外服務(wù),當(dāng)負(fù)載均衡器將他們輪流移除。
6.當(dāng)優(yōu)雅退出時間超時了,任何pod中正在運行的進(jìn)程會被發(fā)送SIGKILL信號被殺死。
7.Kubelet會完成pod的刪除,將優(yōu)雅退出的時間設(shè)置為0(表示立即刪除)。pod從API中刪除,不在對客戶端可見。
nginx與SIGTERM默認(rèn)情況下,所有的刪除操作的優(yōu)雅退出時間都在30秒以內(nèi)。kubectl delete命令支持--grace-period=的選項,以運行用戶來修改默認(rèn)值。0表示刪除立即執(zhí)行,并且立即從API中刪除pod這樣一個新的pod會在同時被創(chuàng)建。在節(jié)點上,被設(shè)置了立即結(jié)束的的pod,仍然會給一個很短的優(yōu)雅退出時間段,才會開始被強(qiáng)制殺死。
有兩種方式可以向正在運行的Nginx進(jìn)程的發(fā)送信號以完全管理操作:使用Nginx進(jìn)程的 -s 選項或者直接使用系統(tǒng)命令kill發(fā)送信號給master進(jìn)程。使用 -s 選項時,nginx會自動查找運行中的master進(jìn)程ID(master進(jìn)程負(fù)責(zé)接收并處理信號,同時根據(jù)不同的信號,對所有工作進(jìn)程完成不同的管理操作).
SIGINT和SIGTERM作用一樣,用于強(qiáng)制 Nginx進(jìn)程退出;master進(jìn)程接到強(qiáng)制退出信號時,會向所有工作進(jìn)程發(fā)送強(qiáng)制退出信號,如果工作進(jìn)程未能及時退出,master使用計時器重復(fù)發(fā)送強(qiáng)制信號,計時器觸發(fā)時會發(fā)送SIGALRM信號;SIGIO信號被Nginx顯式忽略;SIGCHLD信號告訴 master進(jìn)程有工作進(jìn)程退出,需要完成資源回收或者重啟工作進(jìn)程的工作。
Nginx進(jìn)程退出分為兩種master進(jìn)程接到SIGQUIT信號時
將此信號轉(zhuǎn)發(fā)給工作進(jìn)程。工作進(jìn)程隨后關(guān)閉監(jiān)聽端口以便不再接收新的連接請求,并閉空閑連接,等待活躍連接全部正常結(jié)速后,調(diào)用 ngx_worker_process_exit 退出。而 master 進(jìn)程在所有工作進(jìn)程都退出后,調(diào)用 ngx_master_process_exit 函數(shù)退出;
master進(jìn)程接收到SIGTERM或者SIGINT信號時
將信號轉(zhuǎn)發(fā)給工作進(jìn)程。工 作進(jìn)程直接調(diào)用 ngx_worker_process_exit 函數(shù)退出。master進(jìn)程在所有工作進(jìn)程都退出后,調(diào)用ngx_master_process_exit 函數(shù)退出。另外,如果工作進(jìn)程未能正常退出,master進(jìn)程會等待1秒后,發(fā)送SIGKILL信號強(qiáng)制終止工作進(jìn)程。
-s signal Send signal to the master process. The argument signal can be one of: stop, quit, reopen, reload. The following table shows the corresponding system signals. stop SIGTERM quit SIGQUIT reopen SIGUSR1 reload SIGHUP
其中
stop — 快速關(guān)閉
quit — 優(yōu)雅退出,執(zhí)行完當(dāng)前的請求后退出
reload — 重新加載配置文件
reopen — 重新打開日志文件
kind: Deployment metadata: name: nginx-demo namespace: scm labels: app: nginx-demo spec: replicas: 1 template: metadata: labels: app: nginx-demo spec: containers: - name: nginx-demo image: library/nginx-demo imagePullPolicy: IfNotPresent lifecycle: preStop: exec: # nginx -s quit gracefully terminate while SIGTERM triggers a quick exit command: ["/usr/local/openresty/nginx/sbin/nginx","-s","quit"] env: - name: PROFILE value: "test" ports: - name: http containerPort: 8080題外
如何優(yōu)雅地關(guān)閉java應(yīng)用
command: ["/bin/bash", "-c", "PID=`pidof java` && kill -SIGTERM $PID && while ps -p $PID > /dev/null; do sleep 1; done;"]doc
uinx 信號 SIGINT SIGTERM SIGKILL區(qū)別
優(yōu)雅的終止docker容器
Termination of Pods
Issues with running as PID 1 in a Docker container.
Docker and the PID 1 zombie reaping problem
Docker 和 PID 1 僵尸進(jìn)程問題
Docker系統(tǒng)中僵尸進(jìn)程問題
kubernetes-chinese-docs-pods
Nginx 源代碼筆記 - 運維命令
Does nginx have a soft quit?
Container Lifecycle Hooks
Graceful shutdown of pods with Kubernetes
Gracefully stopping a Java process in a pod in Kubernetes?
How can I ensure graceful scaling in kubernetes?
Do Kubernetes pods still receive requests after receiving SIGTERM?
Deleting pods and other resources with graceful shutdown
文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請注明本文地址:http://systransis.cn/yun/39447.html
摘要:被設(shè)計為這樣一種方式,父進(jìn)程必須明確地等待子進(jìn)程終止,以便收集它的退出狀態(tài)。會完成的刪除,將優(yōu)雅退出的時間設(shè)置為表示立即刪除。 SIGINT SIGTERM SIGKILL區(qū)別 三者都是結(jié)束/終止進(jìn)程運行。 1.SIGINT SIGTERM區(qū)別 前者與字符ctrl+c關(guān)聯(lián),后者沒有任何控制字符關(guān)聯(lián)。前者只能結(jié)束前臺進(jìn)程,后者則不是。 2.SIGTERM SIGKILL的區(qū)別 前者可以被...
摘要:假如我們先告訴網(wǎng)關(guān)或服務(wù)注冊中心我們要下線,等對方完成服務(wù)摘除操作再中止進(jìn)程,那不會有任何流量受到影響這是優(yōu)雅停止,將單個組件的啟停對整個系統(tǒng)影響最小化。與此同時,會將從對應(yīng)的上摘除。 作者:吳葉磊 一直以來我對優(yōu)雅地停止 Pod 這件事理解得很單純:不就利用是?PreStop hook?做優(yōu)雅退出嗎?但最近發(fā)現(xiàn)很多場景下 PreStop Hook 并不能很好地完成需求,這篇文章就簡單...
摘要:假如我們先告訴網(wǎng)關(guān)或服務(wù)注冊中心我們要下線,等對方完成服務(wù)摘除操作再中止進(jìn)程,那不會有任何流量受到影響這是優(yōu)雅停止,將單個組件的啟停對整個系統(tǒng)影響最小化。與此同時,會將從對應(yīng)的上摘除。 作者:吳葉磊 一直以來我對優(yōu)雅地停止 Pod 這件事理解得很單純:不就利用是?PreStop hook?做優(yōu)雅退出嗎?但最近發(fā)現(xiàn)很多場景下 PreStop Hook 并不能很好地完成需求,這篇文章就簡單...
摘要:既然要組集群那就涉及諸如的資源調(diào)度管理等等一系列問題。目前涉及集群的三個主要的技術(shù)無外乎三種。從本文開始作者將會一一實踐這幾種主要的集群技術(shù),話不多說,現(xiàn)在開始。完全運行于內(nèi)存中,體積小,啟動快。 showImg(https://segmentfault.com/img/remote/1460000015723680); 前言 相信Docker技術(shù)大家都有所了解,單個Docker能發(fā)...
閱讀 1061·2021-11-22 15:35
閱讀 1698·2021-10-26 09:49
閱讀 3240·2021-09-02 15:11
閱讀 2086·2019-08-30 15:53
閱讀 2642·2019-08-30 15:53
閱讀 2937·2019-08-30 14:11
閱讀 3536·2019-08-30 12:59
閱讀 3248·2019-08-30 12:53