eureka服务发现和注册
是Netflix开源的一款提供服务注册
和发现
的产品,它提供了完整的Service Registry和Service Discovery实现。也是springcloud体系中最重要最核心的组件之一
Eureka 是一个基于 REST
的服务,主要在 AWS 云中使用, 定位服务来进行中间层服务器的负载均衡和故障转移
什么是服务中心?
服务中心又称注册中心,管理各种服务功能包括服务的注册、发现、熔断、负载、降级等,比如dubbo admin后台的各种功能
在有服务注册中心之前–>项目A调用项目B是直接调用
有了服务注册中心之后–>任何一个服务都不能直接调用,都需要通过服务注册中心来调用
由于各种服务都注册到了服务中心,就有了去做很多高级功能条件。比如几台服务提供相同服务来做均衡负载
;监控服务器调用成功率来做熔断
,移除服务列表中的故障点
;监控服务调用时间来对不同的服务器设置不同的权重
等等
eureka的两个组件
-
Eureka服务器
用来简化与服务器的交互、作为轮询负载均衡器,并提供服务的故障切换支持
-
Eureka客户端
提供基于流量、资源利用率以及出错状态的加权负载均衡
Eureka的基本结构:
三个角色:
-
Eureka Server
提供服务注册和发现
-
Service Provider
服务提供方,将自身服务注册到Eureka,从而使消费方能够找到
-
Service Consumer
服务消费方,从eureka注册服务列表,从而能够消费服务
配置服务中心
- pom导入依赖
<dependencies>
<!-- eureka的服务端 -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
</dependency>
<!-- web启动器 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
<!-- 热部署工具 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<scope>runtime</scope>
<optional>true</optional>
</dependency>
<!-- lombok -->
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
</dependency>
<!-- 测试 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
</dependency>
</dependencies>
- 在启动器加入
@SpringBootApplication
注解标明事服务端
@SpringBootApplication
@EnableEurekaServer
public class EurekaMain7001 {
public static void main(String[] args) {
SpringApplication.run(EurekaMain7001.class,args);
}
}
- 配置文件,在application.yml配置eureka的信息
server:
port: 7001
eureka:
instance:
hostname: eureka7001.com #eureka服务端的实例名字
client:
register-with-eureka: false #表识不向注册中心注册自己 默认true
fetch-registry: false #表示自己就是注册中心,职责是维护服务实例,并不需要去检索服务 默认为true
service-url:
defaultZone: http://eureka7002.com:7002/eureka/ #设置与eureka server交互的地址查询服务和注册服务都需要依赖这个地址
-
启动工程后,访问:http://localhost:7001/ ,可以看到下面的页面,其中还没有发现任何服务
http://favorites.ren/assets/images/2017/springcloud/eureka_start.jpg?ynotemdtimestamp=1606818054331
集群
在一个分布式系统中,服务注册中心是最重要的基础部分,理应随时处于可以提供服务的状态。为了维持其可用性,使用集群是很好的解决方案。Eureka通过互相注册的方式来实现高可用的部署,所以我们只需要将Eureke Server配置其他可用的serviceUrl就能实现高可用部署
假如我们只有一个服务端,当这个服务端出现一些 guz问题,故障的话,造成的损失就是毁灭性的
为了避免这样的情况,我们可以多开几个服务端,实现高可用
双节点注册中心
双节点注册中心,就必须在双方互相注册服务
这是节点1:7001端口的server
server:
port: 7001
eureka:
instance:
hostname: eureka7001.com #eureka服务端的实例名字
client:
register-with-eureka: false #表识不向注册中心注册自己
fetch-registry: false #表示自己就是注册中心,职责是维护服务实例,并不需要去检索服务
service-url:
defaultZone: http://eureka7002.com:7002/eureka/ #设置与eureka server交互的地址查询服务和注册服务都需要依赖这个地址
这是节点2:7002端口的server
server:
port: 7002
eureka:
instance:
hostname: eureka7002.com #eureka服务端的实例名字
client:
register-with-eureka: false #表识不向注册中心注册自己
fetch-registry: false #表示自己就是注册中心,职责是维护服务实例,并不需要去检索服务
service-url:
defaultZone: http://eureka7001.com:7001/eureka/ #设置与eureka server交互的地址查询服务和注册服务都需要依赖这个地址
记得在host文件里面配置映射
127.0.0.1 eureka7001.com
127.0.0.1 eureka7002.com
双节点注册中心的使用?(客户端)
每个客户端都要注册两个节点
server:
port: 8001
eureka:
client:
register-with-eureka: true
fetchRegistry: true
service-url:
defaultZone: http://localhost:7001/eureka,http://localhost:7002/eureka
instance:
instance-id: payment8001
#访问路径可以显示IP地址
prefer-ip-address: true
依次启动完成后,浏览器输入:http://localhost:8001/ 效果图如下:
服务提供
- 服务提供者也是一个客户 client 必须导入依赖
<!-- client -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
- 核心配置application.yml如下
server:
port: 8001
spring:
application:
name: cloud-payment-service
eureka:
client:
register-with-eureka: true
fetchRegistry: true
service-url:
defaultZone: http://localhost:7001/eureka,http://localhost:7002/eureka
instance:
instance-id: payment8001
#访问路径可以显示IP地址
prefer-ip-address: true
- 主启动类添加注解
@EnableEurekaClient //标明为客户端(服务提供者)
- 启动工程后,就可以在服务中心看到服务
cloud-payment-service
了
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-EbGTQOpJ-1606895505478)(http://favorites.ren/assets/images/2017/springcloud/eureka_server.png?ynotemdtimestamp=1606866293139)]
服务提供者就配置好了!!!
服务调用
- 调用者一般都是消费者/用户 所以应该和服务提供者一样配置进服务中心,pom文件
<!-- 导入client -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
- 核心配置文件—application.yml
server:
port: 80
spring:
application:
name: cloud-consumer-order
eureka:
client:
register-with-eureka: true
fetchRegistry: true
service-url:
defaultZone: http://localhost:7001/eureka,http://localhost:7002/eureka
- 启动类,加上
@EnableDiscoveryClient
和@EnableFeignClients
@EnableDiscoveryClient //服务注册与发现
@EnableFeignClients //远程调用
- 使用feign实现远程调用(自定义接口实现,非web调用)
@FeignClient(name = "eureka-service-provider") //属性:name,远程服务名
public interface ProviderRemoteService {
/**
* 相当于服务提供者在调用者模块中的接口,可以理解 为面向接口的编程
* @param name
* @return
*/
@RequestMapping(value = "/hello", method = RequestMethod.GET)
public String hello(@RequestParam("name") String name);
}
- 实现远程调用(web)
@Resource //实例化刚刚的那个接口 在controller中就可以直接调用
private ProviderRemoteService providerRemoteService;
@RequestMapping(value = "/sayHello", method = RequestMethod.GET)
public String sayHello(@RequestParam(value = "name") String name) {
String result = providerRemoteService.hello(name);
return "调用远程接口返回信息:" + result;
}
负载均衡
自带的负载均衡是会实现轮询提供调用
将两个服务提供者注册到一个服务中,当调用这个服务的时候会轮询调用这两个提供者
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-BquSqDPI-1606895505480)(http://favorites.ren/assets/images/2017/springcloud/eureka_server2.png)]
服务提供者1:
spring:
application:
name: cloud-payment-service
eureka:
client:
register-with-eureka: true
fetchRegistry: true
service-url:
defaultZone: http://localhost:7001/eureka,http://localhost:7002/eureka
instance:
instance-id: payment8001
#访问路径可以显示IP地址
prefer-ip-address: true
服务提供者2:
spring:
application:
name: cloud-payment-service
eureka:
client:
register-with-eureka: true
fetchRegistry: true
service-url:
defaultZone: http://localhost:7001/eureka,http://localhost:7002/eureka
instance:
instance-id: payment8002
#访问路径可以显示IP地址
prefer-ip-address: true
通过用户访问服务提供者就可以达到轮询访问 也就是我们的负载均衡了
自我保护机制
在我们的eureka服务列表上面会有一句话,红色的
EMERGENCY! EUREKA MAY BE INCORRECTLY CLAIMING INSTANCES ARE UP WHEN THEY’RE NOT. RENEWALS ARE LESSER THAN THRESHOLD AND HENCE THE INSTANCES ARE NOT BEING EXPIRED JUST TO BE SAFE.
是eureka的自我保护机制
标识在某个时刻,某一个微服务不可用了,eureka不会自动清理掉,依旧会保存该微服务的信息
eureka的设计思想是微服务架构中的cap中的ap
怎么关闭自我保护机制:
客户端每分钟会给服务端发送心跳,默认30s发送一次,而服务端90秒之内如果没收到心跳的话,如果有自我保护机制就不会立马删掉服务的信息,如果不在自我保护机制的话,则会立马停掉服务
那么,如何关闭呢?
server:
# 服务端关闭自我保护机制
enable-self-preservation: false
# 2秒之内没发送心态的服务就清理
eviction-interval-timer-in-ms: 2000
客户端的配置:
eureka:
instance:
# 30秒提交一次心跳 默认30
lease-renewal-interval-in-seconds: 30
# 90秒提交检测一次 默认90
lease-expiration-duration-in-seconds: 90
服务端90秒之内如果没收到心跳的话,如果有自我保护机制就不会立马删掉服务的信息,如果不在自我保护机制的话,则会立马停掉服务
那么,如何关闭呢?
server:
# 服务端关闭自我保护机制
enable-self-preservation: false
# 2秒之内没发送心态的服务就清理
eviction-interval-timer-in-ms: 2000
客户端的配置:
eureka:
instance:
# 30秒提交一次心跳 默认30
lease-renewal-interval-in-seconds: 30
# 90秒提交检测一次 默认90
lease-expiration-duration-in-seconds: 90
ok,搞定收工