Spring Cloud與微服務之註冊中心Eureka
文章目錄
Eureka
SpringCloud提供了多種註冊中心的支援,如:Eureka、ZooKeeper等。推薦使用Eureka。
Eureka是Netflix開源的服務發現元件,本身是一個基於REST的服務。它包含Server和Client兩部分。Spring Cloud將它整合在子專案Spring Cloud Netflix中,從而實現微服務的註冊於發現。
Eureka包含兩個元件:
- Eureka Service
- Eureka Client。
Eureka Service
提供服務註冊,各個節點啟動後,會在Eureka Service中進行註冊,這樣Eureka Service中的服務登錄檔中將會儲存所有可用服務節點的資訊,服務節點的資訊可以在介面中直觀的看到。
預設情況下,如果Eureka Server在一定時間內沒有接收到某個微服例項的心跳,Eureka Server將會登出該例項(預設90秒)。但是當網路分割槽故障發生時,微服務與Eureka Server之間無法正常通訊,以上行為可能變得非常危險了——因為微服務本身是健康的,此時本不應該登出掉這個微服務。
Eureka通過“自我保護模式”來解決這個問題——當Eureka Server節點在短時間內丟失過多客戶端時(可能發生了網路分割槽故障),那麼這個節點就會進入自我保護模式。一旦進入該模式,Eureka Server就會保護服務登錄檔中的資訊,不再刪除服務登錄檔中的資料(也就是不會登出任何微服務)。當網路故障恢復後,該Eureka Server節點會自動退出自我保護模式。
禁用自我保護模式:
enable-self-preservation: false #禁用自我保護模式
不過一般還是使用吧,所以說上面的程式碼就不用添加了。
Eureka Client
是一個Java客戶端,用於簡化Eureka Server的互動,客戶端同時也就別一個內建的,使用輪詢(round-robln)負載演算法的負載均衡器。
在應用啟動後,將會向Eureka Server傳送心跳預設週期為30秒,如果Eureka Server在多個心跳週期內沒有接收到某個節點的心跳,Eureka Service將會從服務登錄檔中把這個服務節點移除(預設90秒)。
Eureka Service之間通過複製的方式完成資料的同步,Eureka還提供了客戶端快取機制,即使所有的Eureka Server都掛掉,客戶端依然可以利用快取中的資訊消費其他服務的API。綜上,Eureka通過心跳檢查、客戶端快取等機制,確保了系統的高可用性、靈活性和可伸縮性。
微服務註冊與發現
微服務註冊與發現機制是這樣的:
1、服務提供者將服務註冊到註冊中心。
2、服務消費者通過註冊中心查詢服務。
3、查詢到服務後進行呼叫(這裡就是無需硬編碼url的解決方案)
4、服務的消費者與服務中心保持心跳連線,一旦服務提供者的地址發生變更時,註冊中心會通知服務消費者。
Eureka註冊中心原始碼
由於Eureka註冊中心支援叢集架構,這樣可以防止一個Eureka服務掛掉後,整個註冊中心不能使用,因為這樣可以在生產環境中避免出現單點故障,確保Eureka服務的高可用性。
所以說這裡直接建立兩個Eureka註冊中來模擬Eureka叢集註冊中心中相互在對方註冊服務的情況。
springcloud-eureka註冊中心
springcloud-eureka專案結構
pom.xml原始碼:
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<artifactId>springcloud-parent</artifactId>
<groupId>com.lyc</groupId>
<version>1.0-RELEASE</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>springcloud-eureka</artifactId>
<packaging>jar</packaging>
<name>SpringCloud微服務::Eureka服務1</name>
<url>http://www.example.com</url>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
<!--匯入SpringCloud的依賴管理-->
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>Dalston.SR3</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<!--匯入Eureka服務的依賴-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-eureka-server</artifactId>
</dependency>
<!--安全認證-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
</dependencies>
<build>
<finalName>${project.artifactId}</finalName>
</build>
</project>
EurekaServer原始碼:
package com.lyc;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.eureka.server.EnableEurekaServer;
@EnableEurekaServer //申明這是一個Eureka服務
@SpringBootApplication
public class EurekaServer {
public static void main(String[] args) {
SpringApplication.run(EurekaServer.class,args);
}
}
application.yml原始碼:
server:
port: 6868 #服務埠
spring:
application:
name: springcloud-eureka #指定服務名
eureka:
client:
registerWithEureka: true #是否將自己註冊到Eureka服務中,本身就是所有無需註冊
fetchRegistry: true #是否從Eureka中獲取註冊資訊
serviceUrl: #Eureka客戶端與Eureka服務端進行互動的地址
defaultZone: http://root:[email protected]:6869/eureka/
security:
basic:
enable: true #開啟基於HTTP basic的認證
user: #配置使用者的賬戶資訊
name: root
password: root123
springcloud-eureka2註冊中心
springcloud-eureka2專案結構
pom.xml原始碼
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<artifactId>springcloud-parent</artifactId>
<groupId>com.lyc</groupId>
<version>1.0-RELEASE</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>springcloud-eureka2</artifactId>
<name>SpringCloud微服務::Eureka服務2</name>
<url>http://www.example.com</url>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
<!--匯入SpringCloud的依賴管理-->
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>Dalston.SR3</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<!--匯入Eureka服務的依賴-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-eureka-server</artifactId>
</dependency>
<!--安全認證-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
</dependencies>
<build>
<finalName>${project.artifactId}</finalName>
</build>
</project>
EurekaServer2原始碼:
package com.lyc;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.eureka.server.EnableEurekaServer;
@EnableEurekaServer //申明這是一個Eureka服務
@SpringBootApplication
public class EurekaServer2 {
public static void main(String[] args) {
SpringApplication.run(EurekaServer2.class,args);
}
}
application.yml原始碼:
server:
port: 6869 #服務埠
spring:
application:
name: springcloud-eureka2 #指定服務名
eureka:
client:
registerWithEureka: true #是否將自己註冊到Eureka服務中,本身就是所有無需註冊
fetchRegistry: true #是否從Eureka中獲取註冊資訊
serviceUrl: #Eureka客戶端與Eureka服務端進行互動的地址
defaultZone: http://root:[email protected]:6868/eureka/
security:
basic:
enable: true #開啟基於HTTP basic的認證
user: #配置使用者的賬戶資訊
name: root
password: root123
專案的執行與分析
執行啟動類EurekaServer與EurekaServer2分別啟動兩個註冊中心。
在SpringCloud中,其預設的配置檔案為.yml
格式,在這裡,我們的是application.yml,該檔案的書寫格式與.properties
類似,但是是其書寫格式的簡化版。
比如說在.properties
檔案中,如果我們要指定埠號,我們可以這樣寫:
server.port=6868
但是在SpringCloud的application.yml我們則簡化為:
server:
port: 6868 #服務埠
其中key與value之間有一個空格的距離,而根節點的每一個子節點都會往後縮排兩個字元,比如說port就在server的基礎上縮進了兩個字元間距,如果port後面還有子節點,則其子節點繼續在port的基礎上繼續縮排兩個字元間距。
通過上面分析,我們得知springcloud-eureka的埠號就是在application.yml檔案中指定的,其埠號為6868,所以說我們可以在瀏覽器中直接訪問該註冊中心,註冊中心的訪問地址為:
http://127.0.0.1:6868/
其訪問的結果如下所示:
上面的登入是通過配置檔案的下面程式碼來指定的,其中enable: true
用於開啟基於HTTP basic的認證,而user則用於配置使用者的賬戶資訊。
security:
basic:
enable: true #開啟基於HTTP basic的認證
user: #配置使用者的賬戶資訊
name: root
password: root123
我們直接輸入自己自定義的賬號與密碼後就成功的登入到了註冊中心。
在上圖中如圖所示的箭頭指出了在當前註冊中心中所註冊的服務。
在下面的程式碼中 registerWithEureka: true
指的是將自己的服務註冊到Eureka註冊中心,而fetchRegistry: true
則是指明,我們可以從註冊中心中獲取所註冊的服務項,最後defaultZone
則是指明瞭註冊中心的註冊地址以及登入的賬號與密碼。
eureka:
client:
registerWithEureka: true #是否將自己註冊到Eureka服務中,本身就是所有無需註冊
fetchRegistry: true #是否從Eureka中獲取註冊資訊
serviceUrl: #Eureka客戶端與Eureka服務端進行互動的地址
defaultZone: http://root:[email protected]:6869/eureka/
同理在springcloud-eureka2中,我們也有類似的配置
eureka:
client:
registerWithEureka: true #是否將自己註冊到Eureka服務中,本身就是所有無需註冊
fetchRegistry: true #是否從Eureka中獲取註冊資訊
serviceUrl: #Eureka客戶端與Eureka服務端進行互動的地址
defaultZone: http://root:[email protected]:6868/eureka/
這裡的配置就是將springcloud-eureka2註冊中心註冊到springcloud-eureka中。
由於上面的配置,我們的註冊中心springcloud-eureka與springcloud-eureka2就實現了彼此間的相互註冊,可以共享註冊服務資訊,這樣我們就實現了註冊中心的叢集配置。