SpringCloud封装了Netflix公司开发的Eureka模块来实现服务治理。java
在传统的RPC远程调用框架中,管理每一个服务与服务之间依赖关系比较复杂,管理比较复杂,因此须要服务治理,管理服务与服务间的依赖关系,能够实现服务调用,负载均衡,容错等,实现服务注册与发现。git
Eureka采用了CS的设计架构:Eureka Server做为服务注册功能的服务器,它是服务注册中心。而系统中的其余微服务,使用Eureka Client链接到Eureka Server并维持心跳链接。这样系统的维护人员就能够经过Eureka Server来监控系统中各个服务是否正常运行。spring
在服务注册与发现中,有一个注册中心。当服务器启动的时候,会把当前本身服务器信息【好比:服务地址、通信地址等】以别名的方式注册到注册中心上。另外一方【消费者服务提供者】,以该别名的方式去注册中心上获取到实际的服务通信地址,而后再实现本地RPC调用。api
远程调用框架核心思想:在与注册中心,由于使用注册中心管理每一个与服务之间的一个依赖关系【服务治理概念】。在任何RPC远程框架中,都会有一个注册中心【存放服务地址相关的信息:接口地址】。缓存
Eureka Server提供服务的注册服务服务器
各个微服务节点经过配置启动后,会在EurekaServer中进行注册,这样EurekaServer中的服务注册表中将会存储所服务节点的信息,服务节点的信息能够在接口中直观的看到。架构
Eureka Client经过注册中心进行访问app
是一个Java客户端,用与简化Eureka Server的交互,客户端同时也具有一个内置的,使用轮询(round-robin)的负载均衡器。在应用启动后,将会向Eureka Server发送心跳(默认周期为30s)。若是Eureka Server在多个心跳周期内没有接收到某个节点的心跳,Eureka Server将会从服务注册表中把这个服务节点移除掉(默认90s,也就是3个心跳周期).负载均衡
了解了Eureka的系统架构图以后,咱们应该很是清楚,最简单的实现也须要三个角色:服务消费者,服务提供者,注册中心EurekaServer。已知咱们已经拥有了两个角色:框架
咱们还需建立一个服务中心模块:cloud-eureka-server7001。
<!--eureka server--> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-netflix-eureka-server</artifactId> </dependency>
server: port: 7001 eureka: instance: hostname: localhost #eureka服务端的实例名称 client: register-with-eureka: false #false表示不向注册中心注册本身。 fetch-registry: false #false表示本身端就是注册中心,个人职责就是维护服务实例,并不须要去检索服务 service-url: # 设置与Eureka Server交互的地址查询服务和注册服务都须要依赖这个地址 defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka/
@SpringBootApplication @EnableEurekaServer public class EurekaServer7001Application { public static void main(String[] args) { SpringApplication.run(EurekaServer7001Application.class,args); } }
访问localhost:7001/
,出现以下界面,表示Eureka已经配置完成。但此时你会发现,第二栏出现了No instances available,由于此时尚未将两个客户端加入。
服务端已经配置,接下来就是配置注册客户端的操做。在操做以前,咱们应该可以联想,既然代表服务注册中心用的是:@EnableEurekaServer,那么是否是代表客户端也有相似的注解呢?是否是也要引入相似的依赖呢?确实,是这样的。咱们以cloud-provider-payment8001
服务为例,先试着将该服务注册进注册中心。
<dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId> </dependency>
在yml中增长一下内容:
eureka: client: #表示是否将本身注册进EurekaServer默认为true。 register-with-eureka: true #是否从EurekaServer抓取已有的注册信息,默认为true。单节点无所谓,集群必须设置为true才能配合ribbon使用负载均衡 fetchRegistry: true service-url: #单机版 defaultZone: http://localhost:7001/eureka
@EnableEurekaClient @SpringBootApplication public class Payment8001Application { public static void main(String[] args) { SpringApplication.run(Payment8001Application.class,args); } }
咱们先启动EurekaServer7001Application,再启动Payment8001Application,接着访问:localhost:7001/
,咱们能够看到Application为CLOUD-PAYMENT-SERVICE
的服务已经注册进来。
而这里的Application的名称就是咱们在yml中配置的spring.application.name=cloud-payment-service
。
ok,咱们能够照着上述步骤,将另一个客户端也注册进来,这里就不赘述了。
启动服务并注册完成后,若是停掉服务,30s后,Eureka会开启保护机制:
服务注册实际上就是将服务信息注册到注册中心中,服务发现实际上就是从注册中心中获取到服务的信息,本质上就是key-value形式信息的存入与读取。
key就是服务的名字,value就是服务调用的地址。
搭建Eureka注册中心集群,实现负载均衡和故障容错,也就是Eureka server和provider都是多个的,这防止一个注册中心故障,全部都GG。
而集群的搭建原理在于:每一个Eureka注册中心之间相互注册,相互同步心跳。
此时从父pom中查看一下module的结构:
<modules> <module>cloud-provider-payment8001</module> <module>cloud-consumer-order80</module> <module>cloud-api-commons</module> <module>cloud-eureka-server7001</module> <module>cloud-eureka-server7002</module> </modules>
在C:\Windows\System32\drivers\etc
目录下的hosts文件添加如下映射:
127.0.0.1 eureka7001.com 127.0.0.1 eureka7002.com
server: port: 7001 eureka: instance: hostname: eureka7001.com #eureka服务端的实例名称 client: register-with-eureka: false #false表示不向注册中心注册本身。 fetch-registry: false #false表示本身端就是注册中心,个人职责就是维护服务实例,并不须要去检索服务 service-url: #集群指向其它eureka defaultZone: http://eureka7002.com:7002/eureka/ ######################### 7001 < - > 7002 ############################# server: port: 7002 eureka: instance: hostname: eureka7002.com #eureka服务端的实例名称 client: register-with-eureka: false #false表示不向注册中心注册本身。 fetch-registry: false #false表示本身端就是注册中心,个人职责就是维护服务实例,并不须要去检索服务 service-url: #集群指向其它eureka defaultZone: http://eureka7001.com:7001/eureka/
访问localhost:7001/
和localhost:7002/
,发现两个中心都成功启动。固然,咱们已经配置了路径映射,访问eureka7001.com:7001/
和eureka7002.com:7002/
的效果是同样的。
单机版的时候稳定指向http://localhost:7001/eureka
,集群状态下须要改变eureka.client.service-url.defaultZone
的值:
eureka: client: #表示是否将本身注册进EurekaServer默认为true。 register-with-eureka: true #是否从EurekaServer抓取已有的注册信息,默认为true。单节点无所谓,集群必须设置为true才能配合ribbon使用负载均衡 fetchRegistry: true service-url: # #单机版 # defaultZone: http://localhost:7001/eureka # 集群版 defaultZone: http://eureka7001.com:7001/eureka,http://eureka7002.com:7002/eureka
此时两个注册中心都注册了两个客户端服务,表明已经配置完成。
咱们访问注册中心,能够发现CLOUD-PAYMENT-SERVICE对应两台提供服务者:
private static final String PAYMENT_URL = "http://CLOUD-PAYMENT-SERVICE";
@Configuration public class ApplicationContextConfig { @Bean @LoadBalanced //赋予RestTemplate负载均衡的能力 public RestTemplate restTemplate(){ return new RestTemplate(); } }
接着屡次访问:http://localhost/consumer/payment/1
,会轮换者调用不一样服务者的接口。
本系列文章为《尚硅谷SpringCloud教程》的学习笔记【版本稍微有些不一样,后续遇到bug再作相关说明】,主要作一个长期的记录,为之后学习的同窗提供示例,代码同步更新到Gitee:https://gitee.com/tqbx/spring-cloud-learning,而且以标签的形式详细区分每一个步骤,这个系列文章也会同步更新。