sentinel规则持久化

Sentinel数据源

Sentinel的数据源可以通过多种方式加载:json、xml文件;zookeeper;apollo;nacos;并且可以多种数据源同时使用。

扩展方式

动态数据源:DataSource`扩展常见的实现方式


拉模式

客户端主动向某个规则管理中心定期轮询拉取规则,这个规则中心可以是 RDBMS、文件,甚至是 VCS 等。这样做的方式是简单,缺点是无法及时获取变更;

推模式

规则中心统一推送,客户端通过注册监听器的方式时刻监听变化,比如使用 Nacos、Zookeeper 等配置中心。这种方式有更好的实时性和一致性保证。


一:客户端从Nacos读取限流规则

Sentinel客户端配置

1. 引入POM依赖


    com.alibaba.cloud
    spring-cloud-starter-alibaba-sentinel
    2.2.1.RELEASE


    com.alibaba.csp
    sentinel-datasource-nacos
    1.7.2


    com.alibaba
    fastjson
    1.2.70


2. 修改配置文件

默认sentinel控制台推送到nacos的dataId定义为: ${spring.application.name}-flow-rules
server.port=8083
# 配置中心url
spring.application.name=order-server
#注册中心地址
spring.cloud.nacos.server-addr=192.168.64.128:8848
#添加sentinel依赖后 暴露/actuator/sentinel端点
# 开启健康检查
management.endpoints.web.exposure.include=*
management.endpoint.health.show-details=ALWAYS
#打开/关闭掉对Spring MVC端点的保护
spring.cloud.sentinel.filter.enabled=false
#这里的 spring.cloud.sentinel.transport.port 端口配置会在应用对应的机器上启动一个 Http Server,该 Server 会与 Sentinel 控制台做交互。比如 Sentinel 控制台添加了1个限流规则,会把规则数据 push 给这个 Http Server 接收,Http Server 再将规则注册到 Sentinel 中。
spring.cloud.sentinel.transport.port=8731
#指定sentinel控制台的地址
spring.cloud.sentinel.transport.dashboard=127.0.0.1:8080

# 设置Sentinel Nacos数据源配置;其中ds是数据源名,可以自行随意修改
# Nacos数据源地址(需要启动一台Nacos Server)
# nacos 地址
spring.cloud.sentinel.datasource.ds.nacos.server-addr=${spring.cloud.nacos.server-addr}
spring.cloud.sentinel.datasource.ds.nacos.dataId=${spring.application.name}-flow-rules
spring.cloud.sentinel.datasource.ds.nacos.groupId=SENTINEL_GROUP
# 数据类型
spring.cloud.sentinel.datasource.ds3.nacos.data-type=json
# 规则类型
spring.cloud.sentinel.datasource.ds.nacos.rule-type=flow

3. 添加Nacos数据源配置类

@Configuration
public class DataSourceInitFunc {

    Logger logger = LoggerFactory.getLogger(DataSourceInitFunc.class);

    @Autowired
    private SentinelProperties sentinelProperties;

    @Bean
    public DataSourceInitFunc init() throws Exception {

        logger.info("[NacosSource初始化,从Nacos中获取熔断规则]");

        sentinelProperties.getDatasource().entrySet().stream().filter(map -> {
            return map.getValue().getNacos() != null;
        }).forEach(map -> {
            NacosDataSourceProperties nacos = map.getValue().getNacos();
            // 限流规则,需要Nacos的dataId中包含flow字符串
            if (nacos.getDataId().contains("flow")) {
                ReadableDataSource> flowRuleDataSource = new NacosDataSource<>(nacos.getServerAddr(),
                        nacos.getGroupId(), nacos.getDataId(),
                        source -> JSON.parseObject(source, new TypeReference>() {
                        }));
                FlowRuleManager.register2Property(flowRuleDataSource.getProperty());
            }

            // 降级规则,需要Nacos的dataId中包含degrade字符串
            if (nacos.getDataId().contains("degrade")) {
                ReadableDataSource> degradeRuleDataSource = new NacosDataSource<>(nacos.getServerAddr(),
                        nacos.getGroupId(), nacos.getDataId(),
                        source -> JSON.parseObject(source, new TypeReference>() {
                        }));
                DegradeRuleManager.register2Property(degradeRuleDataSource.getProperty());
            }

        });
        return new DataSourceInitFunc();
    }
}

4. Nacos中添加熔断规则

根据配置文件配置的 id是 应用名-flow-rules
image.png

备注:

规则文件可以是json文件;也可以是text文件
规则是将 createOrder 的资源进行限流 使用QPS 模式 限流阈值 1

[
    {
        "resource": "createOrder",
        "limitApp": "default",
        "grade": 1,
        "count": 1,
        "strategy": 0,
        "controlBehavior": 0,
        "clusterMode": false
    }
]

5. 测试
访问 http://localhost:8083/order/createorder/1 进行测试

image.png

这样会自动从配置中心读取配置信息不需要每次重启都需要配置了


二:Sentinel控制台 将熔断规则推送到Nacos数据源。

控制台改造主要是为规则实现

  1. DynamicRuleProvider:从Nacos上读取配置
  2. DynamicRulePublisher:将规则推送到Nacos上

1.下载控制台源码
下载Sentinel控制台:https://github.com/alibaba/Sentinel/releases

image.png


2.修改POM文件

将sentinel-datasource-nacos的 test 这一行注释掉


    com.alibaba.csp
    sentinel-datasource-nacos
    


3. 相关类修改

找到 sentinel-dashboard/src/test/java/com/alibaba/csp/sentinel/dashboard/rule/nacos目录,将整个目录拷贝到 sentinel-dashboard/src/main/java/com/alibaba/csp/sentinel/dashboard/rule/nacos

image.png

4.修改NacosConfig类

修改NacosConfig类,修改NacosIP地址
image.png

5. FlowControllerV1修改
自动注入provider和publisher

@Autowired
@Qualifier("flowRuleNacosProvider")
private DynamicRuleProvider> ruleProvider;

@Autowired
@Qualifier("flowRuleNacosPublisher")
private DynamicRulePublisher> rulePublisher;
image.png

修改rules接口,读取nacos中的数据

@GetMapping("/rules")
   @AuthAction(PrivilegeType.READ_RULE)
   public Result> apiQueryMachineRules(@RequestParam String app) {

       if (StringUtil.isEmpty(app)) {
           return Result.ofFail(-1, "app can't be null or empty");
       }
       try {
           List rules = ruleProvider.getRules(app);
           if (rules != null && !rules.isEmpty()) {
               for (FlowRuleEntity entity : rules) {
                   entity.setApp(app);
                   if (entity.getClusterConfig() != null && entity.getClusterConfig().getFlowId() != null) {
                       entity.setId(entity.getClusterConfig().getFlowId());
                   }
               }
           }
           rules = repository.saveAll(rules);
           return Result.ofSuccess(rules);
       } catch (Throwable throwable) {
           logger.error("Error when querying flow rules", throwable);
           return Result.ofThrowable(-1, throwable);
       }
   }
image.png

该类最后的publishRules方法修改如下

private CompletableFuture publishRules(String app, String ip, Integer port) {
    List rules = repository.findAllByMachine(MachineInfo.of(app, ip, port));
    try {
        rulePublisher.publish(app, rules);
        logger.info("添加限流规则成功.....");
    } catch (Exception e) {
        e.printStackTrace();
        logger.info("添加限流规则失败.....");
    }
    return sentinelApiClient.setFlowRuleOfMachineAsync(app, ip, port, rules);
}
image.png

测试

访问http://localhost:8080/可以进入到控制台界面,但是界面上没有任何的客户端

请求一次http://localhost:8083/order/createorder/1,等一会儿,刷新一下就可以看到客户端了

image.png

添加流控规则


image.png

并刷新一下就可以看到我们添加的规则了


image.png

在nacos配置中心查看

我们发现配置已经被推送到了nacos


image.png

重启客户端进行测试

重启客户端后发现我们的规则是生效的,并且修改规则后重启客户端规则也是生效的

访问 http://localhost:8083/order/createorder/1 进行测试

image.png

你可能感兴趣的:(sentinel规则持久化)