Hystrix熔断器是用来防止级联失败的,并允许系统快速失败和快速恢复。他的原理是通过模拟电路中的断路器(熔断器)来实现的,当某个部分发生故障时,断路器会切断电流,防止故障扩散。
在Hystrix中,这种机制用于管理对依赖服务的调用,特别是在这些服务表现不稳定或响应延迟时。
Hystrix断路器主要有三种状态:
Hystrix通过一系列指标来确定是否需要开启断路器,主要指标包括:
在代码中,开发者可以使用Hystrix命令来包装对下游服务的调用。这些命令封装了服务调用的细节,包括超时、失败、回退机制等。当断路器开启时,这些命令会自动执行配置的回退逻辑,而不是执行实际的服务调用。
如果在微服务系统的调用过程中,引入熔断器,那么整个系统将天然具备以下能力:
以下是一个使用Hystrix的Java代码示例,演示如何创建一个Hystrix命令来包装对某个依赖服务的调用,并提供回退逻辑以应对服务调用失败的情况。
假设我们有一个服务方法 getUserById
,用于从远程用户服务获取用户详情。我们将使用Hystrix来包装这个服务调用,以便在远程服务失败时提供回退逻辑。
首先,确保在你的项目中添加了Hystrix依赖。如果你使用Maven,可以在pom.xml
文件中添加以下依赖:
<dependencies>
<dependency>
<groupId>com.netflix.hystrix</groupId>
<artifactId>hystrix-core</artifactId>
<version>1.5.18</version> <!-- 使用适当的版本 -->
</dependency>
</dependencies>
我们将创建一个继承自 HystrixCommand
的类,用于封装对远程服务的调用。
import com.netflix.hystrix.HystrixCommand;
import com.netflix.hystrix.HystrixCommandGroupKey;
import com.netflix.hystrix.HystrixCommandProperties;
public class GetUserCommand extends HystrixCommand<String> {
private final int userId;
public GetUserCommand(int userId) {
super(Setter.withGroupKey(HystrixCommandGroupKey.Factory.asKey("UserServiceGroup"))
.andCommandPropertiesDefaults(
HystrixCommandProperties.Setter()
.withExecutionTimeoutInMilliseconds(1000)
.withCircuitBreakerErrorThresholdPercentage(50)
.withCircuitBreakerRequestVolumeThreshold(20)
.withCircuitBreakerSleepWindowInMilliseconds(5000)
));
this.userId = userId;
}
@Override
protected String run() throws Exception {
// 模拟远程服务调用
return remoteCallToGetUser(userId);
}
@Override
protected String getFallback() {
return "Hollis 的八股文用户";
}
private String remoteCallToGetUser(int userId) {
// 这里应该是实际调用远程服务的代码,例如使用HTTP客户端等
}
}
GetUserCommand
构造函数中,我们设置了Hystrix命令的几个关键属性,如执行超时时间、断路器的错误百分比阈值、请求量阈值和“sleep window”。run()
方法包含实际调用远程服务的逻辑。getFallback()
方法会被调用,返回一个默认值或其他回退逻辑。你可以在应用中如下使用GetUserCommand
来获取用户信息:
public class UserService {
public String getUserById(int userId) {
GetUserCommand command = new GetUserCommand(userId);
return command.execute(); // 同步执行
// 或者使用 command.queue() 来异步执行
}
}
通过这种方式,Hystrix帮助我们管理依赖服务的不确定性和失败,从而增强系统的稳定性和弹性。