资讯动态

SNMP、SNMP-traps与syslog:异构Linux监控日志服务器搭建

发布时间:2026/9/17 10:16:45 来源:尧图企业网站定制
1. 需求拆解轮询、主动告警、日志这三件事各管什么上个月帮一家做设备集成的朋友收拾他们机房里的监控烂摊子八台跑深度社区版的边缘盒子加六台欧拉系统的业务机之前一直是出了事再登进去看的裸奔状态。他们找我提的需求很朴素想在机房里放一台日志服务器把这十几台机器的运行状态和日志都汇到一起能提前发现硬盘写满、服务挂掉、温度异常这些问题。这就是典型的 SNMP 加 SNMP-traps 加 syslog 三件套要解决的问题。很多人第一次听到 SNMP会以为它就是个查看系统信息的工具实际上它解决的是统一采集入口的问题。不同品牌、不同发行版、不同架构的设备只要支持 SNMP就能用同一套协议、同一套 OID 树把它们的状态读出来。这在异构环境里价值极大你不需要为深度社区版写一套采集脚本再为欧拉写另一套。而 syslog 解决的是另一个维度的问题——事件的时间线。SNMP 轮询拿到的是某一时刻的切片五秒一次或者一分钟一次中间发生什么它不知道。日志记录的是连续发生的每一条事件谁在什么时候登录、哪个服务重启了、内核报了什么错这些只能从日志里翻。SNMP-traps 则补上了主动告警这一环设备发现异常不用等监控端来问自己就把告警推过来。三者配合才算把一台机器的可观测性做完整。1.1 三种手段的定位差异与互补关系我用一个实际场景说明这三者的分工。假设欧拉系统上跑的业务进程因为内存泄漏被 OOM Killer 干掉了轮询式 SNMP 只能在下一轮采集时发现进程数变了可能是几十秒之后syslog 会实时记下内核抛出的 OOM 记录而如果业务程序自己集成了 trap 发送能力它甚至可以在内存逼近阈值时就主动报警。所以我在部署时会这样分配性能指标和存量状态走轮询进程崩溃、磁盘满这类临界事件走 trap审计和排障走 syslog。提示不要指望一种手段包打天下。我见过有人只配了 SNMP 轮询结果机器宕机到监控发现之间隔了整整一轮采集周期关键业务的告警延迟就是这么来的。1.2 深度社区版和欧拉的差异决定配置路径这两个系统虽然都是 Linux但底层包管理完全不同。深度社区版是 Debian 系用aptSNMP 相关的包叫snmpd、snmp欧拉是 RPM 系用dnf包名是net-snmp、net-snmp-utils。配置文件路径虽然都是/etc/snmp/snmpd.conf但守护进程的启动参数管理方式不一样——Debian 系习惯把参数写在/etc/default/snmpd里RPM 系用 systemd 的 unit 加/etc/sysconfig/snmpd。这个差异如果不搞清楚就会出现配置改了但没生效的经典问题。另外一个高频坑是默认监听地址。深度社区版的 snmpd 装完默认只监听127.0.0.1外部根本连不上很多人以为服务没起来其实是/etc/default/snmpd里那行SNMPDOPTS把监听地址锁死了。欧拉相对规矩但还是建议显式在配置文件里写死agentaddress别依赖默认值。1.3 为什么选 net-snmp 而不是自研采集市面上监控方案很多为什么我还要坚持用 net-snmp 做底座因为它是事实标准。绝大多数交换机、UPS、NAS、打印机出厂就带 SNMP agent我这边只要有一台接收端就能全部纳管。像机房里的 UPS 电源通过 SNMP 就能读到电池电量、输入电压这些关键量用自研脚本去对接厂商私有接口的维护成本高得多。net-snmp 的extend机制还能把任意 shell 脚本的输出挂成自定义 OID等于给了你无限扩展空间。2. 动手之前先把这几件事捋清楚装软件本身十分钟就完事真正耗时间的是准备工作没做足导致后面反复返工。我现在的习惯是先花二十分钟把环境信息、端口、依赖、时间同步这几件事列成一张表确认无误再动手能省掉后面一大半的排查时间。2.1 系统版本识别与软件源确认第一步永远是确认你到底在什么系统上。命令看起来简单但很多欧拉其实装的是某些下游商业版本包名和源都不一样cat /etc/os-release uname -r深度社区版会显示类似Deepin 20.x / 23.x的信息欧拉会显示openEuler 20.03 LTS或22.03 LTS。确认版本之后重点看软件源能不能用。欧拉如果是内网离线环境需要挂载 ISO 做本地源mkdir -p /mnt/iso mount -o loop /opt/openEuler-22.03-LTS-x86_64-dvd.iso /mnt/iso cat /etc/yum.repos.d/local.repo EOF [local] namelocal baseurlfile:///mnt/iso enabled1 gpgcheck0 EOF dnf clean all dnf makecache深度社区版则要先确认/etc/apt/sources.list里的镜像可达apt update不报错再往下走。这一步我踩过坑有次源里缺snmp-mibs-downloader装到一半失败后来单独找离线 deb 包才补上。2.2 依赖清单与端口规划在动手前把要用的端口和依赖理一遍这是我多年养成的习惯。SNMP 相关就三个端口161/udp给 agent 接收查询162/udp给 trap 接收端514/udp和514/tcp给 syslog。深度的 ufw 和欧拉的 firewalld 开放方式不同先记下来。用途端口/协议方向说明SNMP 轮询161/udp监控端到被监控端agent 监听SNMP-trap162/udp被监控端到监控端trap 接收端监听syslog 传输514/udp 或 514/tcp被监控端到日志服务器UDP 快但可能丢TCP 可靠依赖方面欧拉需要net-snmp、net-snmp-utils、net-snmp-libs深度需要snmpd、snmp、snmp-mibs-downloader。snmp-mibs-downloader是为了让snmpwalk能显示 OID 的名字而不是一串数字排障时能省很多脑力。2.3 时间同步和主机名这些容易被忽视的前置项这条看着不起眼但我吃过亏。日志服务器按主机名分目录存日志如果两台机器主机名重复日志就混在一起了。所以部署前一定确认每台机器主机名唯一并且所有机器的时间都和同一台 NTP 源同步。否则你在日志服务器上看到的时间戳是乱的根本对不上故障时间线。hostnamectl set-hostname node-euler-01 timedatectl set-ntp true timedatectl status时间同步我强烈建议用内网 NTP别依赖公网。有次客户内网没做 NTP各机器时间差了十几分钟排查一次磁盘告警时我对着日志怎么都对不上最后才发现是时钟漂移。3. SNMP 服务端安装与 snmpd.conf 逐项配置准备工作做完正式进入安装环节。这一章我会把两个系统的命令对照着写方便你直接抄。配置文件的每一项我都会解释为什么这么写而不是让你照着粘。3.1 两个系统的安装命令对照欧拉上dnf install -y net-snmp net-snmp-utils net-snmp-libs深度社区版上apt update apt install -y snmpd snmp snmp-mibs-downloader装完之后先别急着改配置确认一下二进制都在which snmpd snmpwalk snmpget snmptrap这里要特别注意深度社区版装完后snmpd默认是被systemd或init拉起来的可能已经在跑了。欧拉如果是最小化安装通常需要手动systemctl enable --now snmpd。我一般先systemctl status snmpd看一眼再决定后面怎么操作。3.2 snmpd.conf 最小可用配置/etc/snmp/snmpd.conf内容很多删掉默认的一堆注释后留下这几行就够跑起来agentaddress udp:161 rocommunity MyReadOnlyKey 192.168.10.0/24 syslocation Rack A-03 syscontact opsexample.com sysservices 72 view allview included .1 access MyGroup any noauth exact allview none none逐条说下意图。agentaddress udp:161显式声明监听所有网卡的 161 端口避免深度社区版默认只监听回环的问题。rocommunity是 v2c 的只读团体名后面跟一个网段做访问控制比裸写public安全得多。syslocation和syscontact会被监控端读走显示在告警里顺手填上省得以后翻机器。view加access这两行是把整个 OID 树都暴露给只读组默认配置里往往只开放了systemview很多指标读不到就是因为这个。注意rocommunity后面接的网段一定要写对。我见过写成192.168.10.0/24却写成192.168.1.0/24的情况结果监控端怎么都连不上查了半小时。3.3 加固从 v2c 平滑迁到 v3v2c 的团体名是明文传输的内网临时用没问题但如果是合规要求高的场景建议上 v3。net-snmp 提供了专门的工具来创建 v3 用户不用手写那一堆参数systemctl stop snmpd net-snmp-create-v3-user -ro \ -A AuthPassw0rd! -a SHA \ -X PrivPassw0rd! -x AES \ monitor systemctl start snmpd这条命令会在/etc/snmp/snmpd.conf里追加rouser monitor authpriv同时在/var/lib/net-snmp/snmpd.conf里写入加密后的密钥。验证时用snmpwalk -v3 -u monitor -l authPriv \ -a SHA -A AuthPassw0rd! \ -x AES -X PrivPassw0rd! \ localhost .1.3.6.1.2.1.1安全等级authPriv表示既认证又加密这是 v3 里最严的档位。迁的时候有个经验先让 v2c 和 v3 并存跑一周确认监控端两边都能读、数据一致再关掉 v2c。直接一刀切的风险是你可能漏掉某台还在用老团体名采集的设备。3.4 用 extend 把自定义指标挂上去这是 net-snmp 最好用的功能。比如我想监控磁盘使用率写个脚本/opt/snmp/check_disk.sh#!/bin/bash df -h / | awk NR2 {gsub(/%/,,$5); print $5}然后在snmpd.conf里加一行extend rootdisk /bin/bash /opt/snmp/check_disk.sh重启后查询snmpwalk -v2c -c MyReadOnlyKey localhost NET-SNMP-EXTEND-MIB::nsExtendOutputFull你会看到输出行里出现脚本的结果。extend生成的 OID 是字符串编码的rootdisk 会被转成一串 ASCII 十进制数字作为 OID 后缀。监控端拿到这个值就能直接设阈值告警。实操心得脚本一定要返回单行、无多余空格的输出并且设置合理的超时。如果脚本卡住snmpd的这次查询会整个超时连带其他正常指标一起拿不到。我一般会在脚本里加timeout 3。3.5 开机自启与配置验证欧拉上systemctl enable --now snmpd firewall-cmd --permanent --add-port161/udp firewall-cmd --reload深度社区版如果用 ufwufw allow 161/udp systemctl enable --now snmpd验证顺序建议这样走先本地snmpwalk localhost再同网段另一台机器上远程snmpwalk最后看监控平台能不能取到数。三层都通了才算配置完成。本地通、远程不通十有八九是防火墙或者agentaddress的问题。4. SNMP-traps让故障主动找上门轮询是监控端主动去问trap 是被监控设备主动汇报。这两种模式配合起来才完整。我在实际部署里凡是涉及事件的告警都走 trap比如服务崩溃、磁盘写满、温度超限。4.1 trap 与轮询的成本对比轮询的代价是频率和实时性的矛盾。你把频率调到 10 秒一次几百台设备的查询流量和管理端 CPU 都会吃不消调低到 5 分钟一次故障发现就慢。trap 的好处是设备一发现异常立刻推几乎没有延迟而且平时不占带宽。但 trap 有个天然短板——UDP 无连接丢了就丢了接收端没收到不会重传。所以我的策略是关键事件用 trap 做即时告警同时保留低频轮询做兜底对账两者数据对不上就说明有 trap 丢了。4.2 snmptrapd 接收端配置接收端一般是那台日志服务器。装的包和 agent 一样但配置的是/etc/snmp/snmptrapd.confdisableAuthorization yes authCommunity log,execute,net MyTrapKey traphandle default /usr/local/bin/trap_handler.shdisableAuthorization yes在 net-snmp 5.7 之后的版本里是必须的否则接收端会拒收未认证的 trap。authCommunity里log,execute,net分别表示记录、执行处理脚本、允许转发。traphandle指定收到 trap 后调用的脚本脚本的 stdin 会收到完整的 trap 内容。启动并用 162 端口监听systemctl enable --now snmptrapd firewall-cmd --permanent --add-port162/udp firewall-cmd --reload ss -lunp | grep 1624.3 用脚本和外部设备触发 trap最简单的手工测试snmptrap -v2c -c MyTrapKey 192.168.10.50:162 \ 1.3.6.1.4.1.8072.9999 \ 1.3.6.1.4.1.8072.9999.1 s disk_usage_above_90这个命令往接收端发一条自定义 trap.1.3.6.1.4.1.8072.9999是自定义企业 OID后面跟的是告警文本。真正落地时我会把它嵌进脚本比如磁盘检查脚本在超过阈值时除了返回数值还额外发一条 trap。像 STM32 这类带网口的嵌入式设备很多方案是跑一个轻量 SNMP 库用 v2c 直接组包发送 trap企业 OID 用自己申请的私有号段。UPS 更简单厂商通常已经内置了 SNMP 卡你只要在接收端配上对应的团体名把它的告警 OID 映射成自己的告警规则即可。NAS 设备也类似出厂基本都支持 trap。注意自定义 OID 千万别随手用.1.3.6.1.4.1.8072之外的公共号段8072 是 net-snmp 自己保留的测试段正式环境最好申请自己的企业号或者统一用一个内部约定号段并做好文档。4.4 trap 收不到的几种典型原因最常见的是团体名不匹配。发送端用的团体名和接收端authCommunity里写的必须一模一样大小写敏感。第二常见的是防火墙没放 162。第三是disableAuthorization没设接收端默默丢弃了。第四是发送端把 trap 发到了161端口而不是162这个错误很隐蔽因为命令执行不会报错只是接收端什么都收不到。排查思路很简单接收端先tcpdump -i any udp port 162 -nn抓包确认包到没到。包到了但没处理就是配置问题包没到就是发送端或网络问题。这一招比对着配置文件瞎猜快得多。5. syslog 采集把散落的日志收口日志是排障的最后一根救命稻草。机器多了以后每台挨个登进去看日志是不现实的必须集中采集。这一步我通常和 SNMP 一起部署共用一个接收端。5.1 rsyslog 远程转发配置主流发行版都自带 rsyslog。发送端在/etc/rsyslog.d/下新建一个配置文件*.info;mail.none;authpriv.none;cron.none action(typeomfwd target192.168.10.50 port514 protocoltcp)这里用 TCP 而不是 UDP原因是 TCP 有确认机制不会丢日志。代价是稍微多一点开销但对日志完整性要求高的场景值得。如果只是收普通系统日志UDP 也能接受把protocol改成udp即可。协议选项之外*.info表示 info 级别及以上都转发mail.none这类是排除指定 facility避免日志量爆炸。改完重启systemctl restart rsyslog logger test from node-euler-01logger命令能手动造一条日志方便快速验证链路通不通。5.2 接收端按主机分目录落盘接收端要开监听并配置落盘模板。在/etc/rsyslog.d/下module(loadimtcp) input(typeimtcp port514) template(nameDynFile typestring string/data/syslog/%HOSTNAME%/%$YEAR%-%$MONTH%-%$DAY%.log) *.* action(typeomfile dynaFileDynFile)DynFile模板让每台机器的日志按主机名分目录、按日期分文件找起来非常方便。接收端要放开 514 端口并确认/data分区有足够空间。firewall-cmd --permanent --add-port514/tcp firewall-cmd --reload mkdir -p /data/syslog systemctl restart rsyslog实操心得/data/syslog所在分区一定要独立或者设好日志轮转。我有次没配轮转一个月下来日志把根分区写满了反而把机器搞挂了非常讽刺。5.3 日志和 SNMP 告警怎么联动日志本身不会主动报警得再加一层过滤。我用得最多的做法是在接收端用 rsyslog 的过滤规则把包含关键字比如OOM、segfault、disk full的日志单独存一份高优先级文件再写个脚本监听这个文件命中就发一条 trap 或者直接邮件告警。这样 syslog 和 SNMP-traps 就串起来了形成从日志到告警的闭环。6. 常见问题排查速查表下面这张表是我这几年攒下来的遇到问题先查它能解决八成情况。现象大概率原因排查与解决本地能walk远程连不上agentaddress 只监听回环检查/etc/default/snmpd或配置文件改成udp:161snmpwalk 报 Timeout防火墙没放 161/udpfirewall-cmd --add-port161/udp或 ufw 放行部分 OID 读不到view 没包含对应子树检查view和access两行trap 发了但收不到团体名不匹配或端口错接收端抓包tcpdump udp port 162snmptrapd 不处理 trap缺disableAuthorization yes补上并重启日志服务器没收到日志514 端口未放行或模板路径不可写检查防火墙和目录权限extend 脚本无输出脚本超时或权限不足手动执行脚本加timeout和绝对路径v3 认证失败加密算法或密码不对用net-snmp-create-v3-user重新生成6.1 selinux 与权限相关的隐藏坑欧拉默认可能开着 SELinuxsnmpd想执行自定义脚本或者连网络会被策略拦住而且日志只写在 audit 里不容易发现。快速验证的办法是临时setenforce 0看问题是否消失确认是策略问题后再用setsebool -P snmpd_can_network_connect on之类的方式精准放行别长期关掉 SELinux。深度社区版通常不启用 SELinux这块省心些但要留意 AppArmor。6.2 版本差异导致配置文件位置不同同一个问题在深度和欧拉上表现可能不一样根子在配置文件位置。深度用/etc/default/snmpd传启动参数欧拉用/etc/sysconfig/snmpd深度装的是snmp-mibs-downloader欧拉可能把 MIB 放在/usr/share/snmp/mibs。排查前先rpm -ql net-snmp或dpkg -L snmpd看文件清单比猜快。7. 我踩过的几个坑和收尾经验最后聊几个具体踩过的坑。第一个是团体名的大小写。有次接收端写的是MyTrapKey发送端脚本里写成mytrapkey包发出去毫无报错接收端安安静静。我抓包确认包到了才回头逐字符比对发现就差了大小写。这种问题最消耗耐心所以我现在习惯全用小写字母加下划线避免视觉混淆。第二个是extend脚本的返回。有次脚本里加了echo调试信息结果多输出了一行OID 解析出来就是两个值监控端取值取到了调试那行阈值判断全乱。从那以后我要求所有 extend 脚本要么静默要么只输出一行最终值调试信息一律走 stderr。第三个是日志轮转。集中式日志服务器最容易死在磁盘满上我现在的标准做法是给日志目录单独分一个分区配上logrotate保留 30 天并且加一条监控磁盘使用率超过 80% 就发 trap。这条自监控的 trap 救过我两次。如果你也想把这套东西铺开我的建议是先在一台机器上把轮询、trap、syslog 三条链路都跑通每种都用一个手工命令验证过再写批量部署脚本复制到其余机器。手工验证那一遍看起来慢但能保证你后面批量部署时心里有底。批量脚本里记得处理主机名和团体名的变量替换别硬编码。这套东西一旦跑顺运维的工作量能实打实地降一个台阶。

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

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

免费获取报价