SpringCloud的Eureka模塊詳解
認(rèn)識Eureka
Eureka 是 Netflix 開發(fā)的,一個基于 REST 服務(wù)的,服務(wù)注冊與發(fā)現(xiàn)的組件,
Eureka采用了CS的設(shè)計架構(gòu),Eureka Sever作為服務(wù)注冊功能的服務(wù)器,它是服務(wù)注冊中心。而系統(tǒng)中的其他微服務(wù),使用Eureka的客戶端連接到 Eureka Server并維持心跳連接。這樣系統(tǒng)的維護(hù)人員就可以通過Eureka Server來監(jiān)控系統(tǒng)中各個微服務(wù)是否正常運行。

Eureka工作原理
Eureka架構(gòu)圖

Eureka兩個組件
Eureka服務(wù)器
Eureka Server提供服務(wù)注冊服務(wù) 各個微服務(wù)節(jié)點通過配置啟動后,會在EurekaServer中進(jìn)行注冊,這樣EurekaServer中的服務(wù)注冊表中將會存儲所有可用服務(wù)節(jié)點的信息,服務(wù)節(jié)點的信息可以在界面中直觀看到。
Eureka客戶端
EurekaClient通過注冊中心進(jìn)行訪問 它是一個Java客戶端,用于簡化Eureka Server的交互,客戶端同時也具備一個內(nèi)置的、使用輪詢(round-robin)負(fù)載算法的負(fù)載均衡器。在應(yīng)用啟動后,將會向Eureka Server發(fā)送心跳(默認(rèn)周期為30秒)。如果Eureka Server在多個心跳周期內(nèi)沒有接收到某個節(jié)點的心跳,EurekaServer將會從服務(wù)注冊表中把這個服務(wù)節(jié)點移除(默認(rèn)90秒)。
Eureka相關(guān)概念
- 服務(wù)注冊:register
- 服務(wù)續(xù)約:renew, 客戶端默認(rèn)每隔30秒向服務(wù)器發(fā)送一次心跳進(jìn)行續(xù)約,如果服務(wù)器90秒內(nèi)沒有收到心跳,則將該客戶端剔除
- 獲取服務(wù)注冊列表信息:fetch registries
- 服務(wù)下線:cancel
- 服務(wù)剔除eviction
Eureka自我保護(hù)模式
應(yīng)用場景
Eureka是通過心跳判斷微服務(wù)是否是健康的,默認(rèn)情況下,微服務(wù)每隔30秒像Eureka Server發(fā)送一次心跳,Eureka Server接收到心跳后就會進(jìn)行服務(wù)續(xù)約,若Eureka Server持續(xù)90秒未收到某個微服務(wù)的心跳,則會將其從服務(wù)注冊表剔除,以防止不健康的服務(wù)會對其他服務(wù)造成影響。但是,還存在一種情況: 微服務(wù)本身是健康的,是網(wǎng)絡(luò)故障造成微服務(wù)與Eureka之間無法正常通信,為了保證服務(wù)的高可用(AP),Eureka寧可保留錯誤的服務(wù)注冊信息,也不盲目注銷任何可能健康的服務(wù)實例
解決辦法
Eureka通過自我保護(hù)模式解決該問題:
當(dāng)Eureka Server節(jié)點在短時間內(nèi)丟失過多客戶端時(可能發(fā)生了網(wǎng)絡(luò)分區(qū)故障),那么這個節(jié)點就會進(jìn)入自我保護(hù)模式。一旦進(jìn)入該模式, Eureka Server就會保護(hù)服務(wù)注冊表中的信息,不再刪除服務(wù)注冊表中的數(shù)據(jù)(也就是不會注銷任何微服務(wù))。當(dāng)網(wǎng)絡(luò)故障恢復(fù)后,該Eureka Server節(jié)點會自動退出自我保護(hù)模式。
具體過程如下:
當(dāng)Eureka服務(wù)器每分鐘收到心跳續(xù)租的數(shù)量低于一個閾值,就會觸發(fā)自我保護(hù)模式。當(dāng)它收到的心跳數(shù)重新恢復(fù)到閾值以上時,該Eureka服務(wù)器節(jié)點才會自動退出自我保護(hù)模式。心跳閥值計算公式如下:
服務(wù)實例總數(shù)量×(60/每個實例心跳間隔秒數(shù))×自我保護(hù)系數(shù)(0.85)
如果在15分鐘內(nèi)超過85%的節(jié)點都沒有正常的心跳,那么Eureka就認(rèn)為客戶端與注冊中心出現(xiàn)了網(wǎng)絡(luò)故障,此時會出現(xiàn)以下幾種情況:
(1)Eureka不再從注冊列表中移除因為長時間沒收到心跳而應(yīng)該過期的服務(wù)
(2)Eureka依然能接受新服務(wù)的注冊和查詢請求,但是不會被同步到其他節(jié)點上(即保證當(dāng)前節(jié)點依然可用)
(3)當(dāng)網(wǎng)絡(luò)穩(wěn)定時,當(dāng)前實例新的注冊信息會被同步到其他節(jié)點中
# 是否開啟自我保護(hù)模式 eureka.server.enable-self-preservation=false # 每個實例心跳間隔秒數(shù) eureka.instance.lease-renewal-interval-in-seconds:30 # 自我保護(hù)系數(shù) eureka.server.renewal-percent-threshold:0.85
自我保護(hù)模式是一種應(yīng)對網(wǎng)絡(luò)異常的安全保護(hù)措施,它是Eureka的一種架構(gòu)哲學(xué):寧可同時保留所有微服務(wù)(健康或不健康均保留),也不盲目注銷任何健康的微服務(wù)。
此模式使Eureka集群更加健壯、穩(wěn)定。
Eureka案例
為了方便依賴的統(tǒng)一管理,首先創(chuàng)建一個maven父工程 spring-cloud-demo
pom文件
<?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/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.mmw.springcloud</groupId>
<artifactId>spring-cloud-demo</artifactId>
<packaging>jar</packaging>
<version>1.0-SNAPSHOT</version>
<!-- 統(tǒng)一依賴管理 -->
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
<junit.version>4.12</junit.version>
<log4j.version>1.2.17</log4j.version>
<lombok.version>1.18.16</lombok.version>
<mysql.version>5.1.49</mysql.version>
<druid.version>1.1.16</druid.version>
<mybatis.spring.boot.version>2.2.1</mybatis.spring.boot.version>
<devtools.version>2.1.17.RELEASE</devtools.version>
<spring.boot.version>2.2.2.RELEASE</spring.boot.version>
<spring.cloud.version>Hoxton.SR1</spring.cloud.version>
</properties>
<dependencyManagement>
<dependencies>
<!--spring boot 2.2.2-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>${spring.boot.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!--spring cloud Hoxton.SR1-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>${spring.cloud.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>${mysql.version}</version>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid-spring-boot-starter</artifactId>
<version>1.1.17</version>
</dependency>
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>${mybatis.spring.boot.version}</version>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>${junit.version}</version>
</dependency>
<dependency>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
<version>${log4j.version}</version>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>${lombok.version}</version>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<version>${devtools.version}</version>
</dependency>
</dependencies>
</dependencyManagement>
</project>創(chuàng)建Eureka服務(wù)端
pom文件
<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.mmw.springcloud</groupId>
<artifactId>spring-cloud-demo</artifactId>
<version>1.0-SNAPSHOT</version>
</parent>
<artifactId>cloud-eureka-9001</artifactId>
<name>cloud-eureka-9001</name>
<description>Eureka Server 9001</description>
<properties>
<java.version>1.8</java.version>
<maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target>
</properties>
<dependencies>
<!--eureka-server-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
</dependency>
<!--boot web actuator-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
</dependencies>
</project>配置文件中添加Eureka配置
# 應(yīng)用名稱
server:
port: 9001
eureka:
instance:
# eureka服務(wù)端的實例名稱
hostname: localhost
client:
# 不像eureka注冊自身
register-with-eureka: false
# false表示自己端就是注冊中心,我的職責(zé)就是維護(hù)服務(wù)實例,并不需要去檢索服務(wù)
fetch-registry: false
service-url:
# 注意這個defaultZone配置需要手動打出來
defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka/
server:
# 開啟自我保護(hù)模式
enable-self-preservation: true
#eviction-interval-timer-in-ms: 2000啟動類上添加注解
package com.mmw.cloud;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
import org.springframework.cloud.netflix.eureka.server.EnableEurekaServer;
@SpringBootApplication
// 啟用Eureka服務(wù)組件
@EnableEurekaServer
public class CloudEureka9001Application {
public static void main(String[] args) {
SpringApplication.run(CloudEureka9001Application.class, args);
}
}最后測試
啟動服務(wù)后,訪問 //localhost:9001/即可看到 Spring Eureka服務(wù)主頁

因為暫時還沒有Eureka Client 服務(wù)注冊,所以顯示 No instances avaliable
創(chuàng)建Eureka客戶端
cloud-eureka-client-9002
POM中引入依賴
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>啟動類上開啟Eureka Client
package com.mmw.eureka;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
@SpringBootApplication
@EnableEurekaClient
public class CloudEurekaClient9002Application {
public static void main(String[] args) {
SpringApplication.run(CloudEurekaClient9002Application.class, args);
}
}配置Eureka
server:
port: 9002
servlet:
context-path: /client9002
spring:
application:
name: cloud-eureka-client-9002
eureka:
client:
# 表示是否將自己注冊進(jìn)Eurekaserver默認(rèn)為true。
register-with-eureka: true
# 是否從EurekaServer抓取已有的注冊信息,默認(rèn)為true。單節(jié)點無所謂,集群必須設(shè)置為true才能配合ribbon使用負(fù)載均衡
fetch-registry: true
service-url:
defaultZone: http://localhost:9001/eureka
instance:
hostname: localhost最后啟動服務(wù),刷新訪問 //localhost:9001,可以看到cloud-eureka-client-9002已經(jīng)注冊進(jìn)去了

到此這篇關(guān)于SpringCloud的Eureka模塊詳解的文章就介紹到這了,更多相關(guān)SpringCloud的Eureka內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
SpringRetry重試機(jī)制之@Retryable注解與重試策略詳解
本文將詳細(xì)介紹SpringRetry的重試機(jī)制,特別是@Retryable注解的使用及各種重試策略的配置,幫助開發(fā)者構(gòu)建更加健壯的應(yīng)用程序,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教2025-04-04
MyBatis Map結(jié)果的Key轉(zhuǎn)為駝峰式
今天小編就為大家分享一篇關(guān)于MyBatis Map結(jié)果的Key轉(zhuǎn)為駝峰式,小編覺得內(nèi)容挺不錯的,現(xiàn)在分享給大家,具有很好的參考價值,需要的朋友一起跟隨小編來看看吧2018-12-12
mybatis-plus阻止全表更新與刪除的實現(xiàn)
BlockAttackInnerInterceptor 是mybatis-plus的一個內(nèi)置攔截器,用于防止惡意的全表更新或刪除操作,本文主要介紹了mybatis-plus阻止全表更新與刪除的實現(xiàn),感興趣的可以了解一下2023-12-12

