Spring Cloud 入門教程四、服務容錯保護:斷路器(Hystrix)

1、前言

一、爲何須要斷路器

在分佈式架構中,一個應用依賴多個服務是很是常見的,若是其中一個依賴因爲延遲太高發生阻塞,調用該依賴服務的線程就會阻塞,若是相關業務的QPS較高,就可能產生大量阻塞,從而致使該應用/服務因爲服務器資源被耗盡而拖垮。java

另外,故障也會在應用之間傳遞,若是故障服務的上游依賴較多,可能會引發服務的雪崩效應。就跟數據癱瘓,會引發依賴該數據庫的應用癱瘓是同樣的道理。git

因此,斷路器就是用來支持服務隔離、熔斷等操做的工具。斷路器會以隔離的方式來處理服務請求,當斷路數量達到閾值,就會觸發熔斷(直接返回失敗)github

二、什麼是Hystrix?

Hystrix是SOA/微服務架構中提供服務隔離、熔斷、降級機制的工具/框架。經過以上手段來下降服務故障帶來的關聯影響,以提升系統的總體可用性。spring

Hystrix is a latency and fault tolerance library designed to isolate points of access to remote systems, services and 3rd party libraries, stop cascading failure and enable resilience in complex distributed systems where failure is inevitable. -https://github.com/Netflix/Hystrix數據庫

Hystrix就是斷路器的典型表明。
Hystrix工做原理:https://ken.io/note/netflix-hystrix-intro-principlejson

三、本篇環境信息

框架 版本
Spring Boot 2.0.0.RELEASE
Spring Cloud Finchley.BUILD-SNAPSHOT
JDK 1.8.x

四、準備工做

  • 準備Eureka Server(註冊中心)、服務提供者

參考上一篇 https://ken.io/note/spring-cloud-feign-quickstart
源碼:https://github.com/ken-io/springcloud-course/tree/master/chapter-03/服務器

啓動Eureka Server: http://localhost:8800
啓動Test Service:http://localhost:8602架構

  • 瞭解服務消費者

服務消費者Ribbon: https://ken.io/note/spring-cloud-ribbon-quickstart
服務消費者Feign:
https://ken.io/note/spring-cloud-feign-quickstartapp

2、Ribbon + Hystrix應用

本篇基於 https://ken.io/note/spring-cloud-ribbon-quickstart
中ribbonclient項目代碼進行修改,引入Spring Cloud Netflix Hystrix框架

源碼:https://github.com/ken-io/springcloud-course/tree/master/chapter-02/ribbonclient

一、項目中引入Hystrix

修改pom.xml,引入Spring Cloud Netflix Hystrix

<dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
  </dependency>

二、配置Hystrix啓動類

修改啓動類App.java,增長@EnableHystrix註解開啓Hystrix

@EnableHystrix
@EnableDiscoveryClient
@SpringBootApplication
public class App {

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

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

三、斷路處理實現

修改TestService.java,增長斷路器功能

  1. 在index方法上增長註解 @HystrixCommand並經過fallbackMethod參數指定斷路後執行的方法
  2. 定義斷路處理方法,返回服務/操做斷路後的提示
@Service
public class TestService {

    @Autowired
    private RestTemplate restTemplate;

    @HystrixCommand(fallbackMethod = "indexError")
    public Object index() {
        return restTemplate.getForObject("http://testservice", String.class);
    }

    public Object plus(int numA, int numB) {
        String url = String.format("http://testservice/plus?numA=%s&numB=%s", numA, numB);
        return restTemplate.getForObject(url, String.class);
    }

    public Object indexError() {
        return "{\"code\": 999,\"message\": \"服務斷路\"}";
    }
}

四、斷路處理測試

啓動 ribbonclient 項目,
訪問:http://localhost:8604/ti ,將看到

{
  "code": 0,
  "message": "hello",
  "content": null,
  "serviceName": "testservice",
  "host": "localhost:8602"
}

關閉testservice,而後再訪問 http://localhost:8604/ti ,將看到

{
  "code": 999,
  "message": "服務斷路"
}

這就說明,當testservice不可用的時候,咱們訪問增長了Hystrix容錯措施的接口,會觸發快速失敗,當即執行fallback。而不是一直等待直到超時,很大程度上下降了形成阻塞可能。

3、Feign + Hystrix應用

本篇基於 https://ken.io/note/spring-cloud-feign-quickstart
中feignclient項目代碼進行修改
源碼:https://github.com/ken-io/springcloud-course/tree/master/chapter-03/feignclient

Feign已經引入了Hystrix,因此不須要再單獨引入

一、開啓Hystrix

修改application.yml,開啓Hystrix

feign:
  hystrix:
    enabled: true

二、斷路處理實現

  • 新建 TestServiceHystrix.java

TestServiceHystrix會做爲TestService的斷路處理實現

package io.ken.springcloud.feignclient.service;

import io.ken.springcloud.feignclient.model.Plus;
import io.ken.springcloud.feignclient.model.Result;
import org.springframework.stereotype.Component;

@Component
public class TestServiceHystrix implements TestService {

    @Override
    public String indexService() {
        return "{\"code\": 999,\"message\": \"服務斷路\"}";
    }

    @Override
    public Result plusService(int numA, int numB) {
        Result result = new Result();
        result.setCode(999);
        result.setMessage("服務斷路");
        return new Result();
    }

    @Override
    public Result plusabService(Plus plus) {
        Result result = new Result();
        result.setCode(999);
        result.setMessage("服務斷路");
        return new Result();
    }

    @Override
    public Result plus2Service(Plus plus) {
        Result result = new Result();
        result.setCode(999);
        result.setMessage("服務斷路");
        return new Result();
    }
}
  • 修改TestService,指定fallback類
@FeignClient(value = "testservice", fallback = TestServiceHystrix.class)
public interface TestService {

    @RequestMapping(value = "/", method = RequestMethod.GET)
    String indexService();

    @RequestMapping(value = "/plus", method = RequestMethod.GET)
    Result plusService(@RequestParam(name = "numA") int numA, @RequestParam(name = "numB") int numB);

    @RequestMapping(value = "/plus", method = RequestMethod.POST, consumes = "application/json")
    Result plusabService(Plus plus);

    @RequestMapping(value = "/plus2", method = RequestMethod.POST)
    Result plus2Service(@RequestBody Plus plus);


}

三、斷路處理測試

啓動 feignclient 項目

訪問:http://localhost:8605/ti ,將看到

{
  "code": 0,
  "message": "hello",
  "content": null,
  "serviceName": "testservice",
  "host": "localhost:8602"
}

關閉testservice,而後再訪問 http://localhost:8605/ti ,將看到

{
  "code": 999,
  "message": "服務斷路"
}

這就說明,當testservice不可用的時候,咱們訪問增長了Hystrix容錯措施的接口,會觸發快速失敗,當即執行fallback。而不是一直等待直到超時,很大程度上下降了形成阻塞可能。

相關文章
相關標籤/搜索