Sentinel-Dashboard 添加配置Nacos持久化,权限控制扩展

Sentinel-Dashboard 添加规则Nacos双向绑定

官网文档地址:https://sentinelguard.io/zh-cn/docs/quick-start.html

思路

从动态规则扩展章节得知,可以通过NacosDataSource作为配置数据源
从Sentinel-Dashboard代码中可以得知,dashboard通过http请求推送配置变更

publishRules(entity.getApp(), entity.getIp(), entity.getPort()).get(5000, TimeUnit.MILLISECONDS);

   List<FlowRuleEntity> rules = repository.findAllByMachine(MachineInfo.of(app, ip, port));
        return sentinelApiClient.setFlowRuleOfMachineAsync(app, ip, port, rules);

所以,只需要在dashboard推送变更后,将配置保存到nacos中且搭配NacosDataSource扩展即可实现配置持久化

从dashboard各个规则的Controller中可以发现,每个Controller都有类似repository的注入

    @Autowired
    private RuleRepository<DegradeRuleEntity, Long> repository;

负责规则的增删改查,默认提供的都是内存控制,例如InMemDegradeRuleStore
每个内存控制类都继承同一个抽象类

public class InMemDegradeRuleStore extends InMemoryRuleRepositoryAdapter<DegradeRuleEntity>

只要在respository写操作后添加配置推送的nacos的操作

实现

注释掉

        <dependency>
            <groupId>com.alibaba.csp</groupId>
            <artifactId>sentinel-datasource-nacos</artifactId>
<!--            <scope>test</scope>-->
        </dependency>
package com.alibaba.csp.sentinel.dashboard.repository.rule;

import com.alibaba.csp.sentinel.dashboard.config.NacosConfig;
import com.alibaba.csp.sentinel.dashboard.datasource.entity.NacosEntity;
import com.alibaba.csp.sentinel.dashboard.datasource.entity.gateway.ApiDefinitionEntity;
import com.alibaba.csp.sentinel.dashboard.datasource.entity.rule.RuleEntity;
import com.alibaba.csp.sentinel.dashboard.discovery.MachineInfo;
import com.alibaba.csp.sentinel.slots.block.Rule;
import com.alibaba.fastjson.JSON;
import com.alibaba.nacos.api.config.ConfigService;
import com.alibaba.nacos.api.config.ConfigType;

import java.util.List;
import java.util.stream.Collectors;

/**
 * @Author Luowenjian
 * @Description
 * @Date 2023/8/1 15:29
 **/

public class NacosRepository<T extends RuleEntity> implements RuleRepository<T, Long> {

    private ConfigService configService;

    private NacosConfig.NacosProperties nacosProperties;

    private InMemoryRuleRepositoryAdapter<T> ruleRepositoryAdapter;

    private final String suffix;

    public NacosRepository(String suffix){
        this.suffix = suffix;
    }

    public ConfigService getConfigService() {
        return configService;
    }

    public void setConfigService(ConfigService configService) {
        this.configService = configService;
    }

    public NacosConfig.NacosProperties getNacosProperties() {
        return nacosProperties;
    }

    public void setNacosProperties(NacosConfig.NacosProperties nacosProperties) {
        this.nacosProperties = nacosProperties;
    }

    public InMemoryRuleRepositoryAdapter<T> getRuleRepositoryAdapter() {
        return ruleRepositoryAdapter;
    }

    public void setRuleRepositoryAdapter(InMemoryRuleRepositoryAdapter<T> ruleRepositoryAdapter) {
        this.ruleRepositoryAdapter = ruleRepositoryAdapter;
    }

    @Override
    public T save(T entity) {
        T save = ruleRepositoryAdapter.save(entity);
        publishConfig(entity.getApp());
        return save;
    }

    @Override
    public List<T> saveAll(List<T> rules) {
        List<T> ts = ruleRepositoryAdapter.saveAll(rules);
        if(ts!=null && !ts.isEmpty()){
            publishConfig(ts.get(0).getApp());
        }
        return ts;
    }

    @Override
    public T delete(Long id) {
        T delete = ruleRepositoryAdapter.delete(id);
        publishConfig(delete.getApp());
        return delete;
    }

    @Override
    public T findById(Long id) {
        return ruleRepositoryAdapter.findById(id);
    }

    @Override
    public List<T> findAllByMachine(MachineInfo machineInfo) {
        return ruleRepositoryAdapter.findAllByMachine(machineInfo);
    }

    @Override
    public List<T> findAllByApp(String appName) {
        return ruleRepositoryAdapter.findAllByApp(appName);
    }

    private void publishConfig(String app) {
        try {
            List<T> allByApp = ruleRepositoryAdapter.findAllByApp(app);
            List<Object> rules = allByApp.stream().map(NacosEntity::new).map(NacosEntity::getRule).collect(Collectors.toList());
            configService.publishConfig(app + "-" + suffix, nacosProperties.getGroup(), JSON.toJSONString(rules), ConfigType.JSON.getType());
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }

}

注入repository

package com.alibaba.csp.sentinel.dashboard.config;

import com.alibaba.csp.sentinel.dashboard.datasource.entity.gateway.ApiDefinitionEntity;
import com.alibaba.csp.sentinel.dashboard.datasource.entity.gateway.GatewayFlowRuleEntity;
import com.alibaba.csp.sentinel.dashboard.datasource.entity.rule.*;
import com.alibaba.csp.sentinel.dashboard.repository.gateway.InMemApiDefinitionStore;
import com.alibaba.csp.sentinel.dashboard.repository.gateway.InMemGatewayFlowRuleStore;
import com.alibaba.csp.sentinel.dashboard.repository.rule.*;
import com.alibaba.nacos.api.config.ConfigService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

/**
 * @Author Luowenjian
 * @Description
 * @Date 2023/8/1 18:05
 **/
@Configuration
public class NacosRepositoryConfig {
    @Autowired
    private ConfigService configService;
    @Autowired
    private NacosConfig.NacosProperties nacosProperties;

    @Bean
    public NacosRepository<ApiDefinitionEntity> apiDefinitionEntityNacosRepository(InMemApiDefinitionStore inMemApiDefinitionStore){
        return buildNacosRepository("gateway-api-definition",inMemApiDefinitionStore);
    };

    @Bean
    public NacosRepository<GatewayFlowRuleEntity> gatewayFlowRuleEntityNacosRepository(InMemGatewayFlowRuleStore inMemGatewayFlowRuleStore){
        return buildNacosRepository("gateway-flow-rule",inMemGatewayFlowRuleStore);
    };

    @Bean
    public NacosRepository<AuthorityRuleEntity> authorityRuleEntityNacosRepository(InMemAuthorityRuleStore inMemAuthorityRuleStore){
        return buildNacosRepository("authority-rule",inMemAuthorityRuleStore);
    };

    @Bean
    public NacosRepository<DegradeRuleEntity> degradeRuleEntityNacosRepository(InMemDegradeRuleStore inMemDegradeRuleStore){
        return buildNacosRepository("degrade-rule",inMemDegradeRuleStore);
    };

    @Bean
    public NacosRepository<FlowRuleEntity> flowRuleEntityNacosRepository(InMemFlowRuleStore inMemFlowRuleStore){
        return buildNacosRepository("flow-rule",inMemFlowRuleStore);
    };

    @Bean
    public NacosRepository<ParamFlowRuleEntity> paramFlowRuleEntityNacosRepository(InMemParamFlowRuleStore inMemParamFlowRuleStore){
        return buildNacosRepository("param-flow-rule",inMemParamFlowRuleStore);
    };

    @Bean
    public NacosRepository<SystemRuleEntity> systemRuleEntityNacosRepository(InMemSystemRuleStore inMemSystemRuleStore){
        return buildNacosRepository("system-rule",inMemSystemRuleStore);
    };

    private <T extends RuleEntity> NacosRepository<T> buildNacosRepository(String suffix, InMemoryRuleRepositoryAdapter<T> ruleRepositoryAdapter){
        NacosRepository<T> nacosRepository = new NacosRepository<>(suffix);
        nacosRepository.setNacosProperties(nacosProperties);
        nacosRepository.setRuleRepositoryAdapter(ruleRepositoryAdapter);
        nacosRepository.setConfigService(configService);
        return nacosRepository;
    }

}

package com.alibaba.csp.sentinel.dashboard.config;

import com.alibaba.nacos.api.NacosFactory;
import com.alibaba.nacos.api.PropertyKeyConst;
import com.alibaba.nacos.api.config.ConfigService;
import com.alibaba.nacos.api.exception.NacosException;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.util.StringUtils;

import java.util.Properties;

/**
 * @Author Luowenjian
 * @Description
 * @Date 2023/8/1 15:30
 **/
@Configuration
@EnableConfigurationProperties(NacosConfig.NacosProperties.class)
public class NacosConfig {

    @ConfigurationProperties(prefix = "nacos.config")
    public static class NacosProperties{
        private String group = "DEFAULT_GROUP";
        private String namespace;
        private String authDataId = "sentinel-dashboard-auth";
        private Long timeout = 3000L;

        private String serverAddr;

        public String getGroup() {
            return group;
        }

        public void setGroup(String group) {
            this.group = group;
        }

        public String getNamespace() {
            return namespace;
        }

        public void setNamespace(String namespace) {
            this.namespace = namespace;
        }

        public Long getTimeout() {
            return timeout;
        }

        public void setTimeout(Long timeout) {
            this.timeout = timeout;
        }

        public String getServerAddr() {
            return serverAddr;
        }

        public void setServerAddr(String serverAddr) {
            this.serverAddr = serverAddr;
        }

        public String getAuthDataId() {
            return authDataId;
        }

        public void setAuthDataId(String authDataId) {
            this.authDataId = authDataId;
        }
    }

    @Bean
    public ConfigService configService(NacosProperties nacosProperties) throws NacosException {
        Properties properties = new Properties();
        properties.setProperty(PropertyKeyConst.SERVER_ADDR, nacosProperties.getServerAddr());
        if (!StringUtils.isEmpty(nacosProperties.getNamespace())) {
            properties.setProperty(PropertyKeyConst.NAMESPACE, nacosProperties.getNamespace());
        }
        return NacosFactory.createConfigService(properties);
    }

}

最后替换掉对应Controller中对应的repository,如

@RestController
@RequestMapping(value = "/v1/flow")
public class FlowControllerV1 {

    private final Logger logger = LoggerFactory.getLogger(FlowControllerV1.class);

    @Autowired
    private NacosRepository<FlowRuleEntity> repository;

添加参数配置

nacos.config.namespace=xxx
nacos.config.serverAddr=xxx
nacos.config.group=xxx

客户端需要添加pom

        <dependency>
            <groupId>com.alibaba.csp</groupId>
            <artifactId>sentinel-datasource-nacos</artifactId>
            <version>xxxx</version>
        </dependency>
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值