Description
I have the following MyConsumer
class:
from channels.generic.websocket import WebsocketConsumer
from channels.exceptions import StopConsumer
import json
class MyConsumer(WebsocketConsumer):
def connect(self):
self.accept()
def receive(self, text_data=None, bytes_data=None):
data = json.loads(text_data)
n = data["number"]
for i in range(n):
self.send(json.dumps({"number":i}))
def disconnect(self, code):
raise StopConsumer()
The input JSON contains only a single parameter called number. I am testing this code using a chrome plugin. When I open the connection and close it without sending any message, the disconnect method is executed as expected.
When the number is for example 100000 and the loop inside the receive method is not yet finished and I disconnect in between, the disconnect method is not called and I get the following error:
ERROR - server - Exception inside application: Attempt to send on a closed protocol.
File "MyConsumer.py", line 2, in receive
self.send
File "python3.6/site-packages/channels/generic/websocket.py", line 69, in send
{"type": "websocket.send", "text": text_data},
File "python3.6/site-packages/channels/consumer.py", line 107, in send
self.base_send(message)
File "python3.6/site-packages/asgiref/sync.py", line 64, in __call__
return call_result.result()
File "/usr/local/var/pyenv/versions/3.6.10/lib/python3.6/concurrent/futures/_base.py", line 432, in result
return self.__get_result()
File "/usr/local/var/pyenv/versions/3.6.10/lib/python3.6/concurrent/futures/_base.py", line 384, in __get_result
raise self._exception
File "python3.6/site-packages/asgiref/sync.py", line 78, in main_wrap
result = await self.awaitable(*args, **kwargs)
File "python3.6/site-packages/channels/sessions.py", line 220, in send
return await self.real_send(message)
File "python3.6/site-packages/daphne/server.py", line 198, in handle_reply
protocol.handle_reply(message)
File "python3.6/site-packages/daphne/ws_protocol.py", line 179, in handle_reply
self.serverSend(message["text"], False)
File "site-packages/daphne/ws_protocol.py", line 223, in serverSend
self.sendMessage(content.encode("utf8"), binary)
File "python3.6/site-packages/autobahn/websocket/protocol.py", line 2216, in sendMessage
raise Disconnected("Attempt to send on a closed protocol")
Attempt to send on a closed protocol
OS: Mac OS X
runtime: python 3.6.10
daphne==2.2.0
Django==2.0.6
channels==2.1.1
channels-redis==2.2.1
-
Expected: The docs mention that the disconnect method should be called when the client closes the connection and an event is received (https://channels.readthedocs.io/en/latest/topics/consumers.html#closing-consumers). I expect that the disconnect method is called even if the loop is not finished yet.
-
I am running Channels using daphne.