![snmptt 以非 root 身份运行,以 root 身份写入文件](https://linux22.com/image/116354/snmptt%20%E4%BB%A5%E9%9D%9E%20root%20%E8%BA%AB%E4%BB%BD%E8%BF%90%E8%A1%8C%EF%BC%8C%E4%BB%A5%20root%20%E8%BA%AB%E4%BB%BD%E5%86%99%E5%85%A5%E6%96%87%E4%BB%B6.png)
我snmptt
作为 的 SNMP 陷阱处理程序运行snmptrapd
,目的是写入可由 Zabbix 读取和处理的陷阱文件。
zabbix
我已通过更改脚本将 snmptt 设置为以用户身份运行init
。
# grep daemon /etc/init.d/snmptt
# description: SNMP Trap Translator daemon
# Short-Description: SNMP Trap Translator daemon
OPTIONS="--daemon"
daemon --user=zabbix /usr/sbin/snmptt $OPTIONS
snmpttt
正在按用户预期运行zabbix
,即运行 Zabbix 服务器的同一用户。
# ps -ef | grep snmp
root 3796 1 0 Jun19 ? 00:13:04 /usr/sbin/snmpd -LS0-6d -Lf /dev/null -p /var/run/snmpd.pid
zabbix 4444 1 0 15:00 ? 00:00:00 /usr/bin/perl /usr/sbin/snmptt --daemon
zabbix 4445 4444 0 15:00 ? 00:00:00 /usr/bin/perl /usr/sbin/snmptt --daemon
root 9300 29899 0 15:25 pts/2 00:00:00 grep snmp
zabbix 16576 16511 0 Aug16 ? 00:00:11 /path/to/sbin/zabbix_server: snmp trapper [processed data in 0.000007 sec, idle 1 sec]
root 16600 1 0 Aug16 ? 00:00:07 /usr/sbin/snmptrapd -A -Lf /var/log/snmptrapd.log -D -p /var/run/snmptrapd.pid
发送捕获的陷阱的日志文件是/var/tmp/zabbixtest/zabbix_traps.tmp
# egrep "^(log_file|pid)" /etc/snmp/snmptt.ini
pid_file = /var/run/snmptt/snmptt.pid
log_file=/var/tmp/zabbixtest/zabbix_traps.tmp
但是,陷阱日志文件正在被写入并由用户拥有root
,而不是像zabbix
预期的用户那样。此外,该文件的权限为0640
,这意味着运行服务器的 zabbix 用户无法读取该文件。
# service snmptt stop
Stopping snmptt: [ OK ]
# rm /var/tmp/zabbixtest/zabbix_traps.tmp
rm: remove regular file `/var/tmp/zabbixtest/zabbix_traps.tmp'? y
# ls -lia /var/tmp/zabbixtest/zabbix_traps.tmp
ls: cannot access /var/tmp/zabbixtest/zabbix_traps.tmp: No such file or directory
# ls -lia /var/tmp/zabbixtest/
total 24
263224 drwxrwxr-x 2 root zabbix 4096 Aug 17 15:32 .
262145 drwxrwxrwt 7 root root 4096 Aug 17 14:53 ..
# service snmptt start
Starting snmptt: PID file: /var/run/snmptt/snmptt.pid
[ OK ]
# ps -ef | grep snmptt
zabbix 9944 1 0 15:32 ? 00:00:00 /usr/bin/perl /usr/sbin/snmptt --daemon
zabbix 9945 9944 0 15:32 ? 00:00:00 /usr/bin/perl /usr/sbin/snmptt --daemon
root 9981 29899 0 15:32 pts/2 00:00:00 grep snmptt
# ps -ef | grep snmp
root 3796 1 0 Jun19 ? 00:13:04 /usr/sbin/snmpd -LS0-6d -Lf /dev/null -p /var/run/snmpd.pid
zabbix 9944 1 0 15:32 ? 00:00:00 /usr/bin/perl /usr/sbin/snmptt --daemon
zabbix 9945 9944 0 15:32 ? 00:00:00 /usr/bin/perl /usr/sbin/snmptt --daemon
root 9986 29899 0 15:32 pts/2 00:00:00 grep snmp
zabbix 16576 16511 0 Aug16 ? 00:00:11 /path/to/sbin/zabbix_server: snmp trapper [processed data in 0.000079 sec, idle 1 sec]
root 16600 1 0 Aug16 ? 00:00:07 /usr/sbin/snmptrapd -A -Lf /var/log/snmptrapd.log -D -p /var/run/snmptrapd.pid
# ls -lia /var/tmp/zabbixtest/zabbix_traps.tmp
262265 -rw-r----- 1 root root 122 Aug 17 15:32 /var/tmp/zabbixtest/zabbix_traps.tmp
请注意 的文件权限和所有权/var/tmp/zabbixtest/zabbix_traps.tmp
。
因此,zabbix
用户无法读取该文件并因此无法处理它。
例如,我可以通过手动将陷阱文件的模式修改/var/tmp/zabbixtest/zabbix_traps.tmp
为 来修复0644
,但我希望有更好的方法,例如通过配置文件,因为文件位置很可能会改变。 (有一些博客网站建议将模式更改为0777,显然这不是正确的解决方案)。
我猜这是由于snmptrapd
配置所致,以 root 身份运行,但不确定解决此问题的最佳方法。
我的问题:
root
为什么陷阱日志文件以具有权限的用户身份写入0640
,而不是以zabbix
用户运行身份写入snmptt
?
我应该如何配置snmptt
和/或snmptrapd
让陷阱文件由 zabbix
用户而不是 root 用户拥有和读取。
其他相关信息:
snmptrapd 配置文件:
# grep -v '^#' /etc/snmp/snmptrapd.conf
disableAuthorization yes
traphandle default /usr/sbin/snmptthandler
运行 RHEL 6.6
答案1
至少在 Richlv 关于以独立模式创建文件的评论之后找到了解决方案。
我做了一些改变,至少得到了一个可行的解决方案。
snmptrapd
我想我在更改snmptrapd.conf
为 readtraphandle default /usr/sbin/snmptthandler
而不是 后没有重新启动traphandle default /usr/sbin/snmptt
。
为什么写成root
snmptt
正在调用 的一个新实例snmptrapd
,该实例以 root 身份运行,并且必须绑定到 snmp 端口 162。因此 写入的文件snmptt
也归 root 所有。
然而,权限对我来说仍然是个谜。我不知道0640
权限来自哪里。
据信已解决该问题的主要更改
- 重新启动
snmptrapd
(service snmptrapd restart
),这会导致重新读取snmptrapd.conf
,以确保snmptthandler
用于处理陷阱snmptt
,而不是之前已写入配置文件的 。
然而,这并不能解决整个问题,因为现在snmptthandler
将陷阱写入假脱机目录,该目录随后由守护进程/var/spool/snmptt
读取:snmptt
# grep spool_directory /etc/snmp/snmptt.ini
spool_directory = /var/spool/snmptt/
# grep -A5 SPOOL /usr/sbin/snmptthandler
...
while (defined(my $line = <>))
{
print SPOOL $line;
if ($DEBUGGING >= 1)
{
# Print out item passed from snmptrapd
print $line."\n";
}
假脱机文件将由 拥有,具有与独立模式下的日志文件root
相同的权限。这意味着守护进程在 完成后仍然无法读取和处理它们。 (在日志文件中,尝试读取假脱机文件时会出现错误。)0640
snmptt
snmptt
snmptthandler
/var/log/snmptt/snmptt.debug
permissions denied
那么,下一步:
将 spool 目录的所有权设置为snmptt
守护程序用户,并使用设置 gid在假脱机目录上,导致写入的新文件由运行snmptt
.
chown zabbix:zabbix /var/spool/smptt
chmod g+s /var/spool/smptt
#ls -lia /var/spool/snmptt/
total 8
209 drwxrwsr-x 2 zabbix zabbix 4096 Aug 18 11:40 .
#ps -ef | grep snmptt
zabbix 8787 1 0 12:44 ? 00:00:00 /usr/bin/perl /usr/sbin/snmptt --daemon
之后,守护程序可以读取假脱机文件,并将文件以用户身份(而不是 root 身份)snmptt
写入预期的日志目录。/var/tmp/zabbixtest/zabbix_traps.tmp
zabbix
### After a trap is received
# ls -lia /var/tmp/zabbixtest/snmptt.log
524605 -rw-rw-r-- 1 zabbix zabbix 646 Aug 18 13:16 snmptt.log
日志文件的 umask 来自snmptt
脚本:
$ grep -i umask /usr/sbin/snmptt
#umask 0;
umask 002;
#umask 0;
umask 002;
其他变化,良好的实践,但不认为直接影响结果
- 改为
snmptt.ini
readmode=daemon
而不是mode=standalone
. (不清楚这有什么影响,如果有的话) - 更改
/etc/snmp/snmptt.ini
为读取daemon_uid=
(空白)而不是daemon_uid=zabbix
(这是推荐的SNMP 文档snmptt
,并防止同一用户进行双重处理。
所以,有一种方法可以解决它。不确定这是否是最好的方法。最好的方法可能包括更改snmptthandler
为使用配置文件中定义的用户/umask。
这并没有回答完整的问题(0640 权限仍然不清楚)欢迎对此发表评论或提供帮助。