1. 程式人生 > 實用技巧 >spingcloud(6)hystrix服務降級

spingcloud(6)hystrix服務降級

眾多的服務串在一起,雖然避免了耦合性,但卻形成了閉合鏈,只要其中一環失效,就會造成整個服務死鎖,這個時候hystrix就可以發揮作用了,將服務降級,

採用替代的方案來頂替出現錯誤的方法,避免整個鏈路中斷。

fallback是對於整個應用來說的,服務提供者和消費者端都可以進行配置,但一般都會配置在客戶端,對於使用者進行反饋。

1.服務提供者。

yml檔案都是常規配置

server:
  port: 8001
spring:
  application:
    name: cloud-provider-hystrix-payment
eureka:
  client:
    register-with-eureka: true
    fetch-registry: true
    service-url:
      #defaultZone: http://localhost:7001/eureka
      defaultZone: http://eureka7001.com:7001/eureka/

啟動類加上斷路器註解

@EnableCircuitBreaker

service測試類

@Service
public class PaymentHystrixService {
    public String paymentinfo_ok(Integer id){
        return "執行緒池:"+Thread.currentThread().getName()+"paymentinfo_ok,id:"+id+"\t"+"成功!!!!";
    }
    @HystrixCommand(fallbackMethod = "paymentinfo_Timeouthander",commandProperties = {
            @HystrixProperty(name 
= "execution.isolation.thread.timeoutInMilliseconds",value = "3000") }) public String paymentinfo_timeout(Integer id){ int timenum=5; try { TimeUnit.SECONDS.sleep(timenum); } catch (InterruptedException e) { e.printStackTrace(); } return "執行緒池:"+Thread.currentThread().getName()+"paymentinfo_timeout,id:"+id+"\t"+"失敗!!!!耗時(秒):"+timenum; }
public String paymentinfo_Timeouthander(@PathVariable("id") Integer id){ return "執行緒池:"+Thread.currentThread().getName()+"系統繁忙,請稍後重試,id:"+id+"\t"+"失敗!!!!o(╥﹏╥)o"; } }
View Code

controller採用feign配合呼叫介面,服務提供者端也可以採用hystrix進行服務降級。

@RestController
@Slf4j
public class PaymentHystrixController {
    @Resource
    private PaymentHystrixService paymentHystrixService;

    @GetMapping(value = "/payment/hystrix/ok/{id}")
    public String payment_ok(@PathVariable("id")Integer id){
        String result = paymentHystrixService.paymentinfo_ok(id);
        log.info("*****result:"+result);
         return result;
    }
    @GetMapping(value = "/payment/hystrix/timeout/{id}")
    public String payment_timeout(@PathVariable("id")Integer id){
        String result = paymentHystrixService.paymentinfo_timeout(id);
        log.info("*****result:"+result);
        return result;
    }
}
View Code

2.客戶端消費者

yml檔案常規配置需要加上新的feign,hystrix配置

server:
  port: 80
#這裡只把feign做客戶端用,不註冊進eureka
eureka:
  client:
    #表示是否將自己註冊進EurekaServer預設為true
    register-with-eureka: false
    fetch-registry: true
    service-url:
      #defaultZone: http://localhost:7001/eureka
      defaultZone: http://eureka7001.com:7001/eureka/
feign:
  hystrix:
    enabled: true
View Code

採用openfeign呼叫介面,建立service介面,fallback後續介紹

@Component
@FeignClient(value = "CLOUD-PROVIDER-HYSTRIX-PAYMENT",fallback = PaymentFallback.class)
public interface PaymentHystrixService {
    @GetMapping(value = "/payment/hystrix/ok/{id}")

    public String payment_ok(@PathVariable("id")Integer id);

    @GetMapping(value = "/payment/hystrix/timeout/{id}")
    public String payment_timeout(@PathVariable("id")Integer id);
}

啟動類常規配置,加上hystrix註解

@SpringBootApplication
@EnableFeignClients
@EnableHystrix

controller

@RestController
@Slf4j
public class OrderController {
    @Resource
    private PaymentHystrixService paymentHystrixService;

    @GetMapping(value = "/consumer/payment/hystrix/ok/{id}")
    public String payment_ok(@PathVariable("id")Integer id){
        String result = paymentHystrixService.payment_ok(id);
        return result;
    }
    @GetMapping(value = "/consumer/payment/hystrix/timeout/{id}")
    /*@HystrixCommand(fallbackMethod = "paymentinfo_Timeouthander",commandProperties = {
            @HystrixProperty(name = "execution.isolation.thread.timeoutInMilliseconds",value = "1500")
    })*/
    public String payment_timeout(@PathVariable("id")Integer id){
        String result = paymentHystrixService.payment_timeout(id);
        return result;
    }
 
}

在面對服務降級的處理中,隨著服務的增多,越來越多的方法需要配置一個獨立的fallback,而且在同一個類中會造成程式碼膨脹和耦合度增強,此時需要採取額外的方法,建立額外的fallback類繼承openfeign的呼叫介面

,此時fallback的作用就是當服務正常的時候不觸發,若是出現方法報錯或者服務端宕機就會自動去調取fallback類中對應的方法。

@Component
public class PaymentFallback implements PaymentHystrixService
{
    @Override
    public String payment_ok(Integer id) {
        return "服務失敗了,o(╥﹏╥)o";
    }
    @Override
    public String payment_timeout(Integer id) {
        return "服務超時或者執行報錯,o(╥﹏╥)o";
    }
}