资讯动态

Zabbix监控Oracle实战:基于orabbix实现JDBC直连与自动发现

发布时间:2026/10/20 8:20:45 来源:尧图企业网站定制
开头做了部分省略后补充以下是完整文章在监控体系搭建这件事上Oracle数据库的接入一直是让我比较头疼的一环。Zabbix本身很强但面对Oracle这种商业数据库它默认提供的监控手段并不算友好要么靠ODBC直连写SQL要么靠外部脚本采集后主动上报。折腾过几条路之后我最终选了orabbix 1.2.3这套方案——它用JDBC直连数据库再把采集结果通过Zabbix的trapper通道送进去整个链路清晰部署成本可控而且对Zabbix版本没有太多挑剔。这篇文章就是把我这次完整搭建的过程、配置思路和踩过的坑都记录下来给正准备做同类监控的朋友一个可以直接参考的落地版本。1. 为什么我在众多方案里选了orabbix先交代一下背景。我这边环境里有一套比较核心的业务系统跑在Oracle上版本是11g和19c混着来DBA团队平时要看的指标包括会话数、表空间使用率、等待事件、归档日志增长这些。Zabbix层面的监控架构是现成的主机已经通过agent纳管但我需要一种方式把Oracle的深度指标拉进来又不希望改动应用端和数据库端太多。1.1 裸监控的痛Zabbix自带的Oracle监控基本不好用Zabbix官方从4.0开始就带了一套Oracle by ODBC模板原理是用unixODBC加上Oracle的ODBC驱动直接通过SQL查询数据库动态性能视图。听起来不难但实际用起来有几个让我非常难受的点。首先是ODBC环境配置繁琐。你得在Zabbix server端装unixODBC、Oracle Instant Client、配置odbc.ini、确认libnnz等库的路径任何一步对不上监控项就疯狂报“cannot connect to ODBC DSN”。更麻烦的是ODBC模板里每条监控项默认的刷新间隔是60秒或者更短如果你主机比较多Zabbix server会频繁发起数据库连接Oracle侧的审计日志会被刷得飞起DBA看到一堆陌生连接心里肯定不舒服。其次是SQL模板的覆盖范围太固定。官方ODBC模板对表空间、会话这些基础指标还行但遇到我们实际关心的归档日志删除策略、RMAN备份状态、特定等待事件趋势模板里并没有现成的监控项你只能自己去写SQL。写SQL本身不是问题问题在于Zabbix ODBC模板的每个监控项都要单独配一条查询语句、一个刷新策略维护成本直接翻倍。1.2 orabbix解决的三个核心问题orabbix给我的第一感受是“它真的懂Oracle”。它本身是一个Java编写的代理程序部署在可以和Oracle数据库网络互通的机器上用JDBC驱动连进去通过配置文件预先定义好一组查询语句周期性地轮询Oracle视图然后把结果推给Zabbix server。这个架构天然解决了三个问题第一不需要在Zabbix server本地配置任何数据库驱动。Zabbix server和orabbix分开数据库连接的压力全部落在orabbix代理上。我再也不用来回折腾ODBC的依赖代理挂了也不会影响Zabbix本身。第二orabbix自带了很多成熟监控项。表空间使用率、会话数、物理读/逻辑读、硬解析/软解析比例、Buffer Cache命中率、共享池命中率、归档日志生成量、甚至RMAN备份状态都有现成的查询逻辑。导入它的模板后你能在Zabbix前端直接看到几十个监控项而不是自己从头写。第三orabbix支持自动发现。它通过LLD机制发现数据库里有哪些表空间然后动态生成监控项新增表空间后不需要手工加监控这个对业务频繁变化的库来说非常实用。1.3 它和ODBC直连方案的差异我接触过一些团队是直接用ODBC方案强行上线的结果在数据库扩容或者跨机房场景下Zabbix server连远程数据库的延迟和稳定性出了不少问题。ODBC方案的特点是“Zabbix直接连库”适合数据库数量少、网络环境简单的情况而orabbix是“代理连库后再推给Zabbix”相当于在数据库和Zabbix之间加了一层缓冲。这层的意义在于orabbix可以对数据库连接做复用一个代理进程维护少量的JDBC连接池而不是每个监控项都新建会话。同时orabbix的轮询方式是通过trapper端口主动上报Zabbix server只需要被动接收数据对server端几乎没有性能压力。从可靠性的角度讲orabbix是可替代的独立进程重启、调整配置都不会影响Zabbix本体运维心态上要稳很多。2. orabbix 1.2.3的运行架构它其实是个“翻译官”用orabbix之前我建议你先理解它的数据流不然出了问题你会不知道往哪儿查。它的角色相当于一个翻译官Oracle只听得懂SQLZabbix只认识监控项和值orabbix把Zabbix要的指标翻译成SQL再到Oracle里查最后把结果翻译回Zabbix的监控项值。2.1 JDBC直连Oracle数据走Zabbix trapper通道orabbix的底层连接方式是JDBC。它启动后会读config.props配置文件里面定义了要监控哪些数据库实例、连接字符串是什么、Zabbix服务器的地址是哪里。对每个数据库实例orabbix会按照配置的轮询周期定时执行一组查询。这些查询结果被分装成一个一个的监控键值对然后通过Zabbix的trapper协议推送到Zabbix server的10051端口。注意这里不是Zabbix agent主动拉取而是orabbix以“主动上报”的方式把数据送到server端所以Zabbix server不需要通过agent去反向连orabbix。这对网络策略比较友好的环境来说是个优势——你只需要让orabbix所在机器能访问Zabbix server的10051端口就行不用开放额外的入方向端口。2.2 一次完整的数据采集链路我举个例子假设orabbix要监控某个Oracle实例的当前会话数。整个链路是这样的orabbix根据config.props里配置的连接串通过JDBC DriverManager创建一个到Oracle实例的连接执行类似select count(*) from v$session的查询语句拿到结果后orabbix内部缓存该值并为这个指标生成一个和Zabbix模板里完全一致的key比如oracle.session_count[{#ORACLE_NAME}]orabbix通过socket连接Zabbix server的10051端口按照trapper协议发送这个监控键和值Zabbix server后续对该key执行trapper类型的item更新存进数据库。这套设计里最值得留意的细节是key的命名。orabbix推送的每一个值都对应模板里定义好的item key如果你的模板没有正确导入或者item key变了数据就会显示“Not supported”或没有数据。所以模板导入这一步并不是随便点一下就完事它决定了item key和orabbix上报的key能不能对上。3. 部署前的准备工作JDK、ojdbc和Oracle监控账号很多人在orabbix上翻车不是程序本身问题而是部署前的前置条件没准备好。orabbix本身是一个Java程序对运行环境有明确要求逐个说清楚。3.1 JDK与驱动的版本匹配orabbix 1.2.3这个版本推出的年代比较早构建时用的JDK版本不高但我实测在JDK 8上运行非常稳定建议直接装JDK 8不要想着用JDK 11或17挑战兼容性。某些高版本JDK移除了老加密算法或者模块化之后缺少Java EE相关组件运行orabbix可能直接报ClassNotFound完全没必要在这个环节浪费时间。Oracle JDBC驱动方面我用的是ojdbc8.jar一般从Oracle官方JDBC下载页面或者数据库安装目录的jdbc/lib下能找到。注意要选择和你数据库版本兼容的驱动如果你的Oracle实例是11gojdbc8也能连如果是Oracle 19c建议用ojdbc8对应版本。还要提醒一句驱动版本不一致时报错信息往往不是“版本不支持”而是诡异的空指针、“ORA-01017 invalid username/password”或者连接超时。排查半天才发现是驱动和数据库版本不匹配这是最常见的第一坑。3.2 在Oracle端创建最小化权限监控账号orabbix为了拿到数据库指标需要登录Oracle查询动态性能视图。建议不要用sys或system这种超级账号而是单独建一个监控账号只授必要权限。我一般是这样做的CREATE USER ORA_MONITOR IDENTIFIED BY 你的强密码; GRANT CONNECT, SELECT_CATALOG_ROLE TO ORA_MONITOR; GRANT SELECT ON sys.v_$instance TO ORA_MONITOR; GRANT SELECT ON sys.v_$database TO ORA_MONITOR; GRANT SELECT ON sys.v_$tablespace TO ORA_MONITOR; GRANT SELECT ON sys.v_$datafile TO ORA_MONITOR; GRANT SELECT ON sys.v_$tempfile TO ORA_MONITOR; GRANT SELECT ON sys.v_$session TO ORA_MONITOR; GRANT SELECT ON sys.v_$process TO ORA_MONITOR; GRANT SELECT ON sys.v_$sysstat TO ORA_MONITOR; GRANT SELECT ON sys.v_$statname TO ORA_MONITOR; GRANT SELECT ON sys.v_$log TO ORA_MONITOR; GRANT SELECT ON sys.v_$archived_log TO ORA_MONITOR; GRANT SELECT ON sys.v_$pgastat TO ORA_MONITOR; GRANT SELECT ON sys.v_$parameter TO ORA_MONITOR; GRANT SELECT ON sys.dba_data_files TO ORA_MONITOR; GRANT SELECT ON sys.dba_free_space TO ORA_MONITOR; GRANT SELECT ON sys.dba_temp_files TO ORA_MONITOR;这段SQL我根据orabbix默认查询列表整理出来的基本覆盖了它需要的所有视图。授权之后一定要先手动验证一下登录是否正常sqlplus ORA_MONITOR/密码//10.0.0.10:1521/ORCLPDB能正常登录并执行select count(*) from v$session;再往下走。这一步花不了两分钟但能提前排除掉80%左右的登录故障。3.3 一个容易忽略的网络检查orabbix所在主机需要能访问Oracle的1521端口同时还要能访问Zabbix server的10051端口。很多人在配置后看不到数据第一反应是orabbix问题最后才发现是从orabbix主机到Zabbix server的10051端口被防火墙拦了。我习惯在部署前先用命令验证一下# 测试到Oracle的连通性 telnet 10.0.0.10 1521 # 测试到Zabbix server的10051端口 telnet 10.0.1.20 10051注意如果Zabbix server的10051端口对外限制得很严你需要确认orabbix所在机器的IP是否在白名单里。另外orabbix和Zabbix server之间的通信可能还会被某些中间设备干扰如果发现trapper收到数据但前端一直没更新抓包看10051端口是最直接的排查方式。4. 安装配置全记录从解压到模板导入前置条件就绪后就可以开始安装了。我用的环境是一台CentOS 7.6服务器orabbix就部署在和Zabbix server分开的独立机器上也可以和Zabbix server同机部署但独立机器更稳。4.1 文件布局与启动方式orabbix 1.2.3发布包通常是一个zip压缩包解压后目录结构大致如下orabbix/ ├── conf/ │ └── config.props ├── lib/ │ ├── ojdbc8.jar │ └── log4j-1.2.16.jar ├── log/ ├── orabbix.sh └── orabbix-1.2.3.jar把对应版本的ojdbc8.jar复制进lib目录后最核心的就是修改conf/config.props。修改前先备份原文件这是经验免得改出问题连保底的配置都没了。4.2 config.props逐段配置说明config.props是orabbix的唯一配置文件里面标注很清楚我先给出一份精简后的实际配置# Zabbix Server列表多个用逗号分隔 ZabbixServerListZabbixServer1 ZabbixServer1.Address10.0.1.20 ZabbixServer1.Port10051 # orabbix代理自身标识 OrabbixDaemon.Address10.0.1.30 OrabbixDaemon.Port10052 # 日志级别 OrabbixDaemon.LogLevelinfo # 轮询周期秒 OrabbixDaemon.PollInterval60 # 实例发现开关 InstanceDiscoverytrue # Oracle JDBC连接池大小 OrabbixDaemon.MaxActive10 # 数据库实例列表 DatabaseListORCL,ORCLPDB # 每个实例的连接配置 ORCL.Address10.0.0.10 ORCL.Port1521 ORCL.UserORA_MONITOR ORCL.Password你的强密码 ORCL.ServiceNameORCL ORCL.MaxActive5 ORCL.MaxWait1000 ORCL.MaxIdle1 ORCLPDB.Address10.0.0.10 ORCLPDB.Port1521 ORCLPDB.UserORA_MONITOR ORCLPDB.Password你的强密码 ORCLPDB.ServiceNameORCLPDB ORCLPDB.MaxActive5 ORCLPDB.MaxWait1000 ORCLPDB.MaxIdle1几个关键参数重点说明ZabbixServerList和ZabbixServer1.Address是orabbix上报数据的去向。如果Zabbix server和agent用的都是同一个IP这里就填server地址端口固定10051。OrabbixDaemon.Address填本机IPPort随便指定一个未占用的端口实际上这更多是身份标识。OrabbixDaemon.PollInterval60表示每60秒轮询一次数据库。不要设置得太短30秒以上已经能满足绝大多数监控场景太短反而给数据库增加负担。DatabaseList是orabbix要监控的Oracle实例列表多个实例用逗号分隔。实例可以指向同一个Oracle也可以指向多个不同的Oracle。每个实例的ServiceName要填写Oracle监听的service name不是SID很多人这里填错导致连不上。4.3 Zabbix前端导入模板并关联主机orabbix发布包中会自带一个模板文件常见名称是Oracle_zbx_templates.xml。这个模板需要在Zabbix前端导入。导入路径配置 → 模板 → 导入选择文件后导入。导入后你会看到一个名为Template_Oracle的模板里面包含几十个监控项还有若干LLD规则用来发现表空间。接下来到配置 → 主机找到你之前创建好的Oracle主机关联了Zabbix agent的那种在模板栏里添加Template_Oracle。注意orabbix监控并不依赖agent去采集Oracle数据但主机上还是要先有agent在运行Zabbix才会认为这个主机是“已监控”状态。模板关联后你会在主机的监控项列表里看到大量以oracle.开头的key。这些key的数据来源就是orabbix通过trapper上报的。比如oracle.buffer_cache_hit_ratiooracle.session_countoracle.tablespace.usedoracle.archive_log_generated看到这些key之后再把模板里的宏填一下。orabbix模板里通常会定义{$ORACLE_USER}、{$ORACLE_PASSWORD}这类宏你在导入后需要去主机宏或者模板宏里填入实际连接Oracle的账号密码。不同版本模板的宏名略有差异你导入后看一眼模板里的监控项宏引用就能确定。4.4 启动验证看进程、看日志、看最新数据启动orabbix很简单执行sh orabbix.sh start启动后确认进程存在ps -ef | grep orabbixorabbix的日志在log目录下默认生成orabbix.log和orabbix_error.log。启动成功的情况下日志中应该能看到connected to database ORCL之类的信息如果报连接失败优先排查账号密码和ojdbc驱动问题。数据是否成功进入Zabbix可以这样看登录Zabbix前端进入该主机的最新数据页面筛选oracle.的监控项。如果能看到数据并且最近时间为当前时间说明整条链路已经通了。如果最新数据时间一直停在导入模板前的状态按下面章节的排查思路逐步查。5. 高频排错链路这些坑我基本都踩过orabbix部署起来不难但在真实环境里总有一些问题不是“装好就能跑”的。我整理了几个实际场景中最高频的坑每个都给出我自己的排查路径。5.1 ORA-01017/ORA-28001账号和密码策略的坑先说登录失败的两个经典报错。ORA-01017 invalid username/password通常不是密码真错了而是以下几种情况之一ojdbc驱动版本和数据库版本不兼容导致认证异常这种情况可以换一个更低版本的ojdbc驱动试试比如ojdbc6Oracle密码里带了特殊字符在config.props里没有正确转义或者被解析成配置分隔符数据库是CDBPDB架构你连接的用户和ServiceName不在同一个PDB里虽然端口和IP都对但认证就是失败。ORA-28001 the password has expired是Oracle密码过期策略导致。监控账号一般用得很频繁但也可能因为数据库密码策略严格而到期。处理方式是先过期重置并确认账号对应profile的过期时限ALTER PROFILE DEFAULT LIMIT PASSWORD_LIFE_TIME UNLIMITED; ALTER USER ORA_MONITOR IDENTIFIED BY 新密码 ACCOUNT UNLOCK;密码改完后同步修改config.props并重启orabbix。5.2 日志里反复出现连接池超时如果你发现日志里有大量类似pool-3-thread-1 ... wait timeout或者Cannot get connection的报错基本可以判断是JDBC连接池参数设得太小或者某条查询语句执行时间太长把连接占满了。我遇到过一次实际案例Oracle数据库负载很高时orabbix默认的监控SQL里有一条查询v$archived_log特别慢执行要十几秒。orabbix内部一个实例默认连接池上限只有5结果几条慢查询同时执行后面的查询全部排队超时。排查思路是先把日志级别调成debug找出具体是哪条SQL执行慢然后到Oracle端用工具分析。如果你的orabbix监控库很多、数据量大适当调大实例的MaxActive和MaxWaitORCL.MaxActive20 ORCL.MaxWait3000同时把OrabbixDaemon.PollInterval拉大到120秒或更长也能显著降低连接池压力。不要只想着一味增加连接数先搞清楚是查询慢还是连接不够再对症下药。5.3 LLD发现不出表空间orabbix的表空间自动发现是通过LLD规则实现的。正常情况下导入模板后等待一到两个发现周期和轮询周期有关配置 → 主机 → 监控项 → 自动发现的规则里应该能看到表空间列表。发现不出来的常见原因有两个第一模板里的宏没有正确填写。LLD规则的过滤条件和监控项SQL中会引用{$ORACLE_USER}、{$ORACLE_PASSWORD}如果宏为空发现查询执行失败Zabbix前端就会一直显示“Discovery”为空。第二数据库账号缺少对相关字典表的查询权限。表空间发现要查询dba_tablespace、dba_data_files这些字典表如果你只授了基础视图权限发现可能一半成功一半失败。检查一下有没有那几张dba_*表的权限GRANT SELECT ON sys.dba_tablespaces TO ORA_MONITOR; GRANT SELECT ON sys.dba_data_files TO ORA_MONITOR; GRANT SELECT ON sys.dba_temp_files TO ORA_MONITOR;补权限后不需要重启orabbix等下一个发现周期即可。5.4 中文乱码与本地字符集的关系这是比较冷门但很烦人的问题。orabbix采集的监控项里如果包含中文信息比如表空间名称、文件路径在Zabbix前端显示为乱码但数据本身是正常的。原因在于orabbix进程读取Oracle返回的中文字符时JVM默认字符集和Oracle客户端字符集、Zabbix前端字符集之间没对齐。解决思路是让orabbix启动时显式指定UTF-8编码。修改orabbix.sh在启动命令中加上JVM参数JAVA_OPTS-Dfile.encodingUTF-8 -Duser.languagezh -Duser.countryCN同时确保config.props本身保存为UTF-8格式不要用Windows记事本的ANSI编码保存否则配置文件里的中文注释和密码都可能变成乱码进而引发密码错误或路径错误。这个问题我曾经排查了一个下午最后发现只是编码问题教训深刻。5.5 采集间隔和IO压力怎么权衡orabbix的好处是连接复用但如果轮询间隔设置不当还是会增加数据库负担。尤其那些本身业务压力就很大的Oracle实例orabbix每30秒甚至更短周期轮询一次大量查询动态性能视图会对数据库产生新的开销。我的经验值是常规监控轮询周期60秒连接池MaxActive 5~10高负载/核心库轮询周期120秒连接池MaxActive 3~5报表型/准实时指标轮询周期30秒连接池MaxActive 10但只保留少量关键监控项。这个配置需要观察orabbix日志和Oracle的AWR报告看新增的监控会话是否占用了明显资源。如果AWR中出现orabbix连接相关的SQL消耗较高就把轮询周期再放大通常没有必要追求秒级数据。6. 监控数据拿到手之后从“能看到”到“能报警”orabbix把数据采集上来其实只完成了第一步。如果只是让监控项在页面上有个数字那和没做监控区别不大。真正有价值的是基于这些数据构建报警策略。6.1 关键监控项怎么挑orabbix模板里监控项很多但每个都设置报警是没有意义的不仅管理成本高还会因为误报让团队产生“报警疲劳”。我自己的习惯是聚焦几类可用性类实例是否存活、监听是否正常。对应orabbix的oracle.alive、oracle.instance_status阈值设为非正常状态就告警容量类表空间使用率、归档日志目录剩余空间。表空间使用率建议按90%/95%分两级告警高水位线再结合日常增长情况调整性能类Buffer Cache命中率、共享池命中率、会话数、活跃会话数。命中率不是越低越要告警要结合基线一般来说命中率低于90%持续10分钟以上值得关注异常类会话数突然飙高、归档日志短时间内大量生成。这类往往关联应用或老问题值得单独设置触发器。我在上线后的实际操作中通常先把这些指标的历史数据跑一周再按照历史均值加两倍标准差的方式设定动态阈值比拍脑袋写死90%要可靠得多。6.2 触发器设计的实际建议触发器表达式建议用“持续N次才告警”的方式。比如表空间使用率last(/Template_Oracle/tablespace.pct.used[{#TABLESPACE}]) 90单次就告警容易误报尤其是数据文件自动扩展的场景下使用率可能瞬时波动。更稳妥的是min(/Template_Oracle/tablespace.pct.used[{#TABLESPACE}],5m) 95表示5分钟窗口内的最小值都超过95%才触发既避免瞬时波动又能及时发现问题。会话数的告警则适合用“速率变化”的思路。比如一个库平时会话稳定在200左右某天突然涨到600这种变化往往比具体数值更值得关注。先用触发器计算窗口内平均会话数再和上一周期对比avg(/Template_Oracle/oracle.session_count,10m) - avg(/Template_Oracle/oracle.session_count,1h) 200这种相对变化类触发器我在实际使用中比绝对阈值更能提前暴露异常。6.3 给监控项加趋势留存和容量观察orabbix上报的数据默认会按照模板中定义的趋势存储策略存历史。我一般会把表空间使用率的历史保留周期设为90天归档日志生成量保留30天其他常规指标保留7天就够了。存储周期太长会增加Zabbix数据库磁盘消耗太短又没法做容量趋势分析。有了历史数据后可以通过Zabbix内置趋势图来看表空间增长斜率。比如某个表空间每周增长近10%按照剩余可用空间估算大约在一个月后会触达90%阈值这就是事前规划扩容的窗口。另外提一个很实用的做法把orabbix采集到的Oracle实例状态和业务系统的主机监控合并在同一个Dashboard上。Zabbix的聚合图形可以同时展示主机CPU、内存、磁盘和Oracle的会话数、等待事件、表空间使用率。当业务反馈变慢时先看聚合面板往往几分钟内能定位到是实例层面的问题还是主机资源问题排查效率提升非常明显。我自己在实际使用中还有一个习惯就是每隔几个月会去检查一次orabbix的版本和社区更新。orabbix 1.2.3本身已经很稳定功能上也没有太多必要追新但博主和社区还是会偶尔修正一些细节。把监控项、触发器和Dashboard整理成一套可复用的模板下次再有新的Oracle实例接入时配置一个新数据库列表、导入模板十分钟就能完成接入。这套方式支撑了我这边好几套Oracle环境的日常巡检比手工写SQL查询省下的时间可不是一点半点。

读完文章,也想定制专属网站?

尧图设计师 24 小时内与您沟通定制方案

免费获取报价 →
↑