限流工具 RateLimiter ,限流工具的用法基本上和前两个差不多,可以通过 AOP 的方式使用,也可以通过编程式来使用。
github :https://github.com/ln0491/resilience4j-springboot
生产者
@RestController
public class HelloContrtoller {
@GetMapping("/hello")
public String hell(String name){
String s= "hello "+name +" !";
System.out.println("s "+s+" "+new Date());
return s;
}
}
消费者端
<dependency>
<groupId>io.github.resilience4j</groupId>
<artifactId>resilience4j-spring-boot2</artifactId>
<version>0.14.1</version>
</dependency>
AOP 式
resilience4j.ratelimiter:
limiters:
backendA:
limitForPeriod: 1
limitRefreshPeriodInMillis: 5000
timeoutInMillis: 5000
subscribeForEvents: true
registerHealthIndicator: true
eventConsumerBufferSize: 100
- backendA 在这里依然表示配置的名称,在 Java 代码中,我们将通过指定限流工具的名称来使用某一种限流策略;
- limitForPeriod 表示请求频次的阈值;
- limitRefreshPeriodInMillis 表示频次刷新的周期;
- timeoutInMillis 许可期限的等待时间,默认为5秒;
- subscribeForEvents 表示开启事件订阅;
- registerHealthIndicator 表示开启健康监控;
- eventConsumerBufferSize 表示事件缓冲区大小。
@Service
@RateLimiter(name = "backendA")
public class HelloServiceRateLimiter {
@Autowired
RestTemplate restTemplate;
public String hello(String name) {
return restTemplate.getForObject("http://provider/hello?name={1}", String.class, name);
}
}
@GetMapping("/rl")
public void rateLimiter(String name) {
for (int i = 0; i < 5; i++) {
String hello = helloServiceRateLimiter.hello(name);
}
}
s hello 富士达顶戴 4234fsdfd ! Wed Jun 26 20:30:59 CST 2019
s hello 富士达顶戴 4234fsdfd ! Wed Jun 26 20:31:01 CST 2019
s hello 富士达顶戴 4234fsdfd ! Wed Jun 26 20:31:06 CST 2019
s hello 富士达顶戴 4234fsdfd ! Wed Jun 26 20:31:11 CST 2019
s hello 富士达顶戴 4234fsdfd ! Wed Jun 26 20:31:16 CST 2019
编程式
public void hello2(String name) {
RateLimiterConfig config = RateLimiterConfig.custom()
.limitRefreshPeriod(Duration.ofMillis(5000))
.limitForPeriod(1)
.timeoutDuration(Duration.ofMillis(6000))
.build();
RateLimiterRegistry rateLimiterRegistry = RateLimiterRegistry.of(config);
RateLimiter rateLimiter = RateLimiter.of("backendB", config);
Supplier<String> supplier = RateLimiter.decorateSupplier(rateLimiter, () ->
restTemplate.getForObject("http://provider/hello?name={1}", String.class, name)
);
for (int i = 0; i < 5; i++) {
Try<String> aTry = Try.ofSupplier(supplier);
System.out.println(aTry.get());
}
}