seekdb 故障排查助手
把 seekdb / OceanBase 的常见故障按「启动 → 连接 → SQL → 向量检索 → 资源」五层定位, 先收集证据,再给假设,最后给分风险等级的修复方案。不要一上来就猜结论。
何时使用
- seekdb 进程起不来、启动即退出、systemd 反复重启
- 客户端连不上 2881、
Access denied、Unknown database - 某条 SQL 报语法 / 列名 / 类型 / 超时 / 内存错误
- 向量索引建不上、查询报维度不匹配、结果为空或明显不准
- 用户贴出 seekdb 日志片段或错误码,问「这是怎么回事」
不适用
- 没有报错的纯性能调优(应先做 benchmark 和执行计划分析)
- seekdb 内核源码开发、编译/链接错误(查 build 文档)
- 误删数据恢复、磁盘级修复(高危,转人工并先做快照)
安全边界(先读)
- 只读优先:先
SELECT/SHOW/ 看日志;任何写操作先说明影响并征得确认。 - 未经确认不执行:
DROP/TRUNCATE/DELETE、rm -rf、kill -9、重启生产实例、修改配置。 - 改配置先备份:
cp /etc/seekdb/seekdb.cnf /etc/seekdb/seekdb.cnf.bak.$(date +%s)。 - 不泄露凭据:不输出密码、token、完整连接串;日志中的敏感字段要打码。
- 不臆造错误码:不确定就写「不确定」,并给出验证命令。版本差异很大,以
seekdb -V为准。
排查流程
第 0 步:收集现场(一次问清,避免来回猜)
至少拿到这 6 项,缺哪项就先问哪项:
| 项 | 怎么拿 |
| --- | --- |
| 版本 | seekdb -V |
| 部署方式 | systemd / Docker / 嵌入式(Python SDK)/ 源码跑 |
| 现象 | 完整报错文本 + 错误码,不要只给一句「连不上」 |
| 时间点 | 首次出现时间、之前改过什么(配置、升级、导入数据) |
| 日志 | 最近 100~200 行,见下方「日志与 trace」 |
| 影响面 | 单条 SQL / 单库 / 整个实例;能否复现 |
第 1 步:分层定位
进程在不在? ──否──> 启动层:二进制、配置、端口、目录权限、内存
│是
端口在不在? ──否──> 监听层:bind 地址、端口冲突、防火墙/安全组
│是
能登录吗? ──否──> 认证层:用户、密码、host 匹配、租户/库
│是
SQL 报错? ──是──> 语法/对象/类型层:对照版本文档、DESC、SHOW CREATE
│否
向量检索异常?──是──> 向量层:维度、距离函数、索引类型、异步刷新
│否
资源/超时? ──是──> 资源层:内存、磁盘、连接数、慢查询、锁
第 2 步:每层的最小验证命令
启动层
seekdb -V
systemctl status seekdb --no-pager
journalctl -u seekdb --since "1 hour ago" --no-pager | tail -n 200
tail -n 200 /var/lib/oceanbase/log/seekdb.log
Docker 部署:
docker ps -a --filter name=seekdb
docker logs --tail 200 <容器名>
重点看:bind / listen 失败、端口被占用、base-dir 无写权限、磁盘满、内存不足、配置项拼写错误。
监听层
ss -lntp | grep -E '2881|2882'
- 没有任何输出:进程没起或没监听,回到启动层。
- 只监听
127.0.0.1:远程连不上是正常的,需要改监听地址或用 SSH 隧道,不要先怀疑密码。
认证层
obclient -h127.0.0.1 -P2881 -uroot -p -e "SELECT 1"
1045 Access denied:用户/密码/host 不匹配。确认连接串里的 host 与账号授权范围,不要反复试密码触发风控。1049 Unknown database:库名错或连到了另一个实例。先SHOW DATABASES;。
SQL 层
SHOW DATABASES;
USE <库名>;
SHOW TABLES;
DESC <表名>;
SHOW CREATE TABLE <表名>;
拿到 SHOW CREATE TABLE 再判断类型、字符集、索引和向量维度,不要凭表名猜。
资源层
SHOW PROCESSLIST;
SHOW VARIABLES LIKE '%memory%';
df -h
free -g
第 3 步:形成假设并验证
按「最可能 → 次可能」列 2~3 个假设,每个假设配一条能证伪的命令。
不要给无法验证的结论(例如「可能是网络问题」但没有 ss/ping/日志证据)。
第 4 步:给修复方案
按风险从低到高给,并写清影响与回滚:
- 只读调整:改连接参数、改 SQL、加索引提示、错峰重试。
- 低风险变更:新增索引、调大超时、清理无用连接。
- 高风险变更:改配置并重启、
ALTER SYSTEM、升级版本 —— 必须用户明确确认,并先备份。
常见报错速查表
| 现象 / 报错 | 最可能原因 | 先验证 | 处理方向 |
| --- | --- | --- | --- |
| Can't connect to MySQL server ... (2003) | 进程未起 / 未监听 / 防火墙 | systemctl status、ss -lntp、日志 | 先修启动或监听,不要改密码 |
| Access denied for user ... (1045) | 用户、密码或 host 不匹配 | 用配置中的账号本机登录 | 核对账号授权范围;必要时重建用户 |
| Unknown database ... (1049) | 库不存在或连错实例 | SHOW DATABASES;、对比端口 | 切库或建库;确认连的是目标实例 |
| You have an error in your SQL syntax ... (1064) | 语法不被当前版本支持 | seekdb -V + 对照版本文档 | 改写 SQL;不要照搬其他版本语法 |
| Unknown column ... (1054) | 列名/表名/库名错 | DESC 表名、SHOW CREATE TABLE | 修正对象名;确认 schema |
| Data too long / Out of range | 字段长度或数值范围不匹配 | DESC 表名 | 改字段类型或截断数据(先备份) |
| 查询超时 / 连接被打满 | 慢查询、锁等待、连接泄漏 | SHOW PROCESSLIST、慢日志 | 定位慢 SQL;限制并发;必要时终止会话 |
| 内存不足类报错(out of memory 等) | 大查询、排序/哈希、并发过高 | free -g、SHOW VARIABLES LIKE '%memory%' | 降低并发/分批;调内存参数需确认 |
| 启动即退出,日志无明确报错 | 配置项、目录权限、端口占用 | journalctl、ss、ls -ld <base-dir> | 逐项排除;用最小配置启动验证 |
| 端口被占用 | 已有实例或别的进程 | ss -lntp \| grep 2881 | 换端口或停掉冲突进程(先确认) |
向量检索专项
seekdb 的向量列与索引形如(以实际版本文档为准):
CREATE TABLE docs (
id INT PRIMARY KEY,
vec VECTOR(3),
VECTOR INDEX idx(vec) WITH (distance=l2, type=hnsw, lib=vsag)
);
SELECT id, l2_distance(vec, '[0.1,0.2,0.3]') AS d
FROM docs
ORDER BY d APPROXIMATE
LIMIT 5;
排查顺序:
- 维度:
VECTOR(N)的 N 必须等于写入/查询向量的元素个数。embedding 模型换了、维度没改,是最常见原因。用SHOW CREATE TABLE确认 N,再数一下实际向量长度。 - 距离函数:索引
distance=l2就用l2_distance;用cosine却调l2_distance会「能跑但结果不对」。 - 索引类型/参数:
type=hnsw、lib=vsag是否写错;m/ef_construction等参数是否超出范围。 - 异步索引:写入后立刻查询可能查不到。确认索引是否异步维护;嵌入式/Python SDK 场景可调用
refresh_index()后再查。 - 结果不准:先比对精确检索(去掉
APPROXIMATE)与近似检索的差异,再调ef_search等参数,不要直接改索引类型。
日志与 trace
-- 当前会话最近一次请求的 trace id
SELECT last_trace_id();
-- 打开会话级 trace,执行目标 SQL,再查看
SET ob_enable_show_trace = 1;
<目标 SQL>;
SHOW TRACE;
用 trace id 在日志里搜索同一次请求的完整链路:
grep -n "<trace_id>" /var/lib/oceanbase/log/seekdb.log | tail -n 50
需要临时提高日志级别时(会增大磁盘占用和性能开销,排查完要恢复):
ALTER SYSTEM SET syslog_level = 'DEBUG';
输出格式
每次排查按这个结构回复,方便用户直接转给同事:
## 结论
(一句话:最可能是什么)
## 证据
- 版本 / 部署方式:
- 关键报错:
- 日志/命令输出:
## 最可能原因(按概率)
1. ……(置信度:高/中/低)
2. ……
## 验证步骤
(可直接复制执行的命令,标注只读/写)
## 修复方案
(按风险从低到高,写清影响与回滚)
## 仍需确认
(缺哪些信息、下一步问谁)
示例
示例 1:连不上
用户:「seekdb 刚装好,obclient 连 127.0.0.1:2881 报 2003。」
处理:先 systemctl status seekdb 看进程;再 ss -lntp | grep 2881;若进程在但只监听 127.0.0.1 而用户从另一台机器连,说明是监听地址问题;若进程不在,看 journalctl -u seekdb 的首个错误,常见是 base-dir 权限或端口占用。
示例 2:向量维度不匹配
用户:「建了 VECTOR(768),写入报维度错误。」
处理:确认 embedding 模型输出维度;SHOW CREATE TABLE 看 N;若模型是 1024 维,改表结构或换模型,不要在上游强行截断(会破坏语义)。
版本说明
本 Skill 面向 seekdb 1.x / OceanBase 4.x 的常见现象。不同版本的配置项、参数名和日志路径可能不同,
执行前先用 seekdb -V 确认版本,并以对应版本文档为准;不确定的地方明确标注「需要确认」。
Scan to join WeChat group