02 | 服务治理:Nacos 如何实现微服务服务治理
前文我們學習了通用的微服務架構應包含哪些組件以及 Spring Cloud Alibaba 生態中對應的技術實現,其中整個架構體系最核心的組件是服務注冊中心 Alibaba Nacos。本講我們就對 Nacos 展開探討,學習它的使用辦法。在本講我們會講解三方面內容:
Nacos 注冊中心的特性
我們以現實業務為例,某超市會員線上購物送等額積分,此積分在下次購物時可抵用現金,其中涉及訂單服務、會員服務、積分服務等多個微服務模塊。
在以往單實例情況下,服務間通常采用點對點通信,即采用 IP+端口+接口的形式直接調用。但考慮避免單點負載壓力過大以及高可用的性能要求,通常會部署多實例節點保障系統的性能,但增加多實例后,調用方該如何選擇哪個服務提供者進行處理呢?還有當服務提供者出現故障后,如何將后續請求轉移到其他可用實例上呢?面對這些問題,微服務架構必須要引入注冊中心對所有服務實例統一注冊管理、有組織地進行健康檢查來保障服務的可用性。
在 Spring Cloud Alibaba 生態中,由 Nacos 中間件承擔注冊中心職責,需要獨立部署。下面我們先來認識一下 Nacos。
Nacos 官方地址為https://nacos.io/zh-cn/index.html。由阿里開源,官方定義為:
一個更易于構建云原生應用的動態服務發現、配置管理和服務管理平臺。
Nacos 具備以下職能:
- 服務發現及管理;
- 動態配置服務;
- 動態 DNS 服務。
下圖是Nacos 的核心特征:
Nacos 的快速部署
在微服務架構中,Nacos 注冊中心處于核心地位,通常我們會采用高性能服務器獨立部署。下面我來演示 Nacos 的部署過程。
環境準備
Nacos 同時支持 Windows 與 Linux 系統。因大多數服務器會選擇安裝 Linux 操作系統,為了模擬真實環境,建議你搭建一個 CentOS 7/8 的虛擬機,我這里的服務器地址為:192.168.31.102。Nacos 采用 Java 進行開發,要求 JDK8+,如果 CentOS 系統中沒有安裝 JDK,可使用下面流程進行基礎環境準備。
- 利用 yum 命令安裝 OpenJDK 8
- 配置 JAVA_HOME 環境變量
安裝后 JDK 不要忘記設置 JAVA_HOME 環境變量,OpenJDK 默認安裝在 /usr/lib/jvm/ 路徑下,之后通過編輯 profile 設置 JAVA_HOME 環境變量。
最后要確認 JAVA_HOME 環境變量是否配置正確
[root@server-1 ~]# echo $JAVA_HOME/usr/lib/jvm/java-1.8.0-openjdk-1.8.0.272.b10-1.el7_9.x86_64JDK安裝后,正式進入 Nacos 的安裝過程。
安裝過程
第一步,訪問 Nacos GitHub:https://github.com/alibaba/nacos/releases/獲取 Nacos 最新版安裝包 nacos-server-1.4.0.tar.gz。
第二步,上傳 nacos-server-1.4.0.tar.gz 到 CentOS 系統,對安裝包解壓縮。
[root@server-1 local]# tar -xvf nacos-server-1.4.0.tar.gz解壓后 Nacos 目錄結構如下。
- bin:保存啟用/關閉 Nacos Server 腳本;
- conf:Nacos Server 配置目錄;
- data:Nacos 數據目錄;
- logs:存放日志目錄;
- target:Nacos Jar 包存放目錄;
第三步,以單點方式啟動 Nacos。
[root@server-1 local]# cd nacos/bin[root@server-1 bin]# sh startup.sh -m standalone啟動日志如下:
nacos is starting with standalonenacos is starting, you can check the /usr/local/nacos/nacos/logs/start.out默認 Nacos 以后臺模式啟動,利用 tail 命令查看啟動日志。可以看到 Nacos 默認端口為 8848,下面日志說明 Nacos 單機模式已啟動成功。
[root@server-1 bin]# tail -f /usr/local/nacos/logs/start.out2020-12-06 21:03:18,759 INFO Tomcat started on port(s): 8848 (http) with context path '/nacos'2020-12-06 21:03:18,766 INFO Nacos Log files: /usr/local/nacos/nacos/logs2020-12-06 21:03:18,766 INFO Nacos Log files: /usr/loca/nacos/nacos/conf2020-12-06 21:03:18,766 INFO Nacos Log files: /usr/local/nacos/nacos/data2020-12-06 21:03:18,767 INFO Nacos started successfully in stand alone mode. use embedded storage第四步,默認 CentOS 系統并沒有對外開放 7848/8848 端口,需要設置防火墻對 7848/8848 端口放行。
其中,8848 端口是 Nacos 對客戶端提供服務的端口,7848 是 Nacos 集群通信端口,用于Nacos 集群間進行選舉,檢測等。
[root@server-1 bin]# firewall-cmd --zone=public --add-port=8848/tcp --permanentsuccess[root@server-1 bin]# firewall-cmd --zone=public --add-port=7848/tcp --permanentsuccess[root@server-1 bin]# firewall-cmd --reloadsuccess此時,Nacos 已單機部署完畢。
第五步,進入 Nacos 管理界面,打開瀏覽器,地址欄輸入:
http://localhost:8848/nacos
其中 localhost 就是 Nacos 服務器的IP地址,端口號 8848。
管理界面默認用戶名與密碼均為nacos,提交后進入首頁。點擊左側菜單“服務管理->服務列表”,這個功能用于查看已注冊微服務列表。
目前因為沒有任何微服務注冊,右側服務列表是空的。那如何讓微服務在 Nacos 中注冊呢?下一小節咱們繼續講解。
微服務如何接入 Nacos
Spring Cloud Alibaba 作為 Spring Cloud 子項目,開發框架仍基于 SpringBoot,只是在構建項目時需要選擇不同的 starter 接入注冊中心,下面我們通過實操完成微服務與 Nacos 服務器的接入工作。
開發工具強烈推薦 IDEA Ultimate,Ultimate 內置 SpringBoot 工程向導,可以非常方便地實現 Spring Cloud 微服務的快速創建。
1. 創建新工程,工程類型選擇 Spring Initializr。
下圖是 SpringBoot 工程向導,右側選中 Custom,寫入阿里云地址http://start.aliyun.com,默認的 https://start.spring.io。 這里需要連接 spring 官方服務器,因為網絡原因經常無法訪問,所以采用國內阿里云鏡像生成工程初始代碼。
Project Metadata 面板,設置 Maven Group 與 Artifact,一般 Artifact 即為微服務名稱,約定俗成以 service 單詞結尾。
2. 在向導后面的依賴頁面,要接入 Nacos 有一項是必選的,請大家注意。
Spring Cloud Alibaba -> Nacos Service Discovery。
Nacos Service Discovery 是在當前SpringBoot工程內置 Nacos 客戶端,在微服務應用啟動時通過 Nacos 客戶端向 Nacos 服務器發送注冊信息。
3. 工程創建成功,打開 pom.xml 文件,確認 Maven 依賴 nacos-discovery,說明服務已內置 Nacos 客戶端成功。
此外,我們需要在當前微服務增加 Spring-Web 依賴。因為微服務默認通過 RESTful API 對外暴露接口,增加 Spring-Web 會在應用中內嵌 Tomcat,使微服務具備 HTTP 響應能力。
4. 在 application.properties 配置 Nacos 注冊中心通信地址。
# 應用名稱,默認也是在微服務中注冊的微服務 IDspring.application.name=sample-service# 配置 Nacos 服務器的IP地址spring.cloud.nacos.discovery.server-addr=192.168.31.102:8848#連接 Nacos 服務器使用的用戶名、密碼,默認為 nacosspring.cloud.nacos.discovery.username=nacosspring.cloud.nacos.discvery.password=nacos#微服務提供Web服務的端口號server.port=90005. 啟動 SampleService 工程,在啟動日志最后三句清晰的說明注冊已成功。
#Web 服務端口號 9000INFO 14188 o.s.b.w.embedded.tomcat.TomcatWebServer : Tomcat started on port(s): 9000 (http) with context path ''#微服務向 Nacos 注冊成功,微服務 ID:sample-serviceINFO 14188 c.a.c.n.registry.NacosServiceRegistry : nacos registry, DEFAULT_GROUP sample-service 192.168.47.1:9000 register finished#微服務啟動成功INFO 14188 c.l.s.SampleServiceApplication : Started SampleServiceApplication in 4.911 seconds (JVM running for 6.039)6. 瀏覽器打開http://192.168.31.102:8848/nacos,查看服務列表時發現 sample-service 服務已出現。
點擊列表右側“詳情按鈕”就會出現詳細信息,在服務詳情下清晰列出 sample-service 服務目前可用實例的 IP 及服務端口。
到這里我們已完成了微服務向 Nacos 注冊登記,因為 SpringBoot 為我們高度封裝了注冊過程。為了你更透徹理解 Nacos,下面我來介紹 Nacos 注冊過程背后的原理。
Nacos 注冊中心的心跳機制
在微服務啟動后每過5秒,會由微服務內置的 Nacos 客戶端主動向 Nacos 服務器發起心跳包(HeartBeat)。心跳包會包含當前服務實例的名稱、IP、端口、集群名、權重等信息。
如果你開啟微服務 Debug 日志,會清晰地看到每 5 秒一個心跳請求被發送到 Nacos 的 /nacos/v1/ns/instance/beat 接口,該請求會被 Nacos 服務器內置的 naming 模塊處理。
如果你開啟微服務 Debug 日志,會清晰地看到每 5 秒一個心跳請求被發送到 Nacos 的 /nacos/v1/ns/instance/beat 接口,該請求會被 Nacos 服務器內置的 naming 模塊處理。
23:11:23.826 DEBUG 10720 --- [ing.beat.sender] s.n.www.protocol.http.HttpURLConnection : sun.net.www.MessageHeader@665891d213 pairs: {PUT /nacos/v1/ns/instance/beat?app=unknown&serviceName=DEFAULT_GROUP%40%40sample-service&namespaceId=public&port=9000&clusterName=DEFAULT&ip=192.168.47.1 HTTP/1.1: null}{Content-Type: application/x-www-form-urlencoded}{Accept-Charset: UTF-8}{Accept-Encoding: gzip,deflate,sdch}{Content-Encoding: gzip}{Client-Version: 1.3.2}{User-Agent: Nacos-Java-Client:v1.3.2}{RequestId: 6447aa06-9d70-41ea-83ef-cd27af1d3422}{Request-Module: Naming}{Host: 192.168.31.102:8848}{Accept: text/html, image/gif, image/jpeg, *; q=.2, */*; q=.2}{Connection: keep-alive}{Content-Length: 326}23:11:28.837 DEBUG 10720 --- [ing.beat.sender] s.n.www.protocol.http.HttpURLConnection : sun.net.www.MessageHeader@5f00479a12 pairs: {PUT /nacos/v1/ns/instance/beat?app=unknown&serviceName=DEFAULT_GROUP%40%40sample-service&namespaceId=public&port=9000&clusterName=DEFAULT&ip=192.168.47.1 HTTP/1.1: null}{Content-Type: application/x-www-form-urlencoded}{Accept-Charset: UTF-8}{Accept-Encoding: gzip,deflate,sdch}{Content-Encoding: gzip}{Client-Version: 1.3.2}{User-Agent: Nacos-Java-Client:v1.3.2}{RequestId: 9fdf2264-9704-437f-bd34-7c9ee5e0be41}{Request-Module: Naming}{Host: 192.168.31.102:8848}{Accept: text/html, image/gif, image/jpeg, *; q=.2, */*; q=.2}{Connection: keep-alive}23:11:38.847 DEBUG 10720 --- [ing.beat.sender] s.n.www.protocol.http.HttpURLConnection : sun.net.www.MessageHeader@3521283812 pairs: {PUT /nacos/v1/ns/instance/beat?app=unknown&serviceName=DEFAULT_GROUP%40%40sample-service&namespaceId=public&port=9000&clusterName=DEFAULT&ip=192.168.47.1 HTTP/1.1: null}{Content-Type: application/x-www-form-urlencoded}{Accept-Charset: UTF-8}{Accept-Encoding: gzip,deflate,sdch}{Content-Encoding: gzip}{Client-Version: 1.3.2}{User-Agent: Nacos-Java-Client:v1.3.2}{RequestId: ccb6a586-897f-4036-9c0d-c614e2ff370a}{Request-Module: Naming}{Host: 192.168.31.102:8848}{Accept: text/html, image/gif, image/jpeg, *; q=.2, */*; q=.2}{Connection: keep-alive}naming 模塊在接收到心跳包后,會按下圖邏輯處理心跳包并返回響應:
到這里一次完整的心跳包處理已完成
總結
以上是生活随笔為你收集整理的02 | 服务治理:Nacos 如何实现微服务服务治理的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: JVM 核心技术 调优分析与面试经验
- 下一篇: 03 | 高可用保证:Nacos 如何有