【发布时间】:2021-06-04 08:00:45
【问题描述】:
我正在尝试在 Mongo Atlas 集群故障转移期间使用 motor 诊断读取故障。 Retryable-Reads 规范定义了aggregate calls are retryable,但是Cursor.getMore is not。我的代码如下所示:
cursor = db.foo.aggregate([...])
if not await cursor.fetch_next:
raise SomeException
doc = cursor.next_object()
此代码似乎不会在集群故障转移期间重试,因为它在内部调用 getMore我假设。我不完全清楚是否是这种情况。更别提fetch_next is deprecated anyway了。
将其更改为可重试读取吗?
async for doc in cursor:
break
else:
raise SomeException
还是这样导致内部处理相同,问题出在其他地方?
目标是尝试以可重试的方式从聚合管道(有一个或没有)读取单个结果文档,如果没有则引发异常。
【问题讨论】:
-
错误是什么?可重试读取是解决网络错误的非常低级的事情。如果您正在获取单个文档,则不会调用 getMore。文档(如果存在)在第一批 github.com/mongodb/mongo-python-driver/blob/… 中返回,并且聚合命令本身是可重试的。
-
ConnectionRefusedError: [Errno 111] Connection refusedDuring handling of the above exception, another exception occurred:[...]pymongo.errors.AutoReconnect: example.mongodb.net:27017: [Errno 111] Connection refused— 我不确定这是否意味着驱动程序 确实 尝试重新连接并且失败了两次。如果是这种情况,那么集群扩展期间的 Atlas 故障转移就相当糟糕了……?! -
可能没有完全损坏,但比可接受的要慢一些。可重试的东西只尝试重新连接一次。如果第二次尝试失败,则返回原始错误。我猜在你的情况下,新的主节点还没有被选举出来,或者至少客户不知道选举结果。
-
尝试设置“primaryPreferred”阅读偏好。它应该有助于解决这种情况。默认情况下,它严格从主要读取以提高一致性。如果您可以阅读过时的数据,请放宽阅读偏好。否则,您将需要在应用程序级别处理此类错误。
-
有道理。所以,需要明确的是,上面的代码应该没问题,问题可能源于“迟到的选举”和过于严格的阅读偏好?
标签: python mongodb pymongo mongodb-atlas