学习报告(三):DM-Oracle DBLINK 类"宕机"问题的复现测试方法
适用对象:客户报"执行 select ... from xxx@link 导致数据库宕机/崩溃"这类疑似产品缺陷的问题,需要复现、定位并给结论
一、先建立认知:这类任务的性质是"复现测试",不是"排障"
|
常规排障 |
复现测试(本类) |
| 目标 |
恢复业务 |
判定产品问题还是客户环境问题 |
| 手段 |
现场取证、消除故障 |
控制变量、逐项对齐环境 |
| 产物 |
根因 + 处置 |
复现结论 + 证据包 + (给厂商的)缺陷提交材料 |
| 结论措辞 |
确定根因 |
必须分级:已实测证实 / 高度指向 / 待补测 |
核心纪律:结论没做完对照实验前,不能写"已定位为产品缺陷",也不能写"复现不了所以没问题"。
二、总体思路:环境对齐矩阵 + 分层隔离
┌── ① DM 侧:版本/构建号、字符集、实例参数、日志、core
DBLINK ────┼── ② 客户端侧:Oracle Instant Client 版本、环境变量、TNS 配置
├── ③ 网络侧:路由、防火墙、监听可达性
└── ④ 目标库侧:Oracle 版本、PDB/服务名、用户权限、监听注册
关键动作:先做"环境对齐",。
| 维度 |
必须对齐的内容 |
本案取值 |
| DM 版本 |
完整构建号(v$version) |
08134284368-20250527-275278-20149 |
| DM 字符集 |
与客户一致 |
UTF-8(CHARSET=1) |
| DM 页大小/端口 |
尽量一致 |
PAGE_SIZE 16 / 5236 |
| Oracle 客户端 |
版本是重中之重 |
客户 23.x;手册原写 11.2.0.4.0 → 实测用 23.26.3.0.0 |
| 目标库 |
版本、PDB、用户、表 |
Oracle XE 21c / XEPDB1 / scott / t1 |
| 网络路径 |
NAT/桥接、网段、防火墙 |
VMware NAT 192.168.45.0/24,放行 1521 |
| 触发语句 |
完全照抄 |
select 1 from dual@link1 |
三、六个入手方向
| # |
方向 |
要回答的问题 |
| 1 |
触发语句最小化 |
崩溃点是 select 1 from dual@link 还是任意查询? |
| 2 |
建链方式 |
connect 'ORACLE' 还是 'DPI'?两者驱动路径完全不同 |
| 3 |
客户端版本 |
11.2 / 19 / 23 —— 是否与客户一致?(本案关键变量) |
| 4 |
环境变量 |
ORACLE_HOME / TNS_ADMIN / LD_LIBRARY_PATH / PATH 是否正确 |
| 5 |
崩溃取证 |
有无 core?dmhalt dump?gdb 栈?DM 日志 FATAL? |
| 6 |
目标库侧 |
监听注册是否完成、老客户端协议是否放行(ORA-28040) |
四、语句/命令库
4.1 复现环境搭建
dminit PATH=/data/dmdata DB_NAME=webtadb INSTANCE_NAME=webtadb \
PORT_NUM=5236 CHARSET=1 PAGE_SIZE=16
ulimit -c unlimited
echo "/data/dmdata/core.%e.%p" > /proc/sys/kernel/core_pattern
tmux new -s dm
cd /dm/dmdbms/bin && ./dmserver /data/dmdata/webtadb/dm.ini
CREATE OR REPLACE PUBLIC LINK link1 CONNECT 'ORACLE'
WITH SCOTT IDENTIFIED BY "SCOTT123" USING 'ORCL';
SELECT * FROM t1@link1;
SELECT 1 FROM dual@link1;
while true; do pgrep -x dmserver >/dev/null || { echo "$(date) dmserver GONE"; break; }; sleep 1; done
4.2 Oracle 客户端环境
export ORACLE_HOME=/opt/oracle/instantclient_23_26
export TNS_ADMIN=$ORACLE_HOME/network/admin
export LD_LIBRARY_PATH=$ORACLE_HOME:$LD_LIBRARY_PATH
export PATH=$ORACLE_HOME:$PATH
ln -s $ORACLE_HOME/libclntsh.so.11.1 $ORACLE_HOME/libclntsh.so
$ORACLE_HOME/sqlplus -V
sqlplus scott/SCOTT123@//192.168.45.1:1521/XEPDB1
4.3 目标库侧(Oracle)
SELECT name, open_mode FROM v$pdbs;
SELECT name FROM v$services;
vi $ORACLE_HOME/network/admin/sqlnet.ora
SQLNET.ALLOWED_LOGON_VERSION_CLIENT=8
SQLNET.ALLOWED_LOGON_VERSION_SERVER=8
4.4 崩溃取证
ls -l /data/dmdata/core.*
ls -l /soft/dmdbms/log/dmhalt_*
grep -iE "FATAL|SHUTDOWN|coredump|signal" /data/dmdbms/log/dm_*.log | tail -50
gdb -q /dm/dmdbms/bin/dmserver /data/dmdata/core.dmserver.<pid> -ex "bt" -ex "quit"
五、分步处置流程(Step by Step)
Step 1:把客户报障翻译成"可执行的最小用例"
- 明确:DM 版本/构建、字符集、DBLINK 类型(ORACLE/DPI)、客户端版本、目标库版本、具体触发语句。
- 客户只说"执行 xxx 就宕机"时,要追问:是否每次都崩?换语句崩不崩?换客户端崩不崩? —— 这几个问题直接决定复现路径。
Step 2:搭环境并逐项对齐(写下矩阵)
- DM 初始化(
CHARSET=1 与客户一致);
- 装 Oracle 目标库 + 建用户/表;
- 装客户端并配置环境变量;
- 把每一处偏离客户环境的地方记下来(如"客户 23.x,本机先用 11.2 还是 23.x"→ 决定测试顺序)。
Step 3:功能基线验证(先证明链路通)
create or replace public link ... 成功;
select * from t1@link1 成功(返回 1 dmtest);
- 再打崩溃点
select 1 from dual@link1。
- 先证通、再打崩溃点,否则分不清"配置没通"还是"触发缺陷"。
Step 4:复现判定
- 观察
dmserver 进程是否存活(前台 tmux + 存活监控)。
- 若未崩溃:记录版本、客户端、日志;不要立刻下"复现不了"结论,先做变量对照。
Step 5:做变量对照实验(本类任务的核心)
- 每次只变一个变量,优先变最可疑的那个(本案 = 客户端版本):
- 23.x 客户端 →
select 1 from dual@link1 → 结果?
- 切回 11.2(改
/etc/profile + libclntsh.so 软链 + 重启 dmserver)→ 再打同一条 → 结果?
- 记录每次的:客户端版本、DM 构建、结果、日志差异。
Step 6:崩溃时的证据固化
- 抓 core、
dmhalt dump、DM 日志 FATAL 段、gdb bt 栈、当时的 dmesg/内核日志。
- 这些是提交厂商的必要材料,缺一项结论就站不住。
六、搭建过程中会踩的坑
A. Oracle XE 21c 建库(Windows)
| 报错 |
原因 |
解决 |
ORA-00821 |
sga_target=1536M 小于 32 核自动下限 |
建库时显式指定 cpu_count=8, sga_target=1536M, pga_aggregate_target=512M |
ORA-56752 |
调大 SGA 又撞 XE 上限 |
同上(核心/内存参数互相冲突,需一起指定) |
DIM-00019 创建服务拒绝访问 |
dbca 权限不足 |
以管理员身份运行 |
ORA-12514 服务不可识别 |
监听重启后 PMON 注册延迟 |
等待或重启 OracleServiceXE |
ORA-65096 公用用户名无效 |
普通用户须建在 PDB |
先切到 XEPDB1 容器 |
ORA-28040(老客户端连 21c) |
协议版本被拒 |
sqlnet.ora 加 SQLNET.ALLOWED_LOGON_VERSION_CLIENT/SERVER=8 |
B. 网络(VM)
| 现象 |
原因 |
解决 |
ORA-12543 destination host unreachable |
双网卡 ens33/ens36 同网段,ens36 抢路由但 ARP 不通 |
禁用 ens36,并设 autoconnect no 防重启复发 |
| VM 无外网、yum 不可用 |
同上双网卡问题 |
经共享目录传 rpm |
C. Oracle 客户端
| 现象 |
原因 |
解决 |
libnsl.so.1 缺失 |
11.2 客户端在 Kylin10 的典型缺库 |
装 libnsl rpm(rpm -ivh --nodeps) |
| 传输的 zip 被截断(1.04MB vs 5.7MB) |
拖拽传输不可靠 |
共享目录解压 + 按字节数核验完整性 |
| 环境变量配了却找不到库 |
23.x 是扁平目录(无 bin/lib) |
环境变量去掉 /bin、/lib 后缀 |
sqlplus 中文显示 ??? |
仅 NLS_LANG 显示问题 |
不影响功能,可忽略 |
D. 环境运维
| 现象 |
原因 |
解决 |
| VMware 剪贴板失效 |
服务名不是 vmware-tools |
systemctl start vmtoolsd |
/mnt/hgfs 共享目录重启后未挂载 |
共享未启用 |
重新启用共享 / 重启 vmtoolsd |
| Windows 重启后 Oracle 没起来 |
服务未自启 |
net start OracleServiceXE |