我正在尝试集成 snmptrapd 和 RabbitMQ 以将陷阱通知传递到外部系统。
我的系统由 3 个组件组成:
- 带有 snmptrapd 和 RabbitMQ (Publisher) 的 Linux 虚拟机;
- 带有 RabbitMQ(消费者)的 Linux 虚拟机;
- 一个带有 docker 的 Linux 裸机,所以我可以有很多容器发送陷阱(使用 nping)
snmptrapd 部分很简单:
authCommunity execute mycom
traphandle default /root/some_script
在我的第一次尝试中,它some_script
是用 Python 编写的,但性能并不完美(20 个容器在 10 秒内每秒发送 1 个陷阱,我在消费者中只收到 160 条消息)。
#!/usr/bin/env python
import pika
import sys
message = ""
for line in sys.stdin :
message += (line)
credentials = pika.PlainCredentials('test', 'test')
parameters = pika.ConnectionParameters('my_ip', 5672, '/', credentials)
connection = pika.BlockingConnection(parameters)
channel = connection.channel()
channel.queue_declare(queue='snmp')
channel.basic_publish(exchange='',
routing_key='snmp',
body=message)
connection.close()
我切换到 Perl,现在我可以获得 200 个陷阱/消息。
我的 Perl 脚本使用Net::AMQP::RabbitMQ
#!/usr/bin/perl
use Net::AMQP::RabbitMQ;
foreach my $line ( <STDIN> ) {
chomp( $line );
$message = "$message\n$line";
}
my $mq = Net::AMQP::RabbitMQ->new();
$mq->connect("my_ip", {
user => "test",
password => "test",
vhost => "/"
});
$mq->channel_open(1);
$mq->publish(1, "snmp", $message);
$mq->disconnect();
但我想要更好。我尝试了 200 个容器每秒发送 1 个陷阱,但失败得很惨,只收到了消费者中大约 10% 的消息。
我认为这与每次收到陷阱都必须在 RabbitMQ 中打开、发布和关闭通道的开销有关,因为在网络级别我收到了所有消息(通过 tcpdump 检查)。
有没有办法保持始终打开的发布通道,这样我就不必重新打开/创建与队列的连接?