1 Eureka是什么

Eureka是Spring Cloud Netflix的一个子模块,也是核心模块之一。Eureka是一个基于REST的服务,用于定位服务,以实现云端中间层服务发现和故障转移。

服务注册与发现对于微服务架构来说是非常重要的,有了服务发现与注册,只需要使用服务的标识符,就可以访问到服务,而不需要修改服务调用的配置文件了。功能类似于dubbo的注册中心,比如Zookeeper。

2 基本概念

Register:服务注册

服务提供者向Eureka Serve注册,注册发生在第一次心跳,它提供关于自己的元数据(诸如主机和端口,健康指标URL等)Eureka Server。

Renew:服务续约

Eureka客户会每隔30秒发送一次心跳来续约。 通过续约来告知Eureka Server该Eureka客户仍然存在,没有出现问题。 正常情况下,如果Eureka Server在90秒没有收到Eureka客户的续约,它会将实例从其注册表中删除。 建议不要更改续约间隔。

注册信息和续订被复制到集群中的Eureka Serve所有节点。 来自任何区域的Eureka Client都可以查找注册表信息(每30秒发生一次)。根据这些注册表信息,Application Client可以远程调用Applicaton Service来消费服务

Fetch Registries:获取注册列表信息

Eureka客户端从服务器获取注册表信息,并将其缓存在本地。客户端会使用该信息查找其他服务,从而进行远程调用。该注册列表信息定期(每30秒钟)更新一次。每次返回注册列表信息可能与Eureka客户端的缓存信息不同, Eureka客户端自动处理。

如果由于某种原因导致注册列表信息不能及时匹配,Eureka客户端则会重新获取整个注册表信息。 Eureka服务器缓存注册列表信息,默认的情况下Eureka客户端使用压缩JSON格式来获取注册列表的信息。

Cancel:服务下线

Eureka客户端在程序关闭时向Eureka服务器发送取消请求。 发送请求后,该客户端实例信息将从服务器的实例注册表中删除。

Eviction 服务剔除

Eviction用来定期(默认为每60秒)在Eureka Server检测失效的服务,检测标准就是超过一定时间没有Renew的服务,默认失效时间为90秒,也就是如果有服务超过90秒没有向Eureka Server发起Renew请求的话,就会被当做失效服务剔除掉, Eureka服务器会将该服务实例从服务注册列表删除。

3 自我保护模式

概述

保护模式主要用于一组客户端和Eureka Server之间存在网络分区场景下的保护。一旦进入保护模式,Eureka Server将会尝试保护其服务注册表中的信息,不再删除服务注册表中的数据,也就是不会注销任何微服务。

如果在Eureka Server的首页看到以下这段提示,则说明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 Server出现时,它尝试从相邻节点获取所有实例注册表信息。如果从Peer节点获取信息时出现问题,Eureka Serve会尝试其他的Peer节点。如果服务器能够成功获取所有实例,则根据该信息设置应该接收的更新阈值。如果有任何时间,Eureka Serve接收到的续约低于为该值配置的百分比(默认为15分钟内低于85%),则服务器开启自我保护模式,即不再剔除注册列表的信息。

这样做的好处就是,如果是Eureka Server自身的网络问题,导致Eureka Client的续约不上,Eureka Client的注册列表信息不再被删除,也就是Eureka Client还可以被其他服务消费。

4 组件

Eureka包含两个组件:Eureka Server和Eureka Client

1:Eureka Server提供服务注册服务,各个节点启动后,会在Eureka Server中进行注册,这样Eureka Server中的服务注册表中将会存储所有可用服务节点的信息,服务节点的信息可以在界面中直观的看到

2:Eureka Client是一个Java客户端,用于简化Eureka Server的交互,客户端同时也具备一个内置的、使用轮询(round-robin)负载算法的负载均衡器。在应用启动后,将会向Eureka Server发送心跳(默认周期为30秒)。如果Eureka Server在多个心跳周期内没有接收到某个节点的心跳,Eureka Server将会从服务注册表中把这个服务节点移除(默认90秒)

3:Eureka Server之间将会通过复制的方式完成数据的同步。Eureka还提供了客户端缓存的机制,即使所有的Eureka Server都挂掉了,客户端依然可以利用缓存中的信息消费其它服务的API。Eureka通过心跳检测、健康检查、客户端缓存等机制,确保了系统的高可用性、灵活性和可伸缩性。

5 测试实战

创建一个SpringBoot项目,用来当作Eureka Server

5.1 注册中心Eureka

5.1.1 添加依赖

Springboot还是采用1.5.6.RELEASE

org.springframework.boot

spring-boot-starter-parent

1.5.6.RELEASE

5.1.2 Eureka Server的依赖

org.springframework.cloud

spring-cloud-starter-eureka-server

5.1.3 添加SpringCloud版本的依赖

org.springframework.cloud

spring-cloud-dependencies

Dalston.RELEASE

pom

import

5.1.4 添加spring-boot-maven-plugin

org.springframework.boot

spring-boot-maven-plugin

5.1.5 添加启动注解

在SpringBoot的启动类上添加:@EnableEurekaServer

5.1.6 配置

可以采用properties或者yml,比如application.yml,示例如下:

server:

port: 8761

eureka:

instance:

hostname: localhost

#是否优选使用ip地址

prefer-ip-address: true

client:

#启动是否注册

registerWithEureka: false

#是否获取注册列表

fetchRegistry: false

serviceUrl:

defaultZone: http://localhost:8761/eureka/

5.1.7 启动

1.5.2 服务提供者

依赖基本跟Eureka Server的项目一样,但不是依赖Eureka Server了,而是:

org.springframework.cloud

spring-cloud-starter-eureka

配置

可以采用properties或者yml,比如application.yml,示例如下:

eureka:

client:

serviceUrl:

defaultZone: http://localhost:8761/eureka/

server:

port: 8765

spring:

application:

name: userService

1.5.2.1 添加注解

在启动类上添加@EnableDiscoveryClient或者@EnableEurekaClient

1:对Eureka Server而言,服务提供者和服务消费者,都是Eureka Server的Client,都是用一样的注解

2:两者区别:

SpringCloud中的“Discovery Service”有多种实现,比如:eureka, consul, zookeeper等。@EnableDiscoveryClient注解是基于spring-cloud-commons依赖,可以在不同的服务注册服务器上使用; @EnableEurekaClient注解是基于spring-cloud-netflix依赖,只能为eureka用

开发服务对外提供REST服务的Controller,以及具体的服务实现

1.5.3 服务消费者

创建一个SpringBoot项目,用来当作服务消费者

依赖基本跟服务提供者的项目一样

配置

可以采用properties或者yml,比如application.yml,示例如下:

eureka:

client:

serviceUrl:

defaultZone: http://localhost:8761/eureka/

server:

port: 8764

spring:

application:

name: userConsumer

在启动类上添加@EnableDiscoveryClient或者@EnableEurekaClient

开发Controller

做一个配置Bean,用来提供RestTemplate

开发具体的服务实现,例如:

@Service

public class UserService {

@Autowired

private RestTemplate restTemplate;

@Autowired

private EurekaClient discoveryClient;

public String hiService(String name) {

InstanceInfo instance = discoveryClient.getNextServerFromEureka("userService", false);

String path = instance.getHomePageUrl();

String ret = restTemplate.getForObject(path+"/userServiceProvider?name="+name,String.class);

return ret;

}

}

![image.png](https://upload-images.jianshu.io/upload_images/23729306-6a5b6aab6b9324ff.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)

![image.png](https://upload-images.jianshu.io/upload_images/23729306-b17d56e901d9c4f4.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)

# 6 Eureka高层架构

![image.png](https://upload-images.jianshu.io/upload_images/23729306-baaba7f8d19ef513.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)

# 7 疑问

- 注册延迟:Eureka Client一启动,不是立即向Eureka Server注册,它有一个延迟向服务端注册的时间,也就是会定期发送心跳到注册表,默认持续时间为30秒。

- Eureka Server的响应缓存:Eureka Server维护每30秒更新的响应缓存,可通过更改配置eureka.server.responseCacheUpdateIntervalMs来修改。 所以即使实例刚刚注册,它也不会出现在返回给客户的结果中

- Eureka Server刷新缓存:Eureka客户端保留注册表信息的缓存。该缓存每30秒更新一次

- 因而极端情况下可能需要3个心跳,客户端才能发现服务。

- 可以使用eureka.instance.leaseRenewalIntervalInSeconds更改期限,这将加快客户端连接到其他服务的过程。在生产中,最好坚持使用默认值,因为服务器内部有一些计算可以对租赁更新期进行假设。

# 8 Eureka与zookeeper对比

- 回忆一下分布式系统的CAP理论:

一致性(C):系统在执行过某项操作后仍然处于一致的,在分布式系统中,更新操作执行成功后所有的用户都应该读取到最新的值,这样的系统被认为具有强一致性。

可用性(A):每个请求都能接受到一个响应,无论响应成功或失败。

分区容错性(P):系统在存在网络分区的情况下仍然可以接受请求并处理,这里网络分区是指由于某种原因网络被分成若干个孤立区域,而区域之间互不相通。

由于分区容错性在是分布式系统中必须要保证的,因此只能在A和C之间进行权衡。Zookeeper保证的是CP, 而Eureka则是AP。

- Zookeeper保证CP

在任何时刻对ZooKeeper的访问请求能得到一致的数据结果,同时系统对网络分割具备容错性、但是它不能保证每次服务请求的可用性,也就是在极端环境下,ZooKeeper可能会丢弃一些请求,消费者程序需要重新请求才能获得结果,比如重新选举leader的时间太长,且选举期间整个zk集群都是不可用的,这就导致在选举期间注册服务瘫痪。

- Eureka保证AP

实际应用中,我们可以容忍注册中心返回的是几分钟以前的注册信息,但不能接受服务直接down掉不可用,也就是说,服务注册功能对可用性的要求要高于一致性。

Eureka服务节点在短时间里丢失了大量的心跳连接,那么这个 Eureka节点会进入“自我保护模式”,同时保留那些“心跳死亡”的服务注册信息不过期。此时,这个Eureka节点对于新的服务还能提供注册服务,对于“死亡”的仍然保留,以防还有客户端向其发起请求。当网络故障恢复后,这个Eureka节点会退出“自我保护模式”。Eureka的哲学是,同时保留“好数据”与“坏数据”总比丢掉任何数据要更好。

# 9 Eureka集群

构建Eureka Server 集群

- 启动多个Eureka Server,配置defaultZone为其它的Eureka Server

- 客户端连接的时候, defaultZone的值可以写多个,用逗号区分

**深入理解**

实际应用中,因负载等原因,往往可能需要在生产环境构建多于两个的Eureka Server节点。那么对于如何配置serviceUrl来让集群中的服务进行同步,需要我们更深入的理解节点间的同步机制来做出决策。

Eureka Server的同步遵循着一个非常简单的原则:只要有一条边将节点连接,就可以进行信息传播与同步。

1:两两注册的方式可以实现集群中节点完全对等的效果,实现最高可用性集群,任何一台注册中心故障都不会影响服务的注册与发现

2:Eureka Server具备单方面有指向的服务传播与同步机制,在一些对服务发现有限制的情况下,可以利用这样的机制进行服务注册与发现的的单向控制

部署集群后同一路径访问:切换不同的服务返回结果

![image.png](https://upload-images.jianshu.io/upload_images/23729306-67b246bc6973d474.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)

![image.png](https://upload-images.jianshu.io/upload_images/23729306-ce3ff3439aed5003.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)

# 10 Eureka Server之间通信

1:Eureka Client首先会尝试与同一区域的Eureka Server进行连接,如果出现问题,或者服务器不在同一个区域中,则客户端将故障转移到其他区域中的服务器。

2:一旦服务器开始接收流量,在服务器上执行的所有操作都将被复制到服务器知道的所有对等节点。如果某个操作由于某种原因而失败,那么该信息将在下一个在服务器之间复制的心跳信号进行核对。

3:当Eureka服务器启动时,它会尝试从邻居节点获取所有实例注册表信息。如果在从节点获取信息时出现问题,服务器在放弃之前尝试所有的对等点。如果服务器能够成功获取所有实例,则会根据该信息设置应该接收的更新阈值。如果任何时候,续订低于为该值配置的百分比(在15分钟内低于85%),则服务器将停止到期实例以保护当前实例注册表信息。也就是进入自我保护模式。

在这种情况下,如果服务器无法从邻居节点获取注册表信息,则会等待几分钟(5分钟),以便客户端可以注册其信息。此时注册可能发生在孤立的服务器上,有些客户端可能会反映新的注册,而其他客户端可能不会。在网络连接恢复到稳定状态后,情况会自动自动更正。当对等方能够正常通信时,注册信息会自动同步。

### 1.10.1 Peer之间的状态同步

Service Provider只需要通知到任意一个Eureka Server后就能保证状态会在所有的Eureka Server中得到更新。

具体实现方式其实很简单,就是接收到Service Provider请求的Eureka Server,把请求再次转发到其它的Eureka Server,调用同样的接口,传入同样的参数,除了会在header中标记isReplication=true,从而避免重复的replicate。

Peer之间的状态是采用异步的方式同步的,所以不保证节点间的状态一定是一致的,不过基本能保证最终状态是一致的。

### 1.10.2 Eureka Server是怎么知道有多少Peer的呢?

Eureka Server在启动后会调用EurekaClientConfig.getEurekaServerServiceUrls来获取所有的Peer节点,并且会定期更新。定期更新频率可以通过eureka.server.peerEurekaNodesUpdateIntervalMs配置。

这个方法的默认实现是从配置文件读取,所以如果Eureka Server节点相对固定的话,可以通过在配置文件中配置来实现。

如果希望能更灵活的控制Eureka Server节点,比如动态扩容/缩容,那么可以覆盖getEurekaServerServiceUrls方法,提供自己的实现,比如通过数据库读取Eureka Server列表

# 11 配置选项

1:SpringCloud中的配置选项可以参看官方文档:http://cloud.spring.io/spring-cloud-static/Dalston.SR4/single/spring-cloud.html#_appendix_compendium_of_configuration_properties

2:客户端的默认配置,在Eureka中是 https://github.com/Netflix/eureka/blob/master/eureka-client/src/main/java/com/netflix/discovery/DefaultEurekaClientConfig.java

在SpringCloud结合Netflix中是:https://github.com/spring-cloud/spring-cloud-netflix/tree/master/spring-cloud-netflix-eureka-client/src/main/java/org/springframework/cloud/netflix/eureka/EurekaClientConfigBean.java

3:服务端的默认配置,在Eureka中是:https://github.com/Netflix/eureka/blob/master/eureka-core/src/main/java/com/netflix/eureka/DefaultEurekaServerConfig.java

在SpringCloud结合Netflix中是:

https://github.com/spring-cloud/spring-cloud-netflix/tree/master/spring-cloud-netflix-eureka-client/src/main/java/org/springframework/cloud/netflix/eureka/EurekaInstanceConfigBean.java

# 12 添加链接权限

n 添加依赖

org.springframework.boot

spring-boot-starter-security

n 在配置文件中添加,示例如下:

security:

basic:

enbled: true

user:

name: admin

password: admin

消费者的连接方式

也需要用户名和密码,否则会报错,示例如下:

defaultZone: http://admin:cc@localhost:8761/eureka/

# 13 状态页和健康指标

1:Eureka实例的状态页面和运行状况指示器分别默认为“/info”和“/health”,它们是Spring Boot中端点的默认位置。

2:默认情况下,Spring CLoud Eureka中各个服务实例的健康检测并不是通过spring-boot-actuator模块的/health端点来实现的,而是依靠客户端心跳的方式来保持服务实例的存活。因此,默认的心跳方式作为健康检测并不保险,因为不能检测服务是否能有效提供服务

可以通过简单的配置,把Eureka客户端的健康检测交给spring-boot-actuator模块的/health端点,以实现更加全面的健康状态维护。 详细步骤如下:

(1)在pom.xml中引入spring-boot-starter-actuator模块的依赖

(2)在application.properties中增加参数配置eureka.client.healthcheck.enabled=true

3:如果要使用非默认上下文路径或servlet路径(例如server.servletPath=/foo)或管理端点路径(例如management.contextPath=/admin),则需要更改,如:

eureka:

instance:

statusPageUrlPath: ${management.context-path}/info

healthCheckUrlPath: ${management.context-path}/health

>继续学习吧~~哈哈,我给大家来了硬广,cc老师创立的私塾在线现在推出2020年高级架构师课程培训课程现在折扣才6800元,包含300+录,60+直播,面试技巧等课程内容,惊喜多多!详情都在私塾的官网,感兴趣的小伙伴,可以一起去 【***[私塾在线](http://sishuok.com)*** 】 学习

eureka动态扩容_SpringCloud- 第二篇 Eureka快速上手相关推荐

  1. 学习动态性能表 第二篇--v$sesstat

    学习动态性能表 第二篇--v$sesstat  按照OracleOnlineBook中的描述,v$sesstat存储session从login到logout的详细资源使用统计. 类似于v$syssta ...

  2. Docker基础篇之快速上手

    下载md查看 链接:https://pan.baidu.com/s/1ocFFFlOvGZdXBDgJovZ8tA 提取码:atm3 Docker基础篇之快速上手 第一章 Docker简介 是什么? ...

  3. 【JavaWeb篇】快速上手Tomcat|实战项目详解

    作者主页:橙子! 主页 系列专栏:JavaWeb基础教程系列 精彩回顾:HTTP协议详解 文章目的:Web服务器TomCat的使用以及配置问题 文章目录 前言 1.Web服务器 2.Tomcat简介 ...

  4. Flink(初识Flink,快速上手)

    目录 初识Flink Flink设计理念 Flink的应用 Flink在企业中的应用 Flink的主要应用场景 流式数据处理的发展和演变 流处理和批处理 传统事务处理 有状态的流处理 Lambda 架 ...

  5. matlab如何测两点的角度_【邢不行|量化小讲堂系列01-Python量化入门】如何快速上手使用Python进行金融数据分析...

    引言: 邢不行的系列帖子"量化小讲堂",通过实际案例教初学者使用python进行量化投资,了解行业研究方向,希望能对大家有帮助. [历史文章汇总]请点击此处 [必读文章]: [邢不 ...

  6. 快速上手Linux核心命令(一):核心命令简介

    Linux核心命令系列文章目录 快速上手Linux核心命令(一):核心命令简介 快速上手Linux核心命令(二):关机.重启 快速上手Linux核心命令(三):文件和目录操作命令 快速上手Linux核 ...

  7. 第二篇:SpringCloud 服务的注册与发现Eureka(Dalston.SR5版本)

    一.创建父工程 1 首先创建一个maven父工程. <?xml version="1.0" encoding="UTF-8"?> <proje ...

  8. eureka server配置_springcloud+eureka整合分布式事务中间件seata

    今天继续给大家分享一下阿里的分布式事务中间件seata的使用,跟上篇文章<springboot多数据源整合分布式事务中间件seata>不一样的是,上篇文章是单服务绑定多数据源的分布式情况, ...

  9. asp.net signalR 专题—— 第二篇 对PersistentConnection持久连接的快速讲解

    上一篇我们快速的搭建了一个小案例,但是并没有对其中的方法进行介绍,这一篇我来逐一解析下. 一:从override的那些方法说起 不管怎么样,我们先上代码,如下: 1 public class MyCo ...

最新文章

  1. 【CV】PAA论文解读:在物体检测中利用概率分布来将anchor分配为正负样本
  2. ASP.NET前台代码绑定后台变量方法总结
  3. 过程作为黑箱抽象——《计算机程序的构造和解释》
  4. 面试官:谈谈Redis缓存和MySQL数据一致性问题
  5. c语言中数组名a和a详细介绍
  6. GridView分页后RowCommand出错:索引超出范围
  7. Quartz2 定时器 《一》(概述)
  8. 职高学计算机走单招是,职高学生不用愁了,还有机会上本科,走“单招”或是最佳途径!...
  9. Linux E325: ATTENTION Found a swap file by the name “./.backu.sh.swp“
  10. 调试 高通_高通平台调整通话音量
  11. MySQL5.7版本安装
  12. Linux操作系统[下载安装][命令][工具使用]
  13. jmeter压力测试+badboy脚本录制
  14. Devops知识技能树(译)
  15. 如何显示手机gps定位服务器,手机gps定位服务器设置
  16. 蓝桥杯 历年试题 矩阵翻硬币
  17. 2022高频经典前端面试题(html+css+js上篇,含答案)
  18. 动态监控zookeeper服务节点变动(附zkUI使用)
  19. 计算机组成原理及汇编语言程序设计 179页4-24题 假设(AX)=0FF60H,有以下程序段:
  20. VxWorks中tornado2.2中的编译器支持哪个C语言标准,有哪些标准库?

热门文章

  1. MySQL Processlist 讲解
  2. 带下划线的二级域名IE无法读取session
  3. 《虚无的十字架》—— 读后总结
  4. 【iCore4 双核心板_uC/OS-II】例程一:认识 uC/OS-II
  5. java怎样读取数据库表中字段的数据类型?
  6. js:select的选择改变事件,获取当前选择的值
  7. Java中常用的加密算法MD5,SHA,RSA
  8. 关于dependency的scope
  9. 【转】其实Unix很简单
  10. 转:Real6410 Linux 常见问题总结(截至2010/07/26)