您的位置:首页 > 编程语言 > Java开发

Spring Cloud Eureka+Ribbon+Hystrix

2017-08-27 21:20 645 查看
把这三个那来一起讲,是因为这是Spring cloud中最基础的架构,后续的高级配件都是围绕它们来做出优化和升级。
 
Eureka:注册中心,单个微服务将自己注册到eureka上供其它服务调用。
Ribbon:客户端负载均衡,负责对eureka中的服务进行调用。
Hystrix:客户端容错保护,负责当ribbon出现问题时保证整个服务的畅通。
 
基于代码来学习下,创建3个服务:
服务A作为服务中心:https://github.com/yejingtao/forblog/tree/master/demo-eureka-register
服务B作为服务注册到服务A中:https://github.com/yejingtao/forblog/tree/master/demo-eureka-server
服务C调用服务B:https://github.com/yejingtao/forblog/tree/master/demo-eureka-consumer
 
服务A Eureka中心:
Pom依赖
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-eureka-server</artifactId>
</dependency>
</dependencies>

<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>Dalston.SR1</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>


(注意cloud的Dalston版本对应boot的1.5版本)
配置文件有3个,其中pee1+peer2是高可用性集群,application.properties是单结点注册中心。
application-peer1.properties
server.port:1111
spring.application.name:eureka-register
eureka.instance.hostname:peer1
eureka.client.serviceUrl.defaultZone:http://peer2:1112/eureka/


application-peer2.properties
server.port:1112
spring.application.name:eureka-register
eureka.instance.hostname:peer2
eureka.client.serviceUrl.defaultZone:http://peer1:1111/eureka/


application.properties
server.port:1111
spring.application.name:eureka-register
eureka.instance.hostname:peer1
eureka.client.registerWithEureka=false
eureka.client.fetchRegistry=false
eureka.client.serviceUrl.defaultZone:http://peer1:1111/eureka/


配置的区别终于在与2个:
eureka.client.registerWithEureka //要不要把自己作为服务注册到eureka
eureka.client.fetchRegistry //要不要去检索服务
这两个默认都是true,多个eureka可以互相注册互相检索组成一个高可用性的集群,如果要搭建单结点注册中心这俩需要配置成false。
eureka.client.serviceUrl.defaultZone//注册中心地址,留给微服务结点配置的地址。
这里peer1和peer2因为要做集群所以要互相注册,配置对方的地址。
服务组测不需要任何逻辑,所以代码很简单只是启动一个SpringBoot的服务,增加一个@EnableEurekaServer注解启动eureka。
为了架构的高可用性我这里决定使用peer1+peer2双结点,eureka启动命令是:
java –jar demo-eureka-register.jar –spring.profiles.active=peer1
java –jar demo-eureka-register.jar –spring.profiles.active=peer2
 
服务B:代码很简单,只是提供一个RestFul服务。
Pom依赖
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-eureka</artifactId>
</dependency>


application.yml
server:
port: 8081
spring:
application:
name: hello-service
eureka:
client:
serviceUrl:
defaultZone: http://peer1:1111/eureka/,http://peer2:1112/eureka/


配置主要有2个,自己注册到eureka上的服务名;Eureka
server的地址,多个地址以逗号隔开.
服务代码
@SpringBootApplication
@EnableEurekaClient
@RestController
public class ServiceDemoApplication {

public static void main(String[] args) {
SpringApplication.run(ServiceDemoApplication.class, args);
}

@Value("${server.port}")
String port;

@RequestMapping("/hi")
public String home(@RequestParam String name) {
return "hi "+name+",i am from port:" +port;
}
}


@EnableEurekaClient代表自己是注册中心的客户端
 
服务C:Ribbon+Hystrix作为客户端访问注册中心上的服务B
Pom依赖
<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>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-hystrix</artifactId>
</dependency>
依赖了eureka、ribbon和hystrix。

配置没有特殊的,最主要的就是eureka的地址。
主程序:

//@SpringBootApplication
//@EnableEurekaClient
//@EnableCircuitBreaker
@SpringCloudApplication
public class ConsumerApplication {

public static void main(String[] args) {
SpringApplication.run(ConsumerApplication.class,args);
}

@Bean
@LoadBalanced
RestTemplate restTemplate() {
return new RestTemplate();
}
}


这里只用了@SpringCloudApplication一个注解,因为它包含了其它3个,从名字也可以看得出这是Spring cloud代码的标配。其中@EnableCircuitBreaker是Hystrix的服务熔断。
restTemplate是访问eureka上应用的客户端,因为我的eureka服务端是peer1+peer2双结点的,所以用了@LoadBalanced负责均衡(这里的是客户端负载均衡,与F5、Apache等服务端负载均衡原理差异性很大)。

@Service
public class HelloService {

@Autowired
private RestTemplate restTemplate;

@HystrixCommand(fallbackMethod="hellServiceFallback")
public String sayHello() {
return restTemplate.getForEntity("http://HELLO-SERVICE/hi?name=yejingtao", String.class).getBody();
}

@SuppressWarnings("unused")
private String hellServiceFallback() {
return "error";
}

}

 restTemplate.getForEntity("http://HELLO-SERVICE/hi?name=yejingtao", String.class).getBody()//用get的方式访问eureka上hello-service上的服务,返回类型是String。

@HystrixCommand(fallbackMethod="hellServiceFallback")//hystrix熔断后服务降级为hellServiceFallback来提供服务。

下面介绍下这几个服务的需要加强学习的知识点。

Eureka:

eureka.instance.lease-renewal-interval-in-seconds=30
eureka.instance.lease-expiratioin-duration-in-seconds=90
失效剔除:超过90秒eureka没有收到客户端上来的心跳就认为此服务挂了,从注册中心剔除出去(心跳是主动上报的,而不是eureka去访问客户端的/health)
自我保护:如果一段时间内eureka管理的85%的服务都失去了心跳,eureka会启动保护机制,它会认为是eureka服务自己所在的网络出现了问题,而不去启用失效剔除机制,继续让注册上来的应用提供服务。

Ribbon的几个特性:
1, 区域亲和策略。可以将同一机房的微服务结点配置成同一个zone,ribbon在对服务进行请求时优先选择跟自己同一个zone的结点。eureka.instance.metadataMap.zone=zoneName
2, 重试机制
默认关闭的,需要配置手动打开:spring.cloud.loadbalance.retry.enabled=true
        service-name.ribbon.ConnectTimeOut:请求连接超时时间
        service-name.ribbon.ReadTimeout:请求处理超时时间
        service-name.ribbon.MaxAutoRetries:对当前实例的重试次数
        service-name.ribbon.MaxAutoRetriesNextServer:切换实例的重试次数
        因为微服务中对同一个服务的提供是多结点负载均衡的,如果配置了重试机制,ribbon会先对本次要请求的结点尝试MaxAutoRetriesNextServer次重试,如果还不行就会尝试MaxAutoRetriesNextServer次切换到同一服务的其它结点来提供服务。

Hystrix熔断器:当某个服务单元发生故障之后向调用方返回一个错误而不是一直等待,避免了故障在分布式系统中的蔓延,防止因为一个或几个服务节点的故障导致整个框架的崩盘。
服务降级:fallback是Hystrix执行失败的后备服务,fallback也可以发起另一个Hystrix请求。
服务熔断:只有当超过断容器请求数而且失败次数大约一定概率时,才会启动熔断机制。默认是请求20次以上失败50%就启动断熔。
请求缓存:客户端缓存,减少对服务端的http交互次数。@CacheResult、@CacheRemove
请求合并:也是为了减少http通信上的消费,但是request和response合并和分解也有很大的性能开销,所以要根据场景慎用。
依赖隔离:线程池方式和信号量方式。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息