php - RabbitMQ 阻塞状态导致挂起的发布者连接
问题描述
在将消息发布到处于阻塞状态的 rabbitmq 服务器时,我们遇到了灾难性的行为。
例如内存警报或磁盘警报会导致rabbitmq 阻止所有发布,直到警报消除。所有尝试写入的连接都必须等待。这一切都很好,但问题是我们找不到任何方法来超时这个等待。
所以产生的行为是,请求永远不会结束(或者由于 nginx 超时而超时)导致崩溃。我们可以用这段代码重现问题:
function p()
{
$c = new \AMQPConnection([
'host' => 'shoprabbit',
'port' => 5672,
'read_timeout' => 1,
'write_timeout' => 1,
'connect_timeout' => 1,
'confirm_timeout' => 1,
'rpc_timeout' => 1,
'login' => 'guest',
'password' => 'guest',
'heartbeat' => '3',
]);
$c->connect();
$ch = new \AMQPChannel($c);
$ch->setPrefetchCount(0);
$ex = new \AMQPExchange($ch);
$ex->setType(AMQP_EX_TYPE_DIRECT);
$queue = new \AMQPQueue($ch);
$queue->setName('demo');
$queue->setFlags(AMQP_DURABLE);
$queue->declareQueue();
$ex->publish('empty', 'demo', AMQP_NOPARAM, ['delivery_mode' => AMQP_DURABLE]);
}
p();
并在rabbitmq中模拟阻塞状态rabbitmqctl set_vm_memory_high_watermark 0
如您所见,在这种情况下,没有任何超时发生。Heartbeat 也不起作用,因为 php 是单线程的,并且无法关闭阻塞连接。
谁能找到解决方案?
解决方案
推荐阅读
- powershell - 字符串上的Powershell调用类?
- python - Python:在类中获取类类型
- python - 如何根据 ID 值更新行 - Sheets API py
- django - 在 django + ubuntu + apache 中写入文件时出现权限错误
- javascript - d3.js 隐藏不透明度的弹出窗口不能与指针事件一起正常工作
- javascript - 如何在JS中的对象的多个字段中转换数据类型
- google-sheets - INDEX MATCH 公式 Google 表格返回 N/A 值
- apache-spark - 如何对 PySpark DataFrame 的精确行数(而不是分数)进行采样()
- vba - 获取 unitVector XYZ 值
- api - 请求不通过tomcat和浏览器访问spring boot嵌入式服务器