Zuul:构建高可用网关之多维度限流

作者:冷冷gg

来源:https://my.oschina.net/giegie/blog/1583705


你想学习Java ?资源都在这里了


介绍 


spring-cloud-zuul-ratelimit是和zuul整合提供分布式限流策略的扩展,只需在yaml中配置几行配置,就可使应用支持限流。


 
  
  1. <dependency>

  2.    <groupId>com.marcosbarbero.cloud</groupId>

  3.    <artifactId>spring-cloud-zuul-ratelimit</artifactId>

  4.    <version>1.3.4.RELEASE</version>

  5. </dependency>


支持的限流粒度 


  • 服务粒度 (默认配置,当前服务模块的限流控制)

  • 用户粒度 (详细说明,见文末总结)

  • ORIGIN粒度 (用户请求的origin作为粒度控制)

  • 接口粒度 (请求接口的地址作为粒度控制)

  • 以上粒度自由组合,又可以支持多种情况。

  • 如果还不够,自定义RateLimitKeyGenerator实现。


 
  
  1. //默认实现

  2. public String key(final HttpServletRequest request, final Route route, final RateLimitProperties.Policy policy) {

  3.    final List<Type> types = policy.getType();

  4.    final StringJoiner joiner = new StringJoiner(":");

  5.    joiner.add(properties.getKeyPrefix());

  6.    if (route != null) {

  7.        joiner.add(route.getId());

  8.    }

  9.    if (!types.isEmpty()) {

  10.        if (types.contains(Type.URL) && route != null) {

  11.            joiner.add(route.getPath());

  12.        }

  13.        if (types.contains(Type.ORIGIN)) {

  14.            joiner.add(getRemoteAddr(request));

  15.        }

  16.        // 这个结合文末总结。

  17.        if (types.contains(Type.USER)) {

  18.            joiner.add(request.getUserPrincipal() != null ? request.getUserPrincipal().getName() : ANONYMOUS_USER);

  19.        }

  20.    }

  21.    return joiner.toString();

  22. }


支持的存储方式 


640?wx_fmt=png


  • InMemoryRateLimiter - 使用 ConcurrentHashMap作为数据存储 

  • ConsulRateLimiter - 使用 Consul 作为数据存储 

  • RedisRateLimiter - 使用 Redis 作为数据存储 

  • SpringDataRateLimiter - 使用 数据库 作为数据存储 


限流配置 


  • limit 单位时间内允许访问的个数 

  • quota 单位时间内允许访问的总时间(统计每次请求的时间综合) 

  • refresh-interval 单位时间设置


 
  
  1. zuul:

  2.  ratelimit:

  3.    key-prefix: your-prefix

  4.    enabled: true

  5.    repository: REDIS

  6.    behind-proxy: true

  7.    policies:

  8.      myServiceId:

  9.        limit: 10

  10.        quota: 20

  11.        refresh-interval: 30

  12.        type:

  13.          - user

 
  
  1.    


以上配置意思是:30秒内允许10个访问,或者要求总请求时间小于20秒


效果展示 


yaml配置:

 
  
  1. zuul:

  2.  ratelimit:

  3.    key-prefix: pig-ratelimite

  4.    enabled: true

  5.    repository: REDIS

  6.    behind-proxy: true

  7.    policies:

  8.      pig-admin-service:

  9.        limit: 2

  10.        quota: 1

  11.        refresh-interval: 3


动态图 ↓↓↓↓↓ 

640?wx_fmt=gif


Redis 中数据结构 注意红色字体 

640?wx_fmt=png


总结 


  1. 可以使用Spring Boot Actuator 提供的服务状态,动态设置限流开关 

  2. 源码可以参考:https://gitee.com/log4j/pig 用户

  3. 限流的实现:如果你的项目整合 Shiro 或者 Spring Security 安全框架,那么会自动维护request域UserPrincipal,如果是自己的框架,请登录成功后维护request域UserPrincipal,才能使用用户粒度的限流,未登录默认是:anonymous。具体代码实现可以看 DefaultRateLimitKeyGenerator,type为USER的实现


-END-

 近期热文:

关注我

640?wx_fmt=jpeg

点击“阅读原文”,看本号其他精彩内容

猜你喜欢

转载自blog.csdn.net/j3T9Z7H/article/details/81660065