Oracle RAC 环境中 Public IP 连接失败故障分析报告
Oracle RAC 环境中 Public IP 连接失败故障分析报告
一、故障现象
某业务系统用户反馈,在尝试通过数据库节点的 Public IP 地址连接 Oracle RAC 实例时,出现以下错误:
$ sqlplus app_user/******@10.0.0.100:1521/orcl_service
ERROR:
ORA-12541: TNS:no listener
但使用同一节点的 VIP(Virtual IP)地址连接正常:
$ sqlplus app_user/******@10.0.0.101:1521/orcl_service
-- ✅ 连接成功
该问题仅影响 节点2(主机名:dbnode02) 的 Public IP 连接,节点1 正常。
二、背景知识:Oracle RAC 中的网络类型
在 Oracle Real Application Clusters (RAC) 架构中,每个节点通常配置三种网络接口:
| 网络类型 | 示例 IP | 用途 | 是否推荐客户端连接 |
|---|---|---|---|
| Public IP | 10.0.0.100 |
用于 SSH 管理、应用直连(非最佳实践) | ❌ 不推荐 |
| VIP(Virtual IP) | 10.0.0.101 |
高可用浮动 IP,节点故障时自动漂移 | ✅ 推荐(若需指定实例) |
| Private IP | 192.168.10.100 |
节点间心跳、Cache Fusion 通信 | ❌ 禁止 |
📌 监听器行为说明:
Oracle Grid Infrastructure (GI) 会自动管理监听器(Listener),并将其绑定到 VIP 和 Public IP(前提是集群服务正常运行)。如果集群资源异常,监听器可能只注册 VIP,导致 Public IP 无法访问。
三、故障诊断过程
步骤 1:确认错误含义
$ oerr ora 12541
12541, 00000, "TNS:no listener"
// *Cause: The connection request could not be completed because the listener
// is not running.
// *Action: Ensure that the listener is running on the remote system.
结论:目标 IP:1521 上无监听进程响应。
步骤 2:登录故障节点,检查监听器状态
以 grid 用户身份登录 dbnode02:
$ su - grid
$ lsnrctl status
输出关键片段:
Listening Endpoints Summary...
(DESCRIPTION=(ADDRESS=(PROTOCOL=tcp)(HOST=10.0.0.101)(PORT=1521)))
❌ 缺失 Public IP (
10.0.0.100) 的监听地址!
步骤 3:确认操作系统网卡配置正常
$ ip addr show
输出示例:
2: eth0: <BROADCAST,MULTICAST,UP> ...
inet 10.0.0.100/24 brd 10.0.0.255 scope global eth0 # Public IP
inet 10.0.0.101/24 brd 10.0.0.255 scope global secondary eth0:1 # VIP
✅ 结论:Public IP 在操作系统层面已正确配置。
步骤 4:检查 Oracle Clusterware(CRS)整体状态
$ crsctl stat res -t
实际输出:
CRS-4535: Cannot communicate with Cluster Ready Services
CRS-4000: Command Status failed
⚠️ 严重异常:Cluster Ready Services (CRS) 主进程无法通信!
步骤 5:检查底层 CRS 初始化资源
绕过主服务,直接查询初始化资源状态:
$ crsctl stat res -t -init
关键输出:
--------------------------------------------------------------------------------
NAME TARGET STATE SERVER STATE_DETAILS
--------------------------------------------------------------------------------
Cluster Resources
--------------------------------------------------------------------------------
ora.crsd ONLINE OFFLINE dbnode02 Stopped
💡
ora.crsd是什么?
它是 Cluster Ready Services Daemon,负责管理所有上层资源(监听器、数据库实例、VIP、ASM 等)。
若它处于OFFLINE,则监听器虽在运行,但不会动态注册 Public IP,也无法响应集群配置变更。
步骤 6:定位 crsd.bin 启动失败原因
查看 CRS 日志:
$ cd $GRID_HOME/log/dbnode02/crsd/
$ tail -n 50 crsd.log | grep -i "error\|fail\|space"
发现关键错误:
CLSU-00101: Operating System error message: No space left on device
ORA-09925: Unable to create audit trail file
⚠️ 注意:
No space left on device不一定表示磁盘空间不足,更常见的是 inode 耗尽!
步骤 7:验证是否 inode 耗尽
$ df -h # 检查磁盘空间
$ df -i # 检查 inode 使用率
df -i 输出示例:
Filesystem Inodes IUsed IFree IUse% Mounted on
/dev/vg01/grid 1000000 999999 1 100% /u01/grid
✅ 确认:inode 使用率达 100%,导致无法创建新文件(包括审计日志、socket 文件等)。
步骤 8:查找占用 inode 的“罪魁祸首”
审计日志目录通常是重灾区:
# 查看审计目录文件数量
$ find /u01/grid/rdbms/audit -name "*.aud" | wc -l
987654
# 按大小排序(小文件多)
$ ls -l /u01/grid/rdbms/audit | head -5
-rw-r----- 1 grid oinstall 120 Jan 20 01:00 db_12345.aud
-rw-r----- 1 grid oinstall 118 Jan 20 01:01 db_12346.aud
...
💡 每个
.aud文件平均仅 100~200 字节,但数量巨大,迅速耗尽 inode。
四、故障恢复操作
1. 清理审计日志(释放 inode)
# 删除 7 天前的审计文件(谨慎操作!)
$ find /u01/grid/rdbms/audit -name "*.aud" -mtime +7 -delete
# 验证 inode 释放
$ df -i
# IUse% 应显著下降(如从 100% → 60%)
2. 手动启动 CRS 资源
# 启动 crsd(使用 -init 模式)
$ crsctl start res ora.crsd -init
# 验证状态
$ crsctl stat res ora.crsrd -init
# STATE 应为 ONLINE
3. 验证监听器是否恢复 Public IP 监听
$ lsnrctl status
预期输出:
Listening Endpoints Summary...
(DESCRIPTION=(ADDRESS=(PROTOCOL=tcp)(HOST=10.0.0.101)(PORT=1521))) # VIP
(DESCRIPTION=(ADDRESS=(PROTOCOL=tcp)(HOST=10.0.0.100)(PORT=1521))) # Public IP ✅
4. 测试连接
$ sqlplus app_user/******@10.0.0.100:1521/orcl_service
-- ✅ 应成功连接
五、根本原因分析
故障因果链如下:
审计日志未清理
→ 生成海量小文件(.aud)
→ 文件系统 inode 耗尽(IUse% = 100%)
→ crsd.bin 无法创建新文件(如审计轨迹、socket)
→ crsd.bin 进程崩溃并无法重启
→ 监听器失去集群管理,不再注册 Public IP
→ 客户端通过 Public IP 连接失败(ORA-12541)
🔑 根本原因:运维未配置审计日志自动清理策略,导致底层文件系统资源(inode)耗尽,引发集群管理服务中断。
六、优化与预防建议
1. 修改审计策略(推荐)
将审计日志写入数据库表,而非文件系统:
-- 登录数据库(sysdba)
SQL> ALTER SYSTEM SET audit_trail=DB SCOPE=SPFILE;
SQL> SHUTDOWN IMMEDIATE;
SQL> STARTUP;
优点:避免文件系统压力;可通过 SQL 查询审计记录;支持分区和归档。
2. 配置日志自动清理(若必须用文件)
创建 cron 任务定期清理:
# /etc/cron.daily/clean_audit.sh
#!/bin/bash
find /u01/grid/rdbms/audit -name "*.aud" -mtime +30 -delete
find /u01/app/oracle/admin/*/adump -name "*.aud" -mtime +30 -delete
3. 监控 inode 使用率
在监控系统(如 Zabbix、Prometheus)中增加指标:
# check_inodes.sh
THRESHOLD=85
INODE_USE=$(df -i | awk 'NR>1 { gsub(/%/,"",$5); if($6=="/u01") print $5 }')
if [ "$INODE_USE" -gt "$THRESHOLD" ]; then
echo "CRITICAL: Inode usage ${INODE_USE}% on /u01"
exit 1
fi
4. 客户端连接最佳实践
- 禁止直接使用 Public IP 连接 RAC。
- 推荐使用 SCAN IP(Single Client Access Name)实现负载均衡与故障转移。
- 若需连接特定实例,使用 VIP。
示例 tnsnames.ora:
ORCL_SERVICE =
(DESCRIPTION =
(ADDRESS = (PROTOCOL = TCP)(HOST = scan-cluster)(PORT = 1521))
(CONNECT_DATA =
(SERVER = DEDICATED)
(SERVICE_NAME = orcl_service)
)
)
5. 定期巡检 CRS 状态
加入日常运维脚本:
crsctl check cluster # 检查集群健康
crsctl stat res -t # 检查资源状态
df -i # 检查 inode
七、附录:常用诊断命令清单
| 目的 | 命令 |
|---|---|
| 查看 ORA 错误含义 | oerr ora 12541 |
| 检查监听器状态 | lsnrctl status |
| 查看网卡 IP | ip addr show 或 ifconfig -a |
| 检查 CRS 状态 | crsctl stat res -t |
| 检查底层 CRS 资源 | crsctl stat res -t -init |
| 检查磁盘空间 | df -h |
| 检查 inode 使用 | df -i |
| 查找大数量小文件 | find /path -type f | wc -l |
| 清理旧审计日志 | find /audit_path -name "*.aud" -mtime +7 -delete |
| 启动 crsd | crsctl start res ora.crsd -init |
- 感谢你赐予我前进的力量

