首批通过分布式安全可靠测评,为关键业务系统打造
黑名单机制
更新时间:2026-04-07 20:57:20
ODP 使用黑名单机制自适应处理 OBServer 节点的错峰合并、升级、leader 切换、宕机、启动和停止等过程中的 OBServer 节点访问控制。
背景信息
ODP 有状态黑名单、探测黑名单和活不可用黑名单三种类型,可通过设置参数对黑名单进行管理。
通过黑名单可主要实现如下场景的访问控制:
错峰合并时正在合并的 Zone 没有流量。
集群升级时不能访问正在升级的 OBServer 节点或 Zone。
OBServer 节点宕机后,不再访问该 OBServer 节点。
Partition 迁移后,不再访问迁移前的 OBServer 节点。
访问的 OBServer 节点不存在租户资源时重试。
OBServer 节点活着不可用(内存超限、超时、OBServer 节点初始化和退出)时重试。
状态黑名单
状态黑名单依赖于 OBServer 节点的状态变更。因为历史原因,和状态黑名单相关的状态不包含 DETECT_ALIVE 和 DETECT_DEAD 两种状态,剩下的状态变更都可以通过访问 OBServer 节点的视图获得。
当通过周期任务获得 OBServer 节点最新状态后,ODP 会进行根据 OBServer 节点状态的不同分别进行如下操作。
ACTIVE:将 OBServer 节点从状态黑名单中移除,洗白 OBServer 节点。INACTIVE/REPLAY:将 OBServer 节点加入状态黑名单。DELETED/DELETING状态:更新内存中 OBServer 节点的机器列表,不会向该节点转发 SQL。UPGRADE状态:不加入状态黑名单,但也不会向该节点转发 SQL,效果和黑名单类似。
探测黑名单
状态黑名单是从 OceanBase 的总控服务节点(Root Service)处获得信息,这种信息有时不能反映 ODP 和 OBServer 节点之间的情况。如下图所示,ODP 从 RS 处获得 OBServer1 节点状态为 ACTIVE,但 ODP 和 OBServer1 节点之间网络不通。

因此,ODP 在现有的状态黑名单基础上又实现了探测黑名单,通过给 OBServer 节点发送探测 SQL 来确定 OBServer 节点状态。ODP 会给 OceanBase 数据库的 sys 租户发送探测 SQL select 'detect server alive' from dual,并设置 5s 的超时时间,当超时时间内无结果返回时,会增加一次探测失败次数,当连续失败次数超过 3 次后认为探测失败,设置 OBServer 节点状态为 DETECT_DEAD。如果有结果返回,会将探测失败次数清零,设置 OBServer 节点状态为 DETECT_ALIVE。发生探测状态变更后,触发 ODP 行为如下。
DETECT_ALIVE状态:将 OBServer 节点从探测黑名单中洗白。DETECT_DEAD状态:将 OBServer 节点加入到探测黑名单,并将所有和该 OBServer 节点的连接关闭。
说明
如果将 OBServer 节点加入到探测黑名单后,不断开和该 OBServer 节点的连接,那么连接会被一直占用,无法发送新的 SQL,在性能数据上会看到这段时间的这台 OBServer 节点的 TPS 为 0。断开后,对于后续请求,ODP 会根据黑名单进行路由,不会转发给这台 OBServer 节点,TPS 就可以恢复。
活不可用黑名单
活不可用黑名单机制的核心是根据业务 SQL 的执行结果去定义 OBServer 节点的状态,触发拉黑和洗白操作。相较于状态黑名单和探测黑名单,活不可用黑名单的拉黑和洗白谨慎了很多,主要是为了防止一次 SQL 执行结果产生误判。具体操作如下。
失败:根据时间点记录下一次失败事件。
ODP 向 OBServer 节点发送 SQL 后,超过 ob_query_timeout 时间后仍然无响应。
OBServer 节点返回错误码 OB_SERVER_IS_INIT、OB_SERVER_IS_STOPPING、OB_PACKET_CHECKSUM_ERROR、OB_ALLOCATE_MEMORY_FAILED。
ODP 和 OBServer 节点建连失败/报文解析失败,数据传输失败。
拉黑:默认情况下,OBServer 节点在 120s 内有五次活不可用的失败记录则拉黑这台 OBServer 节点,由配置项 congestion_fail_window(错误统计周期)和 congestion_failure_threshold(出错次数)控制。
尝试:默认情况下,加入活不可用黑名单超过 20s 后,尝试再次向该 OBServer 节点发送 SQL。重试时间间隔由
congestion_retry_interval配置项控制。洗白:如果尝试的 SQL 执行成功则进行洗白。默认 OBServer 节点在 20s 内不允许被洗白,该值由配置项
min_keep_congestion_interval控制。
上述三种黑名单之间并没有优先级,只要 OBServer 节点在任何一个黑名单中,这台机器就无法接收请求。换而言之,只有当 OBServer 节点不在任何黑名单中才会接收到请求。
所有可选择的 OBServer 节点都处于黑名单中时,会强制重试黑名单中的 OBServer 节点。
黑名单的配置参数
在客户端中使用 root 用户,通过 ODP 代理登录集群的
sys租户。obclient> obclient -h10.10.10.1 -uroot@sys#obdemo -P2883 -p -c此处是以 ODP 机器 IP 为
10.10.10.1,集群名称为obdemo为例,通过 OBClient 连接集群。连接 OceanBase 租户的详细操作可参见 连接方式概述(MySQL 模式) 和 连接方式概述(Oracle 模式)。执行以下命令查看 ODP 的配置参数。
obclient> SHOW PROXYCONFIG;运行
ALTER proxyconfig SET key=value命令更新 ODP 的指定配置参数,配置项更新后会立即生效。与黑名单相关的配置参数描述如下表所示。
配置项 描述 enable_congestion 是否启用黑名单机制。默认开启,在黑名单机制运行出问题时,可以暂时关闭这个选项让 ODP 能够正常工作。 congestion_failure_threshold 控制是否将 OBServer 节点列入黑名单,与 congestion_fail_window搭配使用,在congestion_fail_window时间内,OBServer 节点出错次数超过该值时,ODP 会将该 OBServer 节点加入黑名单。该参数值小于 0 时,则所有在黑名单中的 Server 都会被放出黑名单。congestion_fail_window 设置错误统计周期的时间(秒),默认值 120 秒。如果在错误统计周期中错误次数超过 congestion_failure_threshold的值,则将该 Server 节点加入黑名单。该参数值也可以动态调整,一旦修改了该参数,当前错误统计计数会被清零,将重新按新配置的值开始统计错误次数。congestion_retry_interval 设置被加入活不可用黑名单的 OBServer 节点重试周期,默认值 20 秒。 min_keep_congestion_interval 设置被加入黑名单的 OBServer 节点,多长时间后才允许被放出黑名单。 min_congested_connect_timeout 设置客户端连接超时的值,当连接超时时则将 OBServer 节点加入活不可用黑名单,默认值为 100ms。
查看黑名单
在客户端中使用 root 用户,通过 ODP 代理登录集群的
sys租户。obclient> obclient -h10.10.10.1 -uroot@sys#obdemo -P2883 -p -c此处是以 ODP 机器 IP 为
10.10.10.1,集群名称为obdemo为例,通过 OBClient 连接集群。连接 OceanBase 租户的详细操作可参见 连接方式概述(MySQL 模式) 和 连接方式概述(Oracle 模式)。执行以下命令,查看黑名单信息。
语句如下:
SHOW PROXYCONGESTION [all] [clustername];相关参数说明如下:
不指定可选项时,可查询所有集群的黑名单信息。
仅指定
all时,可显示所有集群的 OBServer 节点信息(包括黑名单中和非黑名单中的 OBServer 节点信息)。仅指定
clustername时,可显示指定集群的黑名单信息。同时指定
all和clustername时,可显示指定集群的 OBServer 节点信息。
示例
此处以查看单节点集群 obcluster 黑名单信息为例。
obclient> show proxycongestion 'obcluster'\G
输出如下:
*************************** 1. row ***************************
cluster_name: obcluster
zone_name: zone1
region_name: sys_region
zone_state: ACTIVE
server_ip: xxx.xxx.xxx.xxx:2881
cr_version: 5
server_state: ACTIVE
alive_congested: 0
last_alive_congested: 0
dead_congested: 0
last_dead_congested: 0
stat_alive_failures: 0
stat_conn_failures: 0
conn_last_fail_time: 0
conn_failure_events: 0
alive_last_fail_time: 0
alive_failure_events: 0
ref_count: 2
detect_congested: 0
last_detect_congested: 0
说明
当
dead_congested和alive_congested中的任意一个状态为1时,表示该 OBServer 节点已加入黑名单。ODP V1.1.2 版本之前,
clustername不需要单引号或者双引号引起来,V1.1.2 版本及之后,必须要用单引号或者双引号引起来。