Zuul: многомерное ограничение тока для построения шлюзов высокой доступности

Redis Spring Безопасность API
  • Ограничьте целевой 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 (источник, запрошенный пользователем в качестве детального контроля)

  • Гранулярность интерфейса (адрес интерфейса запроса в качестве элемента управления гранулярностью)

  • Вышеупомянутые гранулярности можно свободно комбинировать, и они могут поддерживать различные ситуации.

  • Если этого недостаточно, настройте реализацию RateLimitKeyGenerator.

//默认实现
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();
}

Поддерживаемые методы хранения

image

  • InMemoryRateLimiter — использует ConcurrentHashMap в качестве хранилища данных
  • ConsulRateLimiter — использовать Consul в качестве хранилища данных
  • RedisRateLimiter — использовать Redis в качестве хранилища данных
  • SpringDataRateLimiter — использовать базу данных как хранилище данных

Конфигурация ограничения тока

  • limit Количество разрешенных доступов в единицу времени
  • quota Общее время, разрешенное для доступа в единицу времени (статистика для каждого синтеза времени запроса)
  • настройка интервала обновления
zuul:
  ratelimit:
    key-prefix: your-prefix 
    enabled: true 
    repository: REDIS 
    behind-proxy: true
    policies:
      myServiceId:
        limit: 10
        quota: 20
        refresh-interval: 30
        type:
          - user
        

Приведенная выше конфигурация означает: разрешено 10 доступов в течение 30 секунд, а общее время запроса должно быть менее 20 секунд.

Показать результаты

конфигурация ямла:

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

Динамический график ↓↓↓↓↓

image

Структура данных в Redis Обратите внимание на красный шрифт

image

Суммировать

  • Вы можете использовать статус службы, предоставляемый Spring Boot Actuator, для динамической установки текущего концевого выключателя.
  • Исходный код может относиться к:gitee.com/log4j/pig
  • Внедрение текущего ограничения пользователя: если ваш проект интегрирует платформу безопасности Shiro или Spring Security, домен запроса UserPrincipal будет автоматически поддерживаться.Если это ваша собственная структура, сохраните домен запроса после успешного входа в систему.UserPrincipal, вы можете использовать текущий предел детализации пользователя. По умолчанию для незарегистрированных пользователей:anonymous