實用技巧:Spring Cloud中,如何優雅下線微服務?

實用技巧:Spring Cloud中,如何優雅下線微服務?


在生產環境中,服務的上下線是不可避免的,我們希望能夠優雅地下線微服務。本文基於Spring Boot 2.x + Spring Cloud Finchley講解實際項目中優雅下線服務的四種方式,並探討各方式的優缺點。

:Spring Boot 1.x + Spring Cloud Edgware及之前的方式相同,但配置有區別,本文不做討論。


方式一:kill java進程【不建議】

使用方式:

kill java進程ID

該方式藉助的是Spring Boot應用的Shutdown hook,應用本身的下線也是優雅的,但如果你的服務發現組件使用的是Eureka,那麼默認最長會有90秒的延遲,其他應用才會感知到該服務下線,這意味著:該實例下線後的90秒內,其他服務仍然可能調用到這個已下線的實例。因此,該方式是不夠優雅的 。


方式二:/shutdown 端點【不建議】

Spring Boot提供了/shutdown 端點,可以藉助它實現優雅停機。使用方式:

在想下線應用的applicationyml 中添加如下配置,從而啟用並暴露/shutdown 端點:

management:
endpoint:
shutdown:
enabled: true
endpoints:
web:
exposure:
include: shutdown
  • 發送POST請求到/shutdown 端點
curl -X http://你想停止的服務地址/actuator/shutdown

該方式本質和方式一是一樣的,也是藉助Spring Boot應用的Shutdown hook去實現的。

方式三:/pause 端點【生產可用,但有一點缺陷】

Spring Boot應用提供了/pause 端點,利用該端點可實現優雅下線。

使用方式:

  • 在想下線應用的application.yml 中添加配置,從而啟用並暴露/pause 端點:

management:
endpoint:
# 啟用pause端點
pause:
enabled: true
# 啟用restart端點,之所以要啟用restart端點,是因為pause端點的啟用依賴restart端點的啟用。詳見:https://cloud.spring.io/spring-cloud-static/Finchley.SR2/single/spring-cloud.html#_endpoints
restart:
enabled: true
endpoints:
web:
exposure:
include: pause,restart
  • 發送POST請求到/actuator/pause 端點:
curl -X POST http://你想停止的服務實例地址/actuator/pause
  • 執行後的效果類似下圖:
實用技巧:Spring Cloud中,如何優雅下線微服務?


  • 如圖所示,該應用在Eureka Server上的狀已被標記為DOWN ,但是應用本身其實依然是可以正常對外服務的。在Spring Cloud中,Ribbon做負載均衡時,只會負載到標記為UP 的實例上。利用這兩點,你可以:先用pause端點,將要下線的應用標記為DOWN,但不去真正停止應用;然後過一定的時間(例如90秒,或者自己做個監控,看當前實例的流量變成0後)再去停止應用,例如kill 應用 ,當然如果你足夠變態,kill -9 也可以 。

缺點&侷限

缺點描述不同的版本配置不大一樣早期的Spring Cloud版本中,,pause端點是不依賴restart端點的,後來一個pull request導致pause端點必須依賴restart端點…個人給官方提issue,官方最後選擇了繼續依賴,我也是醉了……無法和Eureka的健康檢查配合使用如果你的服務發現組件用的是Eureka

,並且你的應用開啟了健康檢查(eureka.client.healthcheck

.enabled = true ,那麼/pause 端點無效!!!

方式四:/service-registry 端點【生產可用】

使用方式:

  • 在想下線應用的application.yml 中添加配置,從而暴露/service-registry 端點:

management:
endpoints:
web:
exposure:
include: service-registry
  • 發送POST請求到/actuator/service-registry 端點:
curl -X "POST" "http://localhost:8000/actuator/service-registry?status=DOWN" \
-H "Content-Type: application/vnd.spring-boot.actuator.v2+json;charset=UTF-8"
  • 實行後的效果類似如下圖:
實用技巧:Spring Cloud中,如何優雅下線微服務?


  • 由圖可知,使用/service-registry 端點可實現類似/pause 端點的效果。

缺點

暫時沒有發現缺點。

拓展一下

在實際項目中,你可以做一個運維工具:

  • 運維工具讀取服務發現組件中的所有服務。
  • 有一天你想下線某個服務的時候,就點擊該示例的“優雅下線” 按鈕,該按鈕會請求到想要下線的服務的/pause 端點或者service-registry 端點(看你能不能容忍/pause 端點的缺點),這樣就可以把該實例在Eureka上標記為DOWN,流量過一段時間後就不會打到這個實例上。
  • 做一個流量檢測工具(例如QPS統計,這種百度隨便找下,最簡單的一個過濾器 + map就可以做了),如果檢測到當前實例確實已經沒有流量進入,就在運維工具上點擊另一個按鈕,例如停止。真正停止應用。
  • 當然,如何停止應用又是另一個問題了,例如你可以請求實例的shutdown端點(Spring Boot提供了優雅下線的端點),或者用腳本kill,或者如果是容器可以藉助一些探針……

加Java架構師進階交流群獲取Java工程化、高性能及分佈式、高性能、深入淺出。高架構。性能調優、Spring,MyBatis,Netty源碼分析和大數據等多個知識點高級進階乾貨的直播免費學習權限 都是大牛帶飛 讓你少走很多的彎路的 群號是:883922439 對了 小白勿進 最好是有開發經驗

注:加群要求

1、具有工作經驗的,面對目前流行的技術不知從何下手,需要突破技術瓶頸的可以加。

2、在公司待久了,過得很安逸,但跳槽時面試碰壁。需要在短時間內進修、跳槽拿高薪的可以加。

3、如果沒有工作經驗,但基礎非常紮實,對java工作機制,常用設計思想,常用java開發框架掌握熟練的,可以加。

4、覺得自己很牛B,一般需求都能搞定。但是所學的知識點沒有系統化,很難在技術領域繼續突破的可以加。

5.阿里Java高級大牛直播講解知識點,分享知識,多年工作經驗的梳理和總結,帶著大家全面、科學地建立自己的技術體系和技術認知!


分享到:


相關文章: