流控神器-Sentinel-资源节点树的构成(NodeSelectorSlot)

本文详细介绍了Sentinel中资源节点树的构建,包括Resource、Context、Entry和Node的概念及其作用。重点分析了NodeSelectorSlot如何根据资源名创建和选取节点,以及在相同和不同资源名情况下Node的处理逻辑。Sentinel采用责任链模式,通过NodeSelectorSlot收集资源调用路径,用于流量控制和降级策略。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

目录

 

1. 概述

2. 一些需要知道的前提

2.1. Resource

2.2. Context

2.3. Entry

2.4. Node

3. 深入分析

3.1. demo启动

3.2. 创建Context

3.3. 创建Entry

3.4. 执行NodeSelectorSlot.entry

3.4.1. 相同资源名情况下

3.4.2. 不同资源名情况下


1. 概述

之前分析过Sentinel是基于责任链的模式,其逻辑处理部分是一个有一个的Slot

这里大概的介绍下每种Slot的功能职责:

  • NodeSelectorSlot 负责收集资源的路径,并将这些资源的调用路径,以树状结构存储起来,用于根据调用路径来限流降级;

  • ClusterBuilderSlot 则用于存储资源的统计信息以及调用者信息,例如该资源的 RT, QPS, thread count 等等,这些信息将用作为多维度限流,降级的依据;

  • StatisticsSlot 则用于记录,统计不同维度的 runtime 信息;

  • SystemSlot 则通过系统的状态,例如 load1 等,来控制总的入口流量;

  • AuthoritySlot 则根据黑白名单,来做黑白名单控制;

  • FlowSlot 则用于根据预设的限流规则,以及前面 slot 统计的状态,来进行限流;

  • DegradeSlot 则通过统计信息,以及预设的规则,来做熔断降级;

每个Slot执行完业务逻辑处理后,会调用fireEntry()方法,该方法将会触发下一个节点的entry方法,下一个节点又会调用他的fireEntry,以此类推直到最后一个Slot,由此就形成了sentinel的责任链。

2. 一些需要知道的前提

2.1. Resource

资源,是Sentinel世界中的抽象,任何东西都能被定义成资源,自己提供的服务,调用的服务,甚至一段代码,有了资源才能在资源上定义规则,去进行限流降级之类的操作

在Sentinel中提供了两个默认是Resource分别是StringResourceWrapper和MethodResourceWrapper

2.2. Context

Context是上下文的意思,一个线程对应一个Context

其中有三个属性

  • name:名字
  • entranceNode:调用链入口
  • curEntry:当前entry
  • origin:调用者来源
  • async:异步

2.3. Entry

每次调用 SphU.entry() 都会生成一个Entry入口,该入口中会保存了以下数据:入口的创建时间,当前入口所关联的节点(Node),当前入口所关联的调用源对应的节点。Entry是一个抽象类,他只有一个实现类,在CtSph中的一个静态类:CtEntry

其中有这些属性

  • createtime
  • curNode
  • originNode
  • error
  • resourceWrapper
  • parent
  • child
  • chain
  • context

红色的是抽象类Entry的,黑色的是CtEntry中的

一个Entry相当于一个token只有正常生成了一个entry才能算pass,不然报异常BlockException肯定是限流了

2.4. Node

节点是用来保存某个资源的各种实时统计信息的,他是一个接口,通过访问节点,就可以获取到对应资源的实时状态,以此为依据进行限流和降级操作。

有几种节点类型

  • StatisticNode:统计节点
  • DefaultNode:默认节点,NodeSelectorSlot中创建的就是这个节点
  • ClusterNode:集群节点
  • EntranceNode:该节点表示一棵调用链树的入口节点,通过他可以获取调用链树中所有的子节点

3. 深入分析

3.1. demo启动

Entry entry = null;

try {

    entry = SphU.entry("abc");

    entry = SphU.entry("abc");

} catch (BlockException e1) {

     

} finally {

    if (entry != null) {

        entry.exit();

    }

}

CtSph.entryWithPriority

private Entry entryWithPriority(ResourceWrapper resourceWrapper, int count, boolean prioritized, Object... args)

    throws BlockException {

    //先从ThreadLocal获取,第一次肯定是null

    Context context = ContextUtil.get
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值