1. Eureka
Eureka [jʊ’ri:kə] 是Netflix發現的一個服務發現框架,本身是一個基於REST的服務,主要用於定位運行在AWS(Amazon Web Service)域中的中間件服務,以達到負載均和和中間服務故障轉移的目的。Spring Cloud將其集成在自己的子項目Spring Cloud Netflix中,以實現Spring Cloud的服務發現功能。
Eureka的服務發現包含兩大組件:
- 服務端發現組件(Eureka Server),也被稱爲服務註冊中心,主要提供服務的註冊功能。
- 客戶端發現組件(Eureka Client),主要用於處理服務的註冊與發現。
- 客戶端組件可以分爲服務消費者和服務提供者,不過兩者是相對的可以相互轉換。可以既是消費者也是服務提供者。
- 服務提供者指的是提供服務的應用,一般用Spring Boot搭建,也可以是其他技術平臺的,遵循Eureka通訊機制就可以了。提供者應用運行的時候自動將自己提供的服務註冊到Eureka Server以供其他應用發現。
- 服務消費者會週期性地給服務註冊中心發送心跳來更新服務(默認30s一週期),如果連續三次心跳都不能夠發現服務,那麼Eureka就會將這個服務節點從服務註冊表中移除。所以一個服務關閉了,並不會立刻在服務中心不可見,需要一段時間,但是一個服務一啓動註冊就看到了
- 此外,客戶端發現組件還會從服務端查詢當前註冊的服務信息緩存到本地,即使Eureka Server出了問題,客戶端組件也可以通過緩存中的信息調研服務節點服務。各個服務之間會通過註冊中心的註冊信息以REST方式來實現調用,並且可以直接通過服務名調用
2. 使用Eureka搭建服務端註冊中心
2.1 環境
<?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">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.1.3.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>xyz.cglzwz</groupId>
<artifactId>ms-springcloud</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>ms-springcloud</name>
<description>Demo project for Spring Boot</description>
<properties>
<java.version>1.8</java.version>
<spring-cloud.version>Greenwich.SR1</spring-cloud.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>${spring-cloud.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
很多傳遞依賴,導入Eureka Server依賴即可
2.2 配置文件 application.yml
# 服務註冊中心
server:
port: 8765
eureka:
instance:
hostname: localhost
client:
register-with-eureka: false # 這是服務中心,不是要註冊的服務
fetch-registry: false # 也不是服務發現檢索
service-url:
defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka/ # 註冊中心的地址
server:
enable-self-preservation: false # 關閉保護默認開啓的保護機制
${} 是引用前面的屬性值
2.4 項目主類添加註解
@EnableEurekaServer,聲明標註類是一個Eureka Server
package xyz.cglzwz.msspringcloud;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.eureka.server.EnableEurekaServer;
@EnableEurekaServer
@SpringBootApplication
public class MsSpringcloudApplication {
public static void main(String[] args) {
SpringApplication.run(MsSpringcloudApplication.class, args);
}
}
2.5 啓動服務註冊中心
http://localhost:8765,現在還沒有服務
3. 使用Eureka搭建客戶端服務提供者
3.1 環境
可以直接繼承剛剛父項目的依賴,也可以另外配置,這裏直接繼承了前面的項目爲父項目。
<?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">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>xyz.cglzwz</groupId>
<artifactId>ms-springcloud</artifactId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<groupId>xyz.cglzwz</groupId>
<artifactId>ms-user</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>ms-user</name>
<description>Demo project for Spring Boot</description>
<properties>
<java.version>1.8</java.version>
</properties>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
3.2 配置文件
server:
port: 8000 # Eureka 實例端口
eureka:
instance:
prefer-ip-address: true # 顯示主機的IP
client:
service-url:
defaultZone: http://localhost:8765/eureka/ # 指定服務端註冊中心地址
spring:
application:
name: ms-user1 # 指定服務應用的名字
3.3 註解驅動
@EnableEurekaClient
package xyz.cglzwz.msuser;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
@EnableEurekaClient
@SpringBootApplication
public class MsUserApplication {
public static void main(String[] args) {
SpringApplication.run(MsUserApplication.class, args);
}
}
3.4 簡單的一個服務,供消費者調用
package xyz.cglzwz.msuser.controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;
@RestController
public class TestController {
@RequestMapping(value = "/test", method = RequestMethod.GET)
public String print() {
return "Hello ..";
}
}
3.5 啓動運行
必須先啓動服務端註冊中心,不然直接啓動客戶端的會報錯,找不到等異常
4. 使用Eureka搭建客戶端服務消費者
4.1 pom.xml && application.yml
很服務提供者一樣,pom.xml都一樣,配置文件這裏只是修改了端口和服務名
server:
port: 7000
eureka:
instance:
prefer-ip-address: true # 顯示主機的IP
client:
service-url:
defaultZone: http://localhost:8765/eureka/ # 指定服務端地址
spring:
application:
name: ms-user2
4.2 引導類
package xyz.cglzwz.msuser2;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
import org.springframework.context.annotation.Bean;
import org.springframework.web.client.RestTemplate;
@EnableEurekaClient
@SpringBootApplication
public class MsUser2Application {
@Bean
public RestTemplate restTemplate() {
return new RestTemplate();
}
public static void main(String[] args) {
SpringApplication.run(MsUser2Application.class, args);
}
}
這裏還注入了一個RestTemplate的Bean到容器,RestTemplate是Spring提供的用於訪問REST服務的客戶端實例,它提供多種便捷訪問遠程Http服務的方法,能夠大大提供客戶端的編寫效率。
4.3 調用服務提供者提供的一個服務
package xyz.cglzwz.msuser2.controller;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.client.RestTemplate;
@RestController
public class TestController {
@Autowired
private RestTemplate restTemplate;
@GetMapping("/print")
public String print() {
// 調用ms-user1應用的一個顯示Hello功能
return restTemplate.getForObject("http://localhost:8000/test", String.class);
}
}
當輸入http://localhost:7000/print 的時候消費者會調用提供者的服務