Spring Cloud Eureka 是Spring Cloud Netflix 微服务套件中的一部分,它基于Netflix Eureka 做了二次封装,主要负责完成微服务架构中的服务治理功能。Spring Cloud通过为Eureka增加了Spring Bot风格的自动化配置。服务治理是微服务架构中最为核心和基础的模块,主要用来实现微服务实例自动化注册与发现。
- 注册服务:就是将提供某个服务的模块信息(通常是这个服务的ip和端口)注册到1个公共的组件上
- 服务发现:就是新注册的这个服务模块能够及时的被其他调用者发现。不管是服务新增和服务删减都能实现自动发现
1.Eureka 示例
Eureka服务器端,我们称之为注册中心,Eureka支持以集群模式部署,各个微服务启动时,会通过 Eureka Client 向 Eureka Server 注册自己,Eureka Server 会存储该服务的信息也就是说,每个微服务的客户端和服务端,都会注册到 Eureka Server
Eureka客户端:主要处理服务的注册与发现。客户端服务通过注解和参数配置的方式嵌入在客户端应用程序的代码中。运行时,Eureka 客户端向注册中心注册自身提供的服务并周期性的发送心跳来更新它的服务租约。同时,它也能从服务端查询当前注册的服务信息并缓存到本地并周期的刷新服务状态
项目结构说明
项目模块说明
功能说明 | 模块名 | 端口 | 注册中心 | ereka-peer | 1000 | 注册服务 | ms-customer | 8001 | 消费服务 | ms-ribbon-consumer | 8002 |
ereka-peer 等Spring Boot应用在项目中是以模块组成springcloud项目下的pom.xm参考如下
<?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>1.5.2.RELEASE</version>
</parent>
<groupId>springcloud</groupId>
<artifactId>springcloud</artifactId>
<version>1.0-SNAPSHOT</version>
<packaging>pom</packaging>
<modules>
<module>eureka-peer</module>
<module>ms-customer</module>
<module>ms-ribbon-consumer</module>
</modules>
<properties>
<java.version>1.8</java.version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-autoconfigure</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
1.1 服务注册中心
Eureka服务器端,我们称之为注册中心,Eureka支持以集群模式部署,各个微服务启动时,会通过 Eureka Client 向 Eureka Server 注册自己,Eureka Server 会存储该服务的信息也就是说,每个微服务的客户端和服务端,都会注册到 Eureka Server
创建一个基础Spring Boot工程, 命名为eureka-peer, 修改pom.xml 文件,添加依赖。作为Eureka服务器端需要添加引用spring-cloud-starter-eureka-server
<?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>springcloud</groupId>
<artifactId>springcloud</artifactId>
<version>1.0-SNAPSHOT</version>
</parent>
<artifactId>eureka-peer</artifactId>
<version>1.0-SNAPSHOT</version>
<dependencies>
<!-- 服务注册中心 -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-eureka-server</artifactId>
</dependency>
<dependency>
<groupId>javax.xml.bind</groupId>
<artifactId>jaxb-api</artifactId>
<version>2.3.1</version>
</dependency>
<dependency>
<groupId>com.sun.xml.bind</groupId>
<artifactId>jaxb-impl</artifactId>
<version>2.3.1</version>
</dependency>
<dependency>
<groupId>org.glassfish.jaxb</groupId>
<artifactId>jaxb-runtime</artifactId>
<version>2.3.1</version>
</dependency>
</dependencies>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>Dalston.SR5</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
</project>
修改EurekaPeer1Application 启动信息,添加@EnableEurekaServer注解,该注解的作用为 激活Eureka中的DiscouverClient实现,创建一个InfoController 主要用于测试项目启动成功
/**
*
* @EnableEurekaServer注解激活Eureka中的DiscouverClient实现
* @SpringBootApplication默认扫描CustomerApplication所在包所以需要scanBasePackages制定包名
*/
@EnableEurekaServer
@SpringBootApplication
public class EurekaPeer1Application {
public static void main(String[] args) {
System.out.println("服务注册中心:http://127.0.0.1:1000/");
new SpringApplicationBuilder(EurekaPeer1Application.class).web(true).run(args);
}
}
@RestController
public class InfoController {
/**
* http://127.0.0.1:1000/info/
*
* @return
*/
@RequestMapping(value = "/info", method = RequestMethod.GET)
public String into() {
return new Date().toString();
}
}
修改application.properties
server.port=1000
spring.application.name=EUREKA-PEER
############ Eureka ################
#服务注册中心IP
eureka.instance.hostname=127.0.0.1
# 是否注册中心注册,默认=TRUE
eureka.client.register-with-eureka=true
# 是否检索服务
eureka.client.fetch-registry=true
#指定服务注册中心
eureka.client.serviceUrl.defaultZone=http://${eureka.instance.hostname}:1000/eureka/
############ Eureka ################
访问?http://127.0.0.1:1000/?, 查看Eureka 的注服务,由于配置中eureka.client.register-with-eureka和eureka.client.fetch-registry参数配置为true所以项目启动后Eureka注册中心中自身
?修改eureka.client.register-with-eureka和eureka.client.fetch-registry参数配置为false的时候eureka-peer启动后就不会向eureka注册中心注册自己 ,再次访问?http://127.0.0.1:1000/? 会发现Instances currentLy registered with Eureka栏是空的
修改配置参考
server.port=1000
spring.application.name=EUREKA-PEER
############ Eureka ################
#服务注册中心IP
eureka.instance.hostname=127.0.0.1
# 是否注册中心注册,默认=TRUE
eureka.client.register-with-eureka=false
# 是否检索服务
eureka.client.fetch-registry=false
#指定服务注册中心
eureka.client.serviceUrl.defaultZone=http://${eureka.instance.hostname}:1000/eureka/
############ Eureka ################
1.2 服务注册
搭建完服务注册中心后,我们尝试将一个Spring Boot应用键入Eureka服务指令体系中, 创建一个ms-customer的Spring Boot项目
修改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/xsd/maven-4.0.0.xsd">
<parent>
<artifactId>springcloud</artifactId>
<groupId>springcloud</groupId>
<version>1.0-SNAPSHOT</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>ms-customer</artifactId>
<version>1.0-SNAPSHOT</version>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<!-- 注册服务提供 -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-eureka</artifactId>
</dependency>
</dependencies>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>Dalston.SR5</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
</project>
修改Spring Boot应用代码
- 修改启动添加@EnableDiscoveryClient ,将应用注册未Eureka的客户端应用,激活Eureke中DiscoverClient实现,获取服务发现的能力,??
- 创建InfoController,实现当调用 http://127.0.0.1:1111/info/? 时 返回服务信息
//CustomerApplication.java 参考
@EnableDiscoveryClient //将应用注册为Eureka客户端应用,激活Eureke中DiscoverClient实现,获得服务发现的能力
@SpringBootApplication(scanBasePackages = {"com.customer"})
public class CustomerApplication {
public static void main(String[] args) {
System.out.println("Customer:http://127.0.0.1:8001/");
SpringApplication.run(CustomerApplication.class, args);
}
}
//InfoController.java参考
package com.customer.controller;
import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cloud.client.ServiceInstance;
import org.springframework.cloud.client.discovery.DiscoveryClient;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;
import java.util.Date;
@RestController
public class InfoController {
private final Logger logger = Logger.getLogger(getClass());
@Autowired
private DiscoveryClient discoveryClient;
/**
* http://127.0.0.1:8001/info/
*/
@RequestMapping(value = "/info", method = RequestMethod.GET)
public String into() {
ServiceInstance instance = discoveryClient.getLocalServiceInstance();
String message = " host:" + instance.getHost() + ",service_id:" + instance.getServiceId();
logger.info(message);
return message+" Time:"+new Date().toString();
}
}
application.properties 参考:
server.address=127.0.0.1
server.port=8001
#服务的名称
spring.application.name=MS-CUSTOMER
############ Eureka ################
#服务注册中心IP
eureka.instance.hostname=127.0.0.1
# 是否注册中心注册,默认=TRUE
eureka.client.register-with-eureka=true
# 是否检索服务
eureka.client.fetch-registry=true
#指定服务注册中心
eureka.client.serviceUrl.defaultZone=http://${eureka.instance.hostname}:1000/eureka/
#如果有两个注册中心时,参数配置多个节点
#eureka.client.serviceUrl.defaultZone=http://127.0.0.1:1111/eureka/,http://127.0.0.1:1000/eureka/
#服务续约 :定义服务续约任务的调用间隔时间,默认30秒
eureka.instance.lease-renewal-interval-in-seconds=30
#服务续约 :参数用于定义服务时效的时间,默认90秒
eureka.instance.lease-expiration-duration-in-seconds=90
############ Eureka ################
先查看Eureka注册中心 ,打开 http://127.0.0.1:1000/? 会发现MS-CUSTOMER应用已经注册到Eureka注册中心 中
应用启动后调用 http://127.0.0.1:1111/info/? 查看MS-CUSTOMER应用信息
1.3 服务发现与消费
创建ms-ribbon-consumer应用,用于模拟消费 ms-customer服务
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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<artifactId>springcloud</artifactId>
<groupId>springcloud</groupId>
<version>1.0-SNAPSHOT</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>ms-ribbon-consumer</artifactId>
<version>1.0-SNAPSHOT</version>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<!-- 注册服务提供 -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-eureka</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-ribbon</artifactId>
</dependency>
</dependencies>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>Dalston.SR5</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
</project>
添加注解@EnableDiscoveryClient
package com.ribbon;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
import org.springframework.cloud.client.loadbalancer.LoadBalanced;
import org.springframework.context.annotation.Bean;
import org.springframework.web.client.RestTemplate;
@EnableDiscoveryClient //将应用注册为Eureka客户端应用,激活Eureke中DiscoverClient实现,获得服务发现的能力
@SpringBootApplication
public class RibbonConsumerApplication {
public static void main(String[] args) {
SpringApplication.run(RibbonConsumerApplication.class, args);
}
@Bean
@LoadBalanced
RestTemplate resetTemplate(){
return new RestTemplate();
}
}
?创建ConsumerController 来消费服务,通过访问http://127.0.0.1:8002/ribbon-consumer 实现调用 MS-CUSTOMER服务的info信息
package com.ribbon.controller;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.client.RestTemplate;
@RestController
public class ConsumerController {
@Autowired
RestTemplate restTemplate;
/**
* http://127.0.0.1:8002/ribbon-consumer
*/
@RequestMapping(value = "/ribbon-consumer", method = RequestMethod.GET)
public String helloConsumer() {
return restTemplate.getForEntity("http://MS-CUSTOMER/info", String.class).getBody();
}
}
server.address=127.0.0.1
server.port=8002
#服务的名称
spring.application.name=MS-RIBBON-CONSUMER
############ Eureka ################
eureka.instance.hostname=localhost
#指定服务注册中心
eureka.client.serviceUrl.defaultZone=http://${eureka.instance.hostname}:1000/eureka/
############ Eureka ################
同时启动了三个应用
验证 http://127.0.0.1:8002/ribbon-consumer ,可见获取的结果是MS-CUSTOMER应用的info
|