sentinel源码分析第二篇一sentinel-dashboard控制台启动与配置

本文详细介绍了Sentinel的push模式工作原理,包括控制台如何配置规则并推送到Zookeeper,以及客户端如何监听并更新规则。Sentinel控制台通过API持久化规则到内存并推送至Zookeeper,客户端通过ZookeeperDataSource监听规则变化并全量覆盖更新。在生产环境中,使用注册中心如Zookeeper可以确保规则的持久化和高可用。
摘要由CSDN通过智能技术生成

| 工作原理

  • 应用程序启动时需配置控制台地址,使得应用程序与控制台进行交互
  • 应用程序负责向控制台注册
  • 控制台负责配置规则信息
  • 应用程序通过监听等方式拉取rule到本地,等待流量到达依据配置进行限流

|| push模式工作原理

控制台配置规则

在这里插入图片描述

应用程序监听规则

在这里插入图片描述

||| 源码分析

A 控制台

  • 控制台模块是一个轻量级springboot模块
  • 用户通过FlowControllerV2配置规则并且推送zk等配置中心
    在这里插入图片描述

控制台配置

在这里插入图片描述

  • 按照类型修改DynamicRuleProvider和DynamicRulePublisher为zk,nacos等
@RestController
@RequestMapping(value = "/v2/flow")
public class FlowControllerV2 {

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

    @Autowired
    private InMemoryRuleRepositoryAdapter<FlowRuleEntity> repository;

    @Autowired
    @Qualifier("flowRuleDefaultProvider")
    private DynamicRuleProvider<List<FlowRuleEntity>> ruleProvider;
    @Autowired
    @Qualifier("flowRuleDefaultPublisher")
    private DynamicRulePublisher<List<FlowRuleEntity>> rulePublisher;
}

控制台推送

apiAddFlowRule
  • 持久化于内存
  • 推送zk
 @PostMapping("/rule")
 @AuthAction(value = AuthService.PrivilegeType.WRITE_RULE)
 public Result<FlowRuleEntity> apiAddFlowRule(@RequestBody FlowRuleEntity entity) {

     Result<FlowRuleEntity> checkResult = checkEntityInternal(entity);
     if (checkResult != null) {
         return checkResult;
     }
     entity.setId(null);
     Date date = new Date();
     entity.setGmtCreate(date);
     entity.setGmtModified(date);
     entity.setLimitApp(entity.getLimitApp().trim());
     entity.setResource(entity.getResource().trim());
     try {
         持久化于内存
         entity = repository.save(entity);
         推送zk
         publishRules(entity.getApp());
     } catch (Throwable throwable) {
         logger.error("Failed to add flow rule", throwable);
         return Result.ofThrowable(-1, throwable);
     }
     return Result.ofSuccess(entity);
 }
publishRules
  • 获取所有的规则并且推送zk
private void publishRules(/*@NonNull*/ String app) throws Exception {
     List<FlowRuleEntity> rules = repository.findAllByApp(app);
     // FlowRuleApiPublisher
     // FlowRuleApolloPublisher
     // FlowRuleNacosPublisher
     // FlowRuleZookeeperPublisher
     rulePublisher.publish(app, rules);
 }

B 客户端程序

客户端改造

  • Sentinel 针对 ZooKeeper 作了相应适配,底层可以采用 ZooKeeper 作为规则配置数据源。使用时只需添加以下依赖:
<dependency>
    <groupId>com.alibaba.csp</groupId>
    <artifactId>sentinel-datasource-zookeeper</artifactId>
    <version>x.y.z</version>
</dependency>
  • 然后创建 ZookeeperDataSource 并将其注册至对应的 RuleManager 上即可
// remoteAddress 代表 ZooKeeper 服务端的地址
// path 对应 ZK 中的数据路径
ReadableDataSource<String, List<FlowRule>> flowRuleDataSource = new ZookeeperDataSource<>(remoteAddress, path, source -> JSON.parseObject(source, new TypeReference<List<FlowRule>>() {}));
FlowRuleManager.register2Property(flowRuleDataSource.getProperty());

客户端监听与更新

  • 通过zklistener 监听规则变更
  • 全量覆盖更新规则
public class ZookeeperDataSource<T> extends AbstractDataSource<String, T> {
    ...... 删除大量代码
    private void initZookeeperListener(final String serverAddr, final List<AuthInfo> authInfos) {
        ...... 删除大量代码
       this.listener = new NodeCacheListener() {
            @Override
            public void nodeChanged() {
                zk变更
                try {
                    newValue也就是配置的rule信息 比如限流 熔断 等
                    T newValue = loadConfig();
                    RecordLog.info(String.format("[ZookeeperDataSource] New property value received for (%s, %s): %s",
                            serverAddr, path, newValue));
                    
                    更新时同时更新ruleManager的相关规则信息
                    Property对应也存在与ruleManager中
                    getProperty().updateValue(newValue);
                } catch (Exception ex) {
                    RecordLog.warn("[ZookeeperDataSource] loadConfig exception", ex);
                }
            }
        };
    }
}

更新实现

getProperty().updateValue(newValue);更新实现

  • Property注册到FlowRuleManager

FlowRuleManager.register2Property(flowRuleDataSource.getProperty());
  • 修改currentProperty规则信息为zk监听器的property
 public class FlowRuleManager {
    限流规则信息
    private static SentinelProperty<List<FlowRule>> currentProperty = new DynamicSentinelProperty<List<FlowRule>>();

    public static void register2Property(SentinelProperty<List<FlowRule>> property) {
    AssertUtil.notNull(property, "property cannot be null");
    synchronized (LISTENER) {
        currentProperty.removeListener(LISTENER);
        property.addListener(LISTENER);
        修改currentProperty规则信息为zk监听器的property
        currentProperty = property;
    }
}   

总结

  • 生成环境一般采用注册中心保障规则持久化,不会因为宕机丢失
  • 本文概述push模式的实现,sentinel还有pull,内存直接推送模式
Sentinel Dashboard是一个阿里巴巴开源的分布式系统监控和流量控制平台的前端展示组件。如果启动时遇到问题,可能是由以下几个原因导致: 1. **依赖问题**:检查是否有正确的依赖项安装,并且版本是否匹配Sentinel Dashboard的需求。确认Java、Node.js(如果使用)等运行环境已经正确配置。 2. **配置错误**:确保配置文件(如application.yml或config.json)中的服务器地址、端口、数据库连接等设置没有问题。 3. **权限不足**:运行Sentinel Dashboard的用户可能没有足够的权限访问系统资源,比如数据库或日志文件。 4. **文件路径问题**:如果配置了静态资源的路径,确保这些路径是存在的并且有正确的读取权限。 5. **服务冲突**:如果有其他服务占用相同的端口,Sentinel Dashboard无法启动。检查并关闭占用的进程。 6. **环境问题**:在某些环境下,如Windows,可能需要特别的命令行启动参数或者以管理员身份运行。 7. **网络问题**:如果Sentinel Dashboard依赖于网络服务(如Zookeeper或etcd),网络连接异常也可能导致启动失败。 8. **代码bug**:如果最近对代码进行了修改,可能存在未识别的bug,需要查看最新的错误日志获取更多信息。 为了解决这个问题,你可以按照以下步骤操作: 1. 查看控制台的错误日志(通常会有详细的错误信息)。 2. 使用`--debug`或`-Ddebug=true`启动模式获取更详细的调试信息。 3. 如果是网络相关的错误,尝试重启网络服务或者更改配置。 4. 逐个排除上述可能的问题点。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值