Added logic to propagate events to the websockets backend
This commit is contained in:
parent
cd3aea5cd6
commit
c05fc9ee3f
3 changed files with 29 additions and 2 deletions
|
@ -172,6 +172,7 @@ class HttpBackend(Backend):
|
||||||
loop.run_until_complete(send_event(websocket))
|
loop.run_until_complete(send_event(websocket))
|
||||||
except websockets.exceptions.ConnectionClosed:
|
except websockets.exceptions.ConnectionClosed:
|
||||||
self.logger.info('Client connection lost')
|
self.logger.info('Client connection lost')
|
||||||
|
self.active_websockets.remove(websocket)
|
||||||
|
|
||||||
|
|
||||||
def redis_poll(self):
|
def redis_poll(self):
|
||||||
|
|
|
@ -21,7 +21,7 @@ class WebsocketBackend(Backend):
|
||||||
"""
|
"""
|
||||||
|
|
||||||
# Websocket client message recv timeout in seconds
|
# Websocket client message recv timeout in seconds
|
||||||
_websocket_client_timeout = 60
|
_websocket_client_timeout = 0
|
||||||
|
|
||||||
def __init__(self, port=8765, bind_address='0.0.0.0', ssl_cafile=None,
|
def __init__(self, port=8765, bind_address='0.0.0.0', ssl_cafile=None,
|
||||||
ssl_capath=None, ssl_cert=None, ssl_key=None,
|
ssl_capath=None, ssl_cert=None, ssl_key=None,
|
||||||
|
@ -45,7 +45,7 @@ class WebsocketBackend(Backend):
|
||||||
:param ssl_capath: Path to the certificate authority directory if required by the SSL configuration (default: None)
|
:param ssl_capath: Path to the certificate authority directory if required by the SSL configuration (default: None)
|
||||||
:type ssl_capath: str
|
:type ssl_capath: str
|
||||||
|
|
||||||
:param client_timeout: Timeout without any messages being received before closing a client connection. A zero timeout keeps the websocket open until an error occurs (default: 60 seconds)
|
:param client_timeout: Timeout without any messages being received before closing a client connection. A zero timeout keeps the websocket open until an error occurs (default: 0, no timeout)
|
||||||
:type ping_timeout: int
|
:type ping_timeout: int
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
@ -54,6 +54,7 @@ class WebsocketBackend(Backend):
|
||||||
self.port = port
|
self.port = port
|
||||||
self.bind_address = bind_address
|
self.bind_address = bind_address
|
||||||
self.client_timeout = client_timeout
|
self.client_timeout = client_timeout
|
||||||
|
self.active_websockets = set()
|
||||||
|
|
||||||
self.ssl_context = get_ssl_server_context(ssl_cert=ssl_cert,
|
self.ssl_context = get_ssl_server_context(ssl_cert=ssl_cert,
|
||||||
ssl_key=ssl_key,
|
ssl_key=ssl_key,
|
||||||
|
@ -74,10 +75,29 @@ class WebsocketBackend(Backend):
|
||||||
websocket.send(url=url, msg=msg, **websocket_args)
|
websocket.send(url=url, msg=msg, **websocket_args)
|
||||||
|
|
||||||
|
|
||||||
|
def notify_web_clients(self, event):
|
||||||
|
""" Notify all the connected web clients (over websocket) of a new event """
|
||||||
|
async def send_event(websocket):
|
||||||
|
try:
|
||||||
|
await websocket.send(str(event))
|
||||||
|
except Exception as e:
|
||||||
|
self.logger.warning('Error on websocket send_event: {}'.format(e))
|
||||||
|
|
||||||
|
loop = get_or_create_event_loop()
|
||||||
|
|
||||||
|
for websocket in self.active_websockets:
|
||||||
|
try:
|
||||||
|
loop.run_until_complete(send_event(websocket))
|
||||||
|
except websockets.exceptions.ConnectionClosed:
|
||||||
|
self.logger.info('Client connection lost')
|
||||||
|
self.active_websockets.remove(websocket)
|
||||||
|
|
||||||
|
|
||||||
def run(self):
|
def run(self):
|
||||||
super().run()
|
super().run()
|
||||||
|
|
||||||
async def serve_client(websocket, path):
|
async def serve_client(websocket, path):
|
||||||
|
self.active_websockets.add(websocket)
|
||||||
self.logger.debug('New websocket connection from {}'.
|
self.logger.debug('New websocket connection from {}'.
|
||||||
format(websocket.remote_address[0]))
|
format(websocket.remote_address[0]))
|
||||||
|
|
||||||
|
@ -107,9 +127,11 @@ class WebsocketBackend(Backend):
|
||||||
|
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
if isinstance(e, websockets.exceptions.ConnectionClosed):
|
if isinstance(e, websockets.exceptions.ConnectionClosed):
|
||||||
|
self.active_websockets.remove(websocket)
|
||||||
self.logger.debug('Websocket client {} closed connection'.
|
self.logger.debug('Websocket client {} closed connection'.
|
||||||
format(websocket.remote_address[0]))
|
format(websocket.remote_address[0]))
|
||||||
elif isinstance(e, asyncio.TimeoutError):
|
elif isinstance(e, asyncio.TimeoutError):
|
||||||
|
self.active_websockets.remove(websocket)
|
||||||
self.logger.debug('Websocket connection to {} timed out'.
|
self.logger.debug('Websocket connection to {} timed out'.
|
||||||
format(websocket.remote_address[0]))
|
format(websocket.remote_address[0]))
|
||||||
else:
|
else:
|
||||||
|
|
|
@ -33,6 +33,10 @@ class EventProcessor(object):
|
||||||
if backend:
|
if backend:
|
||||||
backend.notify_web_clients(event)
|
backend.notify_web_clients(event)
|
||||||
|
|
||||||
|
backend = get_backend('websocket')
|
||||||
|
if backend:
|
||||||
|
backend.notify_web_clients(event)
|
||||||
|
|
||||||
|
|
||||||
def process_event(self, event):
|
def process_event(self, event):
|
||||||
""" Processes an event and runs the matched hooks with the highest score """
|
""" Processes an event and runs the matched hooks with the highest score """
|
||||||
|
|
Loading…
Reference in a new issue