Postgres侦听/通知为消息队列


17

有什么方法可以使用Postgres侦听/通知功能将消息传递到通道,并且只有一个侦听器使用此消息吗?

这样做的目的是让我有多个“工作者”应用程序都在收听同一个Postgres频道。但是我只希望每个通过通知渠道收到的消息都完成一次工作。

如果“听/通知”不是Postgres中的正确功能,是否应该使用其他功能?

理想情况下,我希望不使用任何其他扩展名即可执行此操作。

Answers:


24

根据有关PostgreSQL的文档NOTIFY

NOTIFY命令将通知事件与可选的“有效载荷”字符串一起发送到每个客户端应用程序,该客户端应用程序先前已为当前数据库中的指定通道名称执行了LISTEN通道。通知对所有用户可见

(强调我的)

这意味着您不能仅仅通过 做自己想做的事情LISTEN/NOTIFY。但是,您既可以有一个表来存储排队的消息,也LISTEN/NOTIFY可以通知外部应用程序“消息队列中有新事物”,并可以使用这些外部应用程序中的一些额外逻辑,以便只有一个人可以使用该消息。

PostgreSQL 9.5中的“跳过锁定是什么 ”一文中描述的策略这可能是在PostgreSQL中实现消息队列的最安全/最简单的方法。请特别注意“跳过锁定如何提供帮助”部分。还要仔细阅读他们的警告之一:

在RDBMS中实现的队列永远无法与快速专用排队系统的性能相提并论,即使该队列能够提供与PostgreSQL相同的原子性和持久性保证。使用SKIP LOCKED优于现有的数据库内方法,但是使用专用且高度优化的外部排队引擎仍会更快。

如果队列数量很大,这尤其重要。


1
我希望我能向该文章的作者颁发赏金。非常有帮助。
通配符

3

我前一段时间做了类似的事情,并获得了成功,我使用了RabbitMQ和这个插件https://github.com/gmr/pgsql-listen-exchange

基本上,RabbitMQ连接到PostgreSQL并侦听notify事件,然后您可以使用RabbitMQ将消息聚合到所需的尽可能多的队列,并有一个使用每个队列的应用程序

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.