""" v5 (GLaDOS) =========== Description ----------- Manage the V5 layer of GLaDOS. """ import logging import socket from threading import Thread from functools import wraps class V5: """Manage connexion beetween the bot and the V5 server, and manage callbacks. Attributes ---------- irc : irc.IRC, public An IRC instance. sock : ssl.SSLSocket, private The V5 socket. handler : Thread, private callbacks : list, private List of the registred callbacks. Methods ------- start : NoneType, public Start v5 handler. on : function, public Add a callback to the v5 handler. handle : NoneType, private Handle the incoming messages and callbacks. """ def __init__(self, v5_params: tuple, irc): """Initialize V5 handle. Parameters ---------- v5 : tuple The information on V5 server (host, port). irc : irc.IRC An initialized IRC instance. """ self.irc = irc self.__sock = socket.socket(socket.AF_INET,socket.SOCK_DGRAM) self.__sock.bind(v5_params) self.__handler = Thread(target=self.__handle) self.__callbacks = [] def start(self): """Start v5 handler.""" self.__handler.start() logging.info("started") def on(self, event): """Adds a callback to the v5 handler. Parameters ---------- event : function ``event`` is a function taking in parameter a list of channels and a string, and return ``True`` if the callback should be executed. """ def callback(func): @wraps(func) def wrapper(channels, message): func(channels, message) self.__callbacks.append((event, wrapper)) return wrapper return callback def __handle(self): while True: data, addr = self.__sock.recvfrom(4096) data = data.decode() logging.debug("received %s", data) channels, message = data.split(":", 1) channels = channels.split(" ") for event, callback in self.__callbacks: if event(channels, message): logging.info("passed %s", event.__name__) callback(channels, message)