SpringCloud基础(4)
来源:互联网 发布:淘宝新店写给顾客的话 编辑:程序博客网 时间:2024/06/05 06:13
6 服务注册中心Consul
前文中介绍了Spring Cloud的核心组件,包括服务注册与发现组件Eureka,熔断器Hystrix,配置中心Spring Cloud Config和服务网关Zuul。
在前文的基础上进行工作。先将Spring Cloud的版本进行升级:将pom.xml中的parent模块版本升级为1.5.4.RELEASE,同时将spring-cloud-dependencies组件升级为Dalston.SR1版本。
Spring Cloud Consul是一个服务发现框架,与Eureka作用类似。当然常用的服务发现框架或者说服务注册中心还有Zookeeper,etcd等。对比图如下:
各个框架的具体差异就不讨论了,这里用Consul替换掉前文中的Eureka。
从官网https://www.consul.io/downloads.html下载consul服务注册中心。以开发模式启动consul:
consul agent –dev
打开http://localhost:8500,可以看到consul的ui界面。
将服务提供者的依赖模块替换:
<parent> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>1.5.4.RELEASE</version> </parent> <dependencies> <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-consul-discovery</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-actuator</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>
然后修改配置文件为:
spring.cloud.consul.host=localhostspring.cloud.consul.port=8500
服务接口修改为:
@RestControllerpublic class ComputeController { private final Logger logger = LoggerFactory.getLogger(getClass()); @Autowired DiscoveryClient discoveryClient; @GetMapping("/dc") public String dc() { String services = "Services: " + discoveryClient.getServices(); System.out.println(services); return services; }}
服务消费者依赖:
<parent> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>1.5.4.RELEASE</version> </parent> <dependencies> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-consul-discovery</artifactId> </dependency> <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-starter-test</artifactId> <scope>test</scope> </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>
配置文件:
spring.application.name=consul-consumerserver.port=2101spring.cloud.consul.host=localhostspring.cloud.consul.port=8500
服务消费者主类:
@SpringBootApplication@EnableDiscoveryClientpublic class ConsumerApplication { @Bean RestTemplate restTemplate() { return new RestTemplate(); } public static void main(String[] args) { new SpringApplicationBuilder(ConsumerApplication.class).web(true).run(args); }}
消费接口类:
@RestControllerpublic class ConsumerController { @Resource LoadBalancerClient loadBalancerClient; @Resource RestTemplate restTemplate; @GetMapping("/consumer") public String dc() { ServiceInstance serviceInstance = loadBalancerClient.choose("consul-provider1"); String url = "http://" + serviceInstance.getHost()+ ":" + serviceInstance.getPort() + "/dc"; System.out.println(url); return restTemplate.getForObject(url, String.class); }}
分别启动服务提供者和服务消费者,访问http://localhost:2101/consumer。返回Services: [consul, consul-consumer, consul-provider1]。
以上是以consul作为注册中心,如果采用eureka作为注册中心的话,除了eureka注册中心需要自己构建外,其他基本一样。
7 Hystrix监控
在前面介绍过,断路器根据快照时间窗口内的请求情况来判断是否需要进行熔断,而这些请求情况的指标信息都是HystrixCommand和HystrixObservableCommand实例在执行过程中记录的重要度量信息,它们除了Hystrix断路器实现中使用以外,对于系统运维也有非常大的帮助。这些指标信息会以“滚动时间窗”与“桶”结合的方式进行汇总,并在内存中驻留一段时间,以供内部或外部进行查询使用,Hystrix Dashboard就是这些指标内容的消费者。
创建一个服务实例my-consumer3。这里仍然以eureka为注册中心,添加依赖:
<parent> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-parent</artifactId> <version>Dalston.SR1</version> </parent> <dependencies> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-eureka</artifactId> </dependency> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-hystrix</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-actuator</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-ribbon</artifactId> </dependency> </dependencies>
配置文件为:
spring.application.name=consumer3server.port=2103eureka.client.serviceUrl.defaultZone=http://localhost:1111/eureka/
控制器为:
@RestControllerpublic class ConsumerController { @Resource ConsumerService consumerService; @GetMapping("/consumer") public String dc() { return consumerService.consumer(); } @Service class ConsumerService { @Resource RestTemplate restTemplate; @HystrixCommand(fallbackMethod = "fallback") public String consumer() { return restTemplate.getForObject("http://compute-service/add?a=1&b=2", String.class); } public String fallback() { return "fallbck"; } }}
主类需要开启@EnableCircuitBreaker注解:
@SpringBootApplication@EnableDiscoveryClient@EnableCircuitBreakerpublic class ConsumerApplication3 { @Bean @LoadBalanced RestTemplate restTemplate() { return new RestTemplate(); } public static void main(String[] args) { SpringApplication.run(ConsumerApplication3.class,args); }}
启动服务注册中心和compute-service服务实例及本实例之后,可以通过调用本实例提供的consumer接口进而调用compute-service服务。
接着创建mysc-hystrixdashboard实例。依赖:
<parent> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-parent</artifactId> <version>Dalston.SR1</version> </parent> <dependencies> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-hystrix</artifactId> </dependency> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-hystrix-dashboard</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-actuator</artifactId> </dependency></dependencies>
配置文件:
spring.application.name=hystrix-dashboardserver.port=1301
主类:
@SpringCloudApplication@EnableHystrixDashboardpublic class HystrixDashboardApplication { public static void main(String[] args) { SpringApplication.run(HystrixDashboardApplication.class,args); }}
实际上,官方也提供了监控包:hystrix-dashboard-#.#.#.war,下载后放到服务器上,一样地使用。不过这里为了方便就使用自己创建的监控实例。
启动hystrix监控实例,访问http://localhost:1301后可以看到Hystrix Dashboard首页。从首页描述可以得知,Hystrix Dashboard支持三种不同的监控方式,分别是:
默认的集群监控:通过URLhttp://turbine-hostname:port/turbine.stream开启,实现对默认集群的监控。
指定的集群监控:通过URLhttp://turbine-hostname:port/turbine.stream?cluster=[clusterName]开启,实现对clusterName集群的监控。
单体应用的监控:通过URLhttp://hystrix-app:port/hystrix.stream开启,实现对具体某个服务实例的监控。
对集群的监控需要整合turbine才能实现。这里先看对单个服务实例的监控。再consumer3实例中引入了actuator和hystrix依赖包,因此可以实现对该实例的hystrix监控。
7.1 单实例监控
启动consumer3,调用一次consumer3提供的consumer接口(如果一次都没调用,监控页面就一直在loading中)。接着访问http://localhost:1301/hystrix,在输入框中输入要监控的实例地址:http://localhost:2103/hystrix.stream,可以看到该实例的hystrix监控信息。
监控台首页中有两个参数,分别是Delay和Title。其中Delay是用来控制服务器上轮询监控信息的延迟时间,默认为2000毫秒,可以通过配置该属性降低客户端的网络和cpu消耗。Title对应了监控地址的内容,默认使用具体监控实例的url,可以通过配置该信息来展示更合适的标题。
具体实例的监控页面可以看到一个实心圆和一条曲线。
实心圆:共有两种含义。它通过颜色的变化代表了实例的健康程度,其健康度从绿色,黄色,橙色。红色依次递减。同时,实心圆的大小随着请求流量发生变化,流量越大该实心圆就越大。所以通过该实心圆的大小和颜色,可以在大量实例中快速发现故障实例和高压力实例。
曲线:用来记录两分钟内流量的相对变化,可以通过它来观察流量的上升和下降趋势。
其他:竖线隔开的两列数字,左边的依次代表请求成功数,短路和熔断数。右边的依次代表请求超时数,线程池拒绝数和失败/异常数。右边百分数代表最近10秒的错误比例。Host和Cluster数值表示该主机和集群上的请求频率,Circuit表示断路器状态。最下面左侧的是集群下的主机报告,右侧的是百分比延迟统计。
7.2 监控数据聚合
在实际的生产环境中有多个实例,对多实例需要将度量指标数据进行聚合,因此需要整合turbine。
在前文的hystrix监控例子中,实现的架构如下图所示:
在上述架构基础上,引入Turbine来对服务的Hystrix数据进行聚合展示。聚合方式有两种。
通过HTTP收集聚合
创建turbine工程,依赖为:
<parent> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-parent</artifactId> <version>Dalston.SR1</version> </parent> <dependencies> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-turbine</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-actuator</artifactId> </dependency></dependencies>
创建应用主类TurbineApplication,并使用@EnableTurbine注解开启Turbine:
@Configuration@EnableAutoConfiguration@EnableTurbine@EnableDiscoveryClientpublic class TurbineApplication { public static void main(String[] args) { SpringApplication.run(TurbineApplication.class, args); }}
在application.properties加入eureka和turbine的相关配置,具体如下:
spring.application.name=turbineserver.port=8989management.port=8990eureka.client.serviceUrl.defaultZone=http://localhost:1111/eureka/turbine.app-config=consumer3turbine.cluster-name-expression="default"turbine.combine-host-port=true
参数说明:
turbine.app-config指定了需要收集监控信息的服务名。
turbine.cluster-name-expression指定了集群名称为default,当服务数量非常多时,可以启动多个turbine服务来构建不同的聚合集群,而该参数可以用来区分这些不同的聚合集群,同时该参数可以在Hystrix仪表盘中定位不同的聚合集群,只需要在Hystrix Stream的URL中通过cluster参数来指定。
turbine.combine-host-port设置为true,可以让同一主机上的服务通过主机名与端口号的组合来进行区分,默认情况下以host来区分不同的服务,这会使得在本地调试时本机上的不同服务聚合成一个服务来统计。
启动服务注册中心server1和server2,服务提供者provider2,服务消费者consumer3,Hystrix监控以及turbine聚合实例,在http://localhost:1301/hystrix监控首页中输入http://localhost:8989/turbine.stream后进行监控,将会看到针对服务consumer3的聚合数据监控。架构为:
通过消息代理收集聚合
Spring Cloud在封装turbine的时候,还实现了基于消息代理的收集实现。因此可以将所有需要收集的监控信息都输出到消息代理中,然后turbine服务再从消息代理中异步的获取这些监控信息,最后将这些监控信息聚合并输出到Hystrix Dashboard中。通过引入消息代理,Turbine和Hystrix Dashboard实现的监控架构可以改成如下:
创建一个maven工程,名为mysc-turbinemq。在pom.xml中添加依赖:
<parent> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-parent</artifactId> <version>Dalston.SR1</version></parent><dependencies> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-turbine-amqp</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-actuator</artifactId> </dependency></dependencies>
这里的spring-cloud-starter-turbine-amqp实际上包装了spring-cloud-starter-turbine-stream和pring-cloud-starter-stream-rabbit。
在主类中开启@EnableTurbineStream注解:
@SpringBootApplication@EnableAutoConfiguration@EnableTurbineStreampublic class TurbinemqApplication { public static void main(String[] args) { SpringApplication.run(TurbinemqApplication.class,args); }}
配置application.properties文件:
spring.application.name=turbine-amqpserver.port=8989management.port=8990eureka.client.serviceUrl.defaultZone=http://localhost:1111/eureka/
然后在消费者consumer3中的pom.xml文件修改一下,添加对amqp的依赖,使监控信息能输出到消息队列里:
<dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-netflix-hystrix-amqp</artifactId></dependency>
然后停止前文的turbine聚合实例,启动turbinemq实例,访问监控页面,可以实现同样的监控效果,但这里的监控信息收集是通过消息代理异步实现的。
代码地址:https://github.com/howetong/mysc/tree/branch1
- SpringCloud基础(4)
- SpringCloud基础(1)
- SpringCloud基础(0)
- SpringCloud基础(2)
- SpringCloud基础(3)
- SpringCloud基础(5)
- 探索SpringCloud一(基础概念)
- springCloud基础配置
- SpringCloud零基础上手(三)——服务注册
- SpringCloud笔记(1):微服务介绍,SpringBoot基础
- 【SpringCloud】(一):SpringCloud入门程序
- springcloud学习4(断路器)
- springcloud常见问题(四)
- springcloud常见问题(三)
- springcloud入门(1)
- Springcloud学习(一)
- SpringCloud--断路器(Hystrix)
- SpringCloud:断路器(Hystrix)
- 【51Nod1836】战忽局的手段
- Java学习第四天
- TI am335x 内核分析2--资源遍历代码分析
- Viewpager+滚动+ta...(代码)
- git bash命令
- SpringCloud基础(4)
- NFS挂载的安装部署和一些记录
- 关于纯C中如何向函数传递结构体指针的记载
- canvas移动端画板
- 文件在线预览和下载的实现
- Softmax函数
- Android之使用GPS和NetWork定位
- 获取手机型号
- BZOJ 1655 [Usaco2006 Jan] Dollar Dayz 奶牛商店 01背包+高精度