gateway整合sentinel限流

官方文档:https://github.com/alibaba/Sentinel/wiki/网关限流

从 1.6.0 版本开始,Sentinel 提供了 Spring Cloud Gateway 的适配模块,可以提供两种资源维度的限流:

  • route 维度:即在 Spring 配置文件中配置的路由条目,资源名为对应的 routeId
  • 自定义 API 维度:用户可以利用 Sentinel 提供的 API 来自定义一些 API 分组

1.快速开始

使用时需引入依赖:

java 复制代码
<dependency>
<groupId>com.alibaba.csp</groupId>
<artifactId>sentinel‐spring‐cloud‐gateway‐adapter</artifactId>
<version>x.y.z</version>
</dependency>

接入sentinel dashboard,添加yml配置

yaml 复制代码
spring:
application:
name: mall‐gateway‐sentinel‐demo
#配置nacos注册中心地址
cloud:
nacos:
discovery:
server‐addr: 127.0.0.1:8848
 sentinel:
 transport:
 # 添加sentinel的控制台地址
 dashboard: 127.0.0.1:8080

使用时只需注入对应的 SentinelGatewayFilter 实例以及SentinelGatewayBlockExceptionHandler 实例即可

java 复制代码
@Configuration
public class GatewayConfiguration {

    private final List<ViewResolver> viewResolvers;
    private final ServerCodecConfigurer serverCodecConfigurer;

    public GatewayConfiguration(ObjectProvider<List<ViewResolver>> viewResolversProvider,
                                ServerCodecConfigurer serverCodecConfigurer) {
        this.viewResolvers = viewResolversProvider.getIfAvailable(Collections::emptyList);
        this.serverCodecConfigurer = serverCodecConfigurer;
    }

    /**
     * 限流异常处理器
     * @return
     */
    @Bean
    @Order(Ordered.HIGHEST_PRECEDENCE)
    public SentinelGatewayBlockExceptionHandler sentinelGatewayBlockExceptionHandler() {
        // Register the block exception handler for Spring Cloud Gateway.
        return new SentinelGatewayBlockExceptionHandler(viewResolvers, serverCodecConfigurer);
    }

    /**
     * 限流过滤器
     * @return
     */
    @Bean
    @Order(Ordered.HIGHEST_PRECEDENCE)
    public GlobalFilter sentinelGatewayFilter() {
        return new SentinelGatewayFilter();
    }

}

用户可以通过 GatewayRuleManager.loadRules(rules) 手动加载网关规则

GatewayConfiguration中添加

java 复制代码
@PostConstruct
    public void doInit() {
        //初始化自定义的API
        initCustomizedApis();
        //初始化网关限流规则
        initGatewayRules();
        //自定义限流异常处理器
        initBlockRequestHandler();
    }

    private void initCustomizedApis() {
        Set<ApiDefinition> definitions = new HashSet<>();
        ApiDefinition api = new ApiDefinition("user_service_api")
                .setPredicateItems(new HashSet<ApiPredicateItem>() {{
                    add(new ApiPathPredicateItem().setPattern("/user/**")
                            .setMatchStrategy(SentinelGatewayConstants.URL_MATCH_STRATEGY_PREFIX));
                }});
        definitions.add(api);
        GatewayApiDefinitionManager.loadApiDefinitions(definitions);
    }

    private void initGatewayRules() {
        Set<GatewayFlowRule> rules = new HashSet<>();
        //resource:资源名称,可以是网关中的 route 名称或者用户自定义的 API 分组名称。
        //count:限流阈值
        //intervalSec:统计时间窗口,单位是秒,默认是 1 秒。
        rules.add(new GatewayFlowRule("order_route")
                .setCount(2)
                .setIntervalSec(1)
        );
        rules.add(new GatewayFlowRule("user_service_api")
                .setCount(2)
                .setIntervalSec(1)
        );

        // 加载网关规则
        GatewayRuleManager.loadRules(rules);
    }

    private void initBlockRequestHandler() {
        BlockRequestHandler blockRequestHandler = new BlockRequestHandler() {
            @Override
            public Mono<ServerResponse> handleRequest(ServerWebExchange exchange, Throwable t) {
                HashMap<String, String> result = new HashMap<>();
                result.put("code",String.valueOf(HttpStatus.TOO_MANY_REQUESTS.value()));
                result.put("msg", HttpStatus.TOO_MANY_REQUESTS.getReasonPhrase());

                return ServerResponse.status(HttpStatus.TOO_MANY_REQUESTS)
                        .contentType(MediaType.APPLICATION_JSON)
                        .body(BodyInserters.fromValue(result));
            }
        };
        //设置自定义异常处理器
        GatewayCallbackManager.setBlockHandler(blockRequestHandler);
    }

2.网关流控控制台

Sentinel 1.6.3 引入了网关流控控制台的支持,用户可以直接在 Sentinel 控制台上查看 API Gateway 实时的 route 和自定义 API 分组监控,管理网关规则和 API 分组配置。

在 API Gateway 端,用户只需要在原有启动参数的基础上添加如下启动参数即可标记应用为 API Gateway 类型:

yaml 复制代码
# 注:通过 Spring Cloud Alibaba Sentinel 自动接入的 API Gateway 整合则无需此参数
-Dcsp.sentinel.app.type=1

3.网关流控实现原理

4.网关高可用

为了保证 Gateway 的高可用性,可以同时启动多个 Gateway 实例进行负载,在 Gateway 的上游使用 Nginx 或者 F5 进行负载转发以达到高可用。

相关推荐
kkoral1 天前
单机docker部署的redis sentinel,使用python调用redis,报错
redis·python·docker·sentinel
骚戴1 天前
n1n:从替代LiteLLM Proxy自建网关到企业级统一架构的进阶之路
人工智能·python·大模型·llm·gateway·api
墨白曦煜1 天前
深入剖析 Redis 客户端:Sentinel 模式下的“寻址”与“感知”艺术
数据库·redis·sentinel
遇见火星1 天前
Redis高可用-哨兵模式(Sentinel)
redis·sentinel
骚戴1 天前
LLM API Gateway:LLM API 架构、AI 聚合与成本优化全解(2025深度指南)
人工智能·python·大模型·llm·gateway·api
YDS8292 天前
SpringCloud —— Sentinel详解
java·spring cloud·sentinel
后端小张2 天前
【JAVA 进阶】深入理解Sentinel:分布式系统的流量守卫者
java·开发语言·spring boot·后端·spring·spring cloud·sentinel
小马爱打代码3 天前
面试题:Hystrix与Sentinel区别
hystrix·sentinel
破烂pan4 天前
Python 整合 Redis 哨兵(Sentinel)与集群(Cluster)实战指南
redis·python·sentinel
serendipity_hky5 天前
【SpringCloud | 第4篇】Gateway网关统一入口
spring·spring cloud·微服务·gateway