欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

程序员,你知道Sentinel限流、降级的统一处理吗?

程序员文章站 2022-04-24 12:36:48
...

前言

之前老顾介绍了sentinel的fallback、blockhandler;不知道小伙伴们有没有注意到一个问题?老顾带着大家来看看。

问题一

sentinel的默认流控返回的是:


1.  `BlockedbySentinel(flow limiting)`

当然我们可以通过@SentinelResource设置定制的fallback、blockhandler方法

程序员,你知道Sentinel限流、降级的统一处理吗?

但是我们也不可能每个限制的方法上面,都要去设置@SentinelResource;这样代码太冗余了。

解决方案

自定义限流页面

默认情况下,当请求被限流时会返回默认的提示页面。可通过二种方式设置自定义的跳转 URL。

方式一:


1.  `WebServletConfig.setBlockPage(blockPage)方法`

程序员,你知道Sentinel限流、降级的统一处理吗?

方式二:


1.  `JVM -Dcsp.sentinel.web.servlet.block.page=xxx`

在启动应用的时候,加入启动参数:

1.  `//设置全局生效,被流控的所有页面都会跳转到这里。`

2.  `-Dcsp.sentinel.web.servlet.block.page=https://www.x.com`

上面的两种方式,都能够做到一旦出现流控异常,就会跳转到指定页面。

更灵活的处理方式

上面的解决方案,只是跳转到另一个页面,但如果我们只要得到json返回值呢;那就需要此方式了,定义UrlBlockHandler接口限流处理逻辑,并将其注册至 WebCallbackManager

首先自定义一个UrlBlockHandler实现类

程序员,你知道Sentinel限流、降级的统一处理吗?

程序员,你知道Sentinel限流、降级的统一处理吗?

在一个初始化方法里面注册此UrlBlockHandler

程序员,你知道Sentinel限流、降级的统一处理吗?

来看看效果

程序员,你知道Sentinel限流、降级的统一处理吗?

注意此解决方案:需要引入一个jar包,这个是基于servlet


1.  `<dependency>`

2.  `<groupId>com.alibaba.csp</groupId>`

3.  `<artifactId>sentinel-web-servlet</artifactId>`

4.  `</dependency>`

问题二

在spring cloud中我们会经常使用到feign,在@FeignClient中我们可以指定fallback,我们来看看案例:

程序员,你知道Sentinel限流、降级的统一处理吗?

程序员,你知道Sentinel限流、降级的统一处理吗?

程序员,你知道Sentinel限流、降级的统一处理吗?

以上就是常规的在使用@FeignClient注解时,加上fallbackFactory;但每次都要为其设置fallbackFactory参数。导致项目中会多出很多冗余代码。那我们能不能有一个自己定制化的默认Fallback去处理这些相同的事情呢?

解决方案

在使用sentinel时,需要引入一个jar包:

1.  `<dependency>`

2.  `<groupId>com.alibaba.cloud</groupId>`

3.  `<artifactId>spring-cloud-starter-alibaba-sentinel</artifactId>`

4.  `</dependency>`

在这个jar包中,有一段源码:

程序员,你知道Sentinel限流、降级的统一处理吗?

程序员,你知道Sentinel限流、降级的统一处理吗?

从源码我们可以看出,在没有配置fallback时,并没有向SentinelInvocationHandler构造方法中传入FallbackFactory。这样的话我们就有了思路:

  • 编写公共FallbackFactory

  • 改写SentinelFeign使得fallbackFactory为void.class时,我们传入自己的公共FallbackFactory实例

让我们一起上代码吧!

先定义全局的fallback处理器

程序员,你知道Sentinel限流、降级的统一处理吗?

程序员,你知道Sentinel限流、降级的统一处理吗?

再定义一个全局的FallbackFactory

程序员,你知道Sentinel限流、降级的统一处理吗?

再后面我们需要重新实现spring-cloud-starter-alibaba-sentinel下的SentinelFeign

程序员,你知道Sentinel限流、降级的统一处理吗?

程序员,你知道Sentinel限流、降级的统一处理吗?

程序员,你知道Sentinel限流、降级的统一处理吗?

程序员,你知道Sentinel限流、降级的统一处理吗?

上面的代码其实是仿照SentinelFeign源码的,唯一的区别就是画上红色的框的。

注意:其中有个方法setAccessible,这个是因为SentinelInvocationHandler的构造方法是私有方法。

其实还有一种方案,就是把重写 的SentinelFeign类,放到com.alibaba.cloud.sentinel.feign包下,也就是在自己的项目中,新建com.alibaba.cloud.sentinel.feign包

最后注入我们的SentinelFeign Bean

程序员,你知道Sentinel限流、降级的统一处理吗?

注意:一定要在配置文件中配置feign.sentinel.enabled=true

到这里就可以了,以后只要定义基本属性@FeignClient,不需要再配置fallBackFactory了哦。

当然你还有特殊的需求,再自定义的可以了。

总结

通过此文章,小伙伴就可以更好的使用Sentinel了,更方便的编写统一的兜底方法了。如果有人使用dubbo时,sentinel也有对应的适配器;有空老顾再写一篇文章。谢谢!!!

 

程序员,你知道Sentinel限流、降级的统一处理吗?