Hystrix关于服务降级
程序员文章站
2022-07-15 13:04:14
...
一 介绍
fallback是Hystrix命令执行失败时的后备方法,用来实现服务的降级处理。
二 HystrixCommand的服务降级示例
package com.didispace.web;
import static org.junit.Assert.*;
import java.util.concurrent.Future;
import org.junit.Test;
import com.netflix.hystrix.HystrixCommand;
import com.netflix.hystrix.HystrixCommandGroupKey;
public class CommandHelloFailure extends HystrixCommand<String> {
private final String name;
public CommandHelloFailure(String name) {
super(HystrixCommandGroupKey.Factory.asKey("ExampleGroup"));
this.name = name;
}
@Override
protected String run() {
throw new RuntimeException("this command always fails");
}
//HystrixCommand中可以通过重载getFallback方法来实现服务降级逻辑,
//Hystrix会在run执行过程中出现错误。超时、线程池拒绝、断路器熔断等情况时,执行
//fwrFallback方法内的逻辑
@Override
protected String getFallback() {
return "Hello Failure " + name + "!";
}
public static class UnitTest {
@Test
public void testSynchronous() {
assertEquals("Hello Failure World!", new CommandHelloFailure("World").execute());
assertEquals("Hello Failure Bob!", new CommandHelloFailure("Bob").execute());
}
@Test
public void testAsynchronous1() throws Exception {
assertEquals("Hello Failure World!", new CommandHelloFailure("World").queue().get());
assertEquals("Hello Failure Bob!", new CommandHelloFailure("Bob").queue().get());
}
@Test
public void testAsynchronous2() throws Exception {
Future<String> fWorld = new CommandHelloFailure("World").queue();
Future<String> fBob = new CommandHelloFailure("Bob").queue();
assertEquals("Hello Failure World!", fWorld.get());
assertEquals("Hello Failure Bob!", fBob.get());
}
}
}
三 HystrixObservableCommand的服务降级
通过HystrixObservableCommand实现的Hystrix命令中,可以通过重载resumeWithFallback方法来实现服务降级。该方法返回一个Observable对象,当命令执行失败时,Hystrix会将Observable中的结果通知给所有的订阅者。
示例:
@Override
protected Observable<Boolean> resumeWithFallback() {
return Observable.just( new UserAccount(customerId, "Unknown Name",
countryCodeFromGeoLookup, true, true, false) );
}
四 通过注解实现服务降级
1 介绍
若要通过注解实现服务降级只需要使用@HystrixCommand中的fallbackMethod参数来指定具体的服务降级实现方法。
2 示例
@Service
public class HelloService {
private final Logger logger = Logger.getLogger(getClass());
@Autowired
RestTemplate restTemplate;
//在使用注解定义服务降级逻辑时,需要具体Hystrix命令与fallback实现函数定义在一个类中
@HystrixCommand(fallbackMethod = "helloFallback", commandKey = "helloKey")
public String hello() {
long start = System.currentTimeMillis();
StringBuilder result = new StringBuilder();
long end = System.currentTimeMillis();
logger.info("Spend time : " + (end - start) );
return result.toString();
}
public String helloFallback() {
return "error";
}
}
五 双重回退逻辑
1 使用场景举例
在上面这个例子中,helloFallback方法将在hello执行时发生错误的情况下执行,若helloFallback方法实现并不是一个稳定逻辑,它依然可能发生异常,那么也可以为它添加@HystrixCommand注解以生成Hystrix命令,同时使用fallbackMethod来指定服务降级逻辑,实现双重回退逻辑。
2 示例
@Service
public class HelloService {
private final Logger logger = Logger.getLogger(getClass());
@Autowired
RestTemplate restTemplate;
//在使用注解定义服务降级逻辑时,需要具体Hystrix命令与fallback实现函数定义在一个类中
@HystrixCommand(fallbackMethod = "helloFallback", commandKey = "helloKey")
public String hello() {
long start = System.currentTimeMillis();
StringBuilder result = new StringBuilder();
long end = System.currentTimeMillis();
logger.info("Spend time : " + (end - start) );
return result.toString();
}
@HystrixCommand(fallbackMethod = "hellosecFallback")
public String helloFallback() {
return "error";
}
public StringhellosecFallback() {
return "second error";
}
}
六 补充
在实际情况下,我们需要为大多数执行过程中可能会失败的Hystrix命令实现服务降级逻辑,但是也有一些情况可以不去实现降级逻辑。
- 执行写操作的命令:通常情况下这类操作返回类型是void或是为空的Observable,实现服务降级的意义不是很大。当写入操作失败的时候,只需要通知调用者即可。
- 执行批处理或离线计算的命令:当Hystrix命令是执行批处理程序生成一份报告或是任何类型的离线计算时,那么通常这些操作只需要将错误传播给调用者,然后让调用者稍后重试而不是发送给调用者一个静默的降级处理响应。
下一篇: JAVA异常总结!!(使用方法)
推荐阅读