当您需要等到深夜才能在生产中部署您的应用程序时,情况会更糟,因为当部署后发生短暂的停机时间时,您害怕破坏用户的体验。
经过漫长的工作日后,您应该睡个好觉,所以让我们找出解决方案。
对于正常的应用,我们只需要做 3 个简单的步骤:
- 定义就绪探测
- 添加容器生命周期 preStop 挂钩
- 收听 SIGTERM 信号
定义就绪探测
kubelet 在您的容器运行后发送请求,但您的应用程序可能还没有准备好接收请求。如何告诉 kubelet 等到您的应用程序准备好或在您的应用程序关闭时停止发送请求。答案是 就绪探测,让我们查看您的部署的示例配置:
...
containers:
- name: my_web_app
readinessProbe:
httpGet:
path: /health # your health check api
port: 8080 # your container port
initialDelaySeconds: 5 # delay 5s before send first request to check
periodSeconds: 2 # send check request every 2s
successThreshold: 1 # success when the response has a status code greater than or equal to 200 and less than 400
failureThreshold: 1 # otherwise failure
...
添加容器生命周期 preStop 挂钩
您应该等待 15 秒,让 kubelet 更新路由以将请求发送到另一个 pod。默认情况下,k8s 在强制杀死你的应用程序之前等待 30 秒,所以你应该使用带有选项的 preStop
钩子: terminationGracePeriodSeconds
...
terminationGracePeriodSeconds: 60 # wait 60 seconds before force killing your app, increase it if you need more time
containers:
- name: my_web_app
...
lifecycle:
preStop:
exec:
command: ["/bin/sh", "-c", "sleep 15"] # sleep 15 seconds before sending SIGTERM to container and let kubelet update routing
...
收听 SIGTERM 信号
最后,听 SIGTERM 信号完成当前请求,关闭你的应用程序和关闭数据库连接等。这是一个 golang 示例:
...
quit := make(chan os.Signal)
signal.Notify(quit, os.Interrupt, syscall.SIGTERM)
<-quit // blocks util receive signal
// finish current requests
// close DB connection
// shutdown app
如何测试?
您可以安装 HTTP 测试工具,如 vegeta以及 jq以在终端中格式化报告
示例命令:
jq -ncM 'while(true; .+1) | {method: "GET", url: "http://localhost:30000?delay=5"}' | \
vegeta attack -rate=200/s -lazy -format=json -duration=30s | \
tee results.bin | \
vegeta report
my_web_app
然后通过以下命令触发强制 k8s 更新部署:
kubectl patch deployment my_web_app -p \
"{\"spec\":{\"template\":{\"metadata\":{\"annotations\":{\"date\":\"`date +'%s'`\"}}}}}"
您可能会收到这份报告:
Requests [total, rate, throughput] 3000, 100.03, 99.05
Duration [total, attack, wait] 30.287s, 29.99s, 297.897ms
Latencies [min, mean, 50, 90, 95, 99, max] 198.877ms, 363.615ms, 309.861ms, 381.551ms, 802.951ms, 1.988s, 2.692s
Bytes In [total, mean] 71244000, 23748.00
Bytes Out [total, mean] 0, 0.00
Success [ratio] 100.00%
Status Codes [code:count] 200:3000
Error Set:
结论
我希望你能找到一些有用的东西来简化你的日常部署任务。
参考