21,Zuul:構建高可用網關之多維度限流

原文:Zuul:構建高可用網關之多維度限流

對請求的目標URL進行限流(例如:某個URL每分鐘只允許調用多少次)
對客戶端的ip進行限流(例如: 對某個Ip每分鐘只允許請求多少次)
對某些特定用戶或者用戶組進行限流(例如: 非vip用戶限制每分鐘只允許滴哦阿勇100次某個API等)
對維度混合的限流。此時,就需要實現一些限流規則的編排機制。與,或,非等關係
介紹
spring-cloud-zuul-ratelimit是和zuul整合提供分佈式限流策略的擴展,只需在yaml中配置幾行配置,就可使應用支持限流

<dependency>
    <groupId>com.marcosbarbero.cloud</groupId>
    <artifactId>spring-cloud-zuul-ratelimit</artifactId>
    <version>1.3.4.RELEASE</version>
</dependency>

支持限流的粒度
服務粒度(默認配置,當前服務模塊的限流控制)
用戶粒度(詳細說明,見文本總結)
ORIGIN粒度(用戶請求的origin作爲粒度控制)
接口粒度(請求接口的地址作爲粒度控制)
以上粒度自由組合,有支持多種情況
如果還不夠,自定義RateLimiKeyGenerator實現。

//默認實現
public String key(final HttpServletRequest request, final Route route, final RateLimitProperties.Policy policy) {
    final List<Type> types = policy.getType();
    final StringJoiner joiner = new StringJoiner(":");
    joiner.add(properties.getKeyPrefix());
    if (route != null) {
        joiner.add(route.getId());
    }
    if (!types.isEmpty()) {
        if (types.contains(Type.URL) && route != null) {
            joiner.add(route.getPath());
        }
        if (types.contains(Type.ORIGIN)) {
            joiner.add(getRemoteAddr(request));
        }
        // 這個結合文末總結。
        if (types.contains(Type.USER)) {
            joiner.add(request.getUserPrincipal() != null ? request.getUserPrincipal().getName() : ANONYMOUS_USER);
        }
    }
    return joiner.toString();
}

InMemoryRateLimiter - 使用 ConcurrentHashMap作爲數據存儲
ConsulRateLimiter - 使用 Consul 作爲數據存儲
RedisRateLimiter - 使用 Redis 作爲數據存儲
SpringDataRateLimiter - 使用 數據庫 作爲數據存儲

限流的配置
limit單位時間內允許訪問的個數
quota 單位時間內允許訪問的總時間(統計每次請求的時間總和)
refresh-interval 單位時間設置

zuul:
   ratelimit:
      key-prefix:  your-prefix
      enabled: true
      repository: REDIS
      behind-proxy: true
      prolicies:
         myServiceId:
                 limit: 10
                 quota: 20
                 refresh-interval: 30
                 type:
                       -user

以上配置的意思是:30秒內允許10個訪問,或者總請求時間小於20秒、、


效果展示
application.yml

zuul:
  ratelimit:
    key-prefix: pig-ratelimite 
    enabled: true 
    repository: REDIS 
    behind-proxy: true
    policies:
      pig-admin-service:
        limit: 2
        quota: 1
        refresh-interval: 3
   

Redis 中數據結構 注意紅色字體

總結

  • 可以使用Spring Boot Actuator 提供的服務狀態,動態設置限流開關
  • 源碼可以參考:https://gitee.com/log4j/pig
  • 用戶限流的實現:如果你的項目整合 Shiro 或者 Spring Security 安全框架,那麼會自動維護request域UserPrincipal,如果是自己的框架,請登錄成功後維護request域UserPrincipal,才能使用用戶粒度的限流,未登錄默認是:anonymous。具體代碼實現可以看 DefaultRateLimitKeyGenerator,type爲USER的實現
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章