我正在使用Django通道,以便在创建模型的新实例时提供即时通知。
为此,我正在使用django-channels和SyncConsumer。除了websocket_disconnect
被n次循环调用之外,一切都按预期进行。
这是我的消费者代码:
class BaseConsumer(SyncConsumer):
def websocket_connect(self, event):
self.send({"type": "websocket.accept"})
def websocket_receive(self, event):
# do some stuff here
def websocket_disconnect(self, event):
print("websocket_disconnect")
这是我的网络服务器上的日志:
api_1 | websocket_disconnect
api_1 | websocket_disconnect
api_1 | websocket_disconnect
api_1 | websocket_disconnect
api_1 | websocket_disconnect
api_1 | websocket_disconnect
api_1 | websocket_disconnect
api_1 | websocket_disconnect
api_1 | websocket_disconnect
api_1 | websocket_disconnect
这种情况一直持续下去,直到我停止Web服务器为止。
当我在前端手动关闭连接(我使用Javascript,因此我叫ws.close()
)以及关闭浏览器选项卡/客户端时,都会发生此行为。
在我看来,这并不是正确的行为,因为我听到我的计算机迷们像地狱一样工作。关闭连接后如何停止触发此方法?因为连接本身已正确关闭,所以我可以在javascript onclose
方法中进行验证,该方法仅在前端触发一次。
还有其他人遇到过类似的事情吗?
谢谢!
答案 0 :(得分:0)
我在StackOverFlow上发布问题几天后才有这个问题,我能够找到解决问题的方法。
深入阅读文档,我发现了以下内容:
关闭与消费者连接的插座或连接时- 由您或客户-您很可能会收到一个发送给您的事件 (例如,http.disconnect或websocket.disconnect),并且您的 应用程序实例将在短时间内采取行动 它。
完成断开后的清理后,您需要 引发channels.exceptions.StopConsumer以停止ASGI应用程序 干净地让服务器清理它。如果让它继续运行- 没有引发此异常-服务器将到达其应用程序 关闭超时(达芙妮默认为10秒),然后终止 您的应用程序并发出警告。
下面的通用消费者为您执行此操作,因此仅在以下情况下才需要 您正在基于AsyncConsumer编写自己的消费者类或 SyncConsumer。
总而言之,为了正确关闭连接,需要引发StopConsumer
。
希望这个答案将来可以解决其他人的头痛!