Skip to content

Checking if a websocket consumer has been accepted #2169

@TheStaticTurtle

Description

@TheStaticTurtle

Hi

I'm currently building a generic decorator that auto-handles exceptions and sends them to the client.
A simplified version looks like this:

def consumer_handler_error_autohandle(response_message_type):
    def decorator(func):
        @functools.wraps(func)
        async def wrapper(self, *args, **kwargs):
            try:
                await func(self, *args, **kwargs)
            except Exception as err:
                self._logger.error(f"{func.__name__}({args}, {kwargs}) failed: {err}")
                try:
                    await self.send(json.dumps({"type": response_message_type, "error": str(err) }))
                except Exception as err2:
                    self._logger.critical(f"Failed to send error message to client", exc_info=err2)
        return wrapper
    return decorator

This works very well for my application. The issue arises when I decorate the connect function. If the exception happens before the call to accept, (which it does because rights and other things are checked before) there is no way of sending the error.

For my application I can just accept the socket, send an error message, and close it immediately afterward.
So after much trial and error, I found a way to check if the socket has been accepted, but it's not pretty:

is_still_connecting = self.base_send.__self__.real_send.args[0].state == WebSocketProtocol.STATE_CONNECTING
if is_still_connecting:
    await self.accept()

Short of doing a subclass and implementing an accepted flag myself inside the consumer, is there a build in way of checking if the the consumer has sent the accept message?

Thanks,
Samuel

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions