def run_message_handler_for_bot( lib_module: Any, quiet: bool, config_file: str, bot_config_file: str, bot_name: str, ) -> Any: """ lib_module is of type Any, since it can contain any bot's handler class. Eventually, we want bot's handler classes to inherit from a common prototype specifying the handle_message function. Set default bot_details, then override from class, if provided """ bot_details = { 'name': bot_name.capitalize(), 'description': "", } bot_details.update(getattr(lib_module.handler_class, 'META', {})) # Make sure you set up your ~/.zuliprc client_name = "Zulip{}Bot".format(bot_name.capitalize()) try: client = Client(config_file=config_file, client=client_name) except configparser.Error as e: display_config_file_errors(str(e), config_file) sys.exit(1) bot_dir = os.path.dirname(lib_module.__file__) restricted_client = ExternalBotHandler(client, bot_dir, bot_details, bot_config_file) message_handler = prepare_message_handler(bot_name, restricted_client, lib_module) if not quiet: print("Running {} Bot:".format(bot_details['name'])) if bot_details['description'] != "": print("\n\t{}".format(bot_details['description'])) print(message_handler.usage()) def handle_message(message: Dict[str, Any], flags: List[str]) -> None: logging.info('waiting for next message') # `mentioned` will be in `flags` if the bot is mentioned at ANY position # (not necessarily the first @mention in the message). is_mentioned = 'mentioned' in flags is_private_message = is_private_message_from_another_user(message, restricted_client.user_id) # Provide bots with a way to access the full, unstripped message message['full_content'] = message['content'] # Strip at-mention botname from the message if is_mentioned: # message['content'] will be None when the bot's @-mention is not at the beginning. # In that case, the message shall not be handled. message['content'] = extract_query_without_mention(message=message, client=restricted_client) if message['content'] is None: return if is_private_message or is_mentioned: message_handler.handle_message( message=message, bot_handler=restricted_client ) signal.signal(signal.SIGINT, exit_gracefully) logging.info('starting message handling...') def event_callback(event: Dict[str, Any]) -> None: if event['type'] == 'message': handle_message(event['message'], event['flags']) client.call_on_each_event(event_callback, ['message'])
def run_message_handler_for_bot( lib_module: Any, quiet: bool, config_file: str, bot_config_file: str, bot_name: str, bot_source: str, ) -> Any: """ lib_module is of type Any, since it can contain any bot's handler class. Eventually, we want bot's handler classes to inherit from a common prototype specifying the handle_message function. Set default bot_details, then override from class, if provided """ bot_details = { "name": bot_name.capitalize(), "description": "", } bot_details.update(getattr(lib_module.handler_class, "META", {})) # Make sure you set up your ~/.zuliprc client_name = f"Zulip{bot_name.capitalize()}Bot" try: client = Client(config_file=config_file, client=client_name) except configparser.Error as e: display_config_file_errors(str(e), config_file) sys.exit(1) bot_dir = os.path.dirname(lib_module.__file__) restricted_client = ExternalBotHandler(client, bot_dir, bot_details, bot_config_file) message_handler = prepare_message_handler(bot_name, restricted_client, lib_module) if not quiet: print("Running {} Bot (from {}):".format(bot_details["name"], bot_source)) if bot_details["description"] != "": print("\n\t{}".format(bot_details["description"])) if hasattr(message_handler, "usage"): print(message_handler.usage()) else: print( f"WARNING: {bot_name} is missing usage handler, please add one eventually" ) def handle_message(message: Dict[str, Any], flags: List[str]) -> None: logging.info("waiting for next message") # `mentioned` will be in `flags` if the bot is mentioned at ANY position # (not necessarily the first @mention in the message). is_mentioned = "mentioned" in flags is_private_message = is_private_message_but_not_group_pm( message, restricted_client) # Provide bots with a way to access the full, unstripped message message["full_content"] = message["content"] # Strip at-mention botname from the message if is_mentioned: # message['content'] will be None when the bot's @-mention is not at the beginning. # In that case, the message shall not be handled. message["content"] = extract_query_without_mention( message=message, client=restricted_client) if message["content"] is None: return if is_private_message or is_mentioned: message_handler.handle_message(message=message, bot_handler=restricted_client) signal.signal(signal.SIGINT, exit_gracefully) logging.info("starting message handling...") def event_callback(event: Dict[str, Any]) -> None: if event["type"] == "message": handle_message(event["message"], event["flags"]) client.call_on_each_event(event_callback, ["message"])
def run_message_handler_for_bot(lib_module, quiet, config_file, bot_name): # type: (Any, bool, str, str) -> Any # # lib_module is of type Any, since it can contain any bot's # handler class. Eventually, we want bot's handler classes to # inherit from a common prototype specifying the handle_message # function. # # Make sure you set up your ~/.zuliprc client = Client(config_file=config_file, client="Zulip{}Bot".format(bot_name.capitalize())) bot_dir = os.path.dirname(lib_module.__file__) restricted_client = ExternalBotHandler(client, bot_dir) message_handler = lib_module.handler_class() if hasattr(message_handler, 'initialize'): message_handler.initialize(bot_handler=restricted_client) # Set default bot_details, then override from class, if provided bot_details = { 'name': bot_name.capitalize(), 'description': "", } bot_details.update(getattr(lib_module.handler_class, 'META', {})) if not quiet: print("Running {} Bot:".format(bot_details['name'])) if bot_details['description'] != "": print("\n\t{}".format(bot_details['description'])) print(message_handler.usage()) def handle_message(message, flags): # type: (Dict[str, Any], List[str]) -> None logging.info('waiting for next message') # `mentioned` will be in `flags` if the bot is mentioned at ANY position # (not necessarily the first @mention in the message). is_mentioned = 'mentioned' in flags is_private_message = is_private_message_from_another_user( message, restricted_client.user_id) # Strip at-mention botname from the message if is_mentioned: # message['content'] will be None when the bot's @-mention is not at the beginning. # In that case, the message shall not be handled. message['content'] = extract_query_without_mention( message=message, client=restricted_client) if message['content'] is None: return if is_private_message or is_mentioned: message_handler.handle_message(message=message, bot_handler=restricted_client) signal.signal(signal.SIGINT, exit_gracefully) logging.info('starting message handling...') def event_callback(event): # type: (Dict[str, Any]) -> None if event['type'] == 'message': handle_message(event['message'], event['flags']) client.call_on_each_event(event_callback, ['message'])
def run_message_handler_for_bot( lib_module: Any, quiet: bool, config_file: str, bot_config_file: str, bot_name: str, ) -> Any: """ lib_module is of type Any, since it can contain any bot's handler class. Eventually, we want bot's handler classes to inherit from a common prototype specifying the handle_message function. Set default bot_details, then override from class, if provided """ bot_details = { 'name': bot_name.capitalize(), 'description': "", } bot_details.update(getattr(lib_module.handler_class, 'META', {})) # Make sure you set up your ~/.zuliprc client_name = "Zulip{}Bot".format(bot_name.capitalize()) try: client = Client(config_file=config_file, client=client_name) except configparser.Error as e: display_config_file_errors(str(e), config_file) sys.exit(1) bot_dir = os.path.dirname(lib_module.__file__) restricted_client = ExternalBotHandler(client, bot_dir, bot_details, bot_config_file) message_handler = prepare_message_handler(bot_name, restricted_client, lib_module) if not quiet: print("Running {} Bot:".format(bot_details['name'])) if bot_details['description'] != "": print("\n\t{}".format(bot_details['description'])) print(message_handler.usage()) def handle_message(message: Dict[str, Any], flags: List[str]) -> None: logging.info('waiting for next message') # `mentioned` will be in `flags` if the bot is mentioned at ANY position # (not necessarily the first @mention in the message). is_mentioned = 'mentioned' in flags is_private_message = is_private_message_from_another_user(message, restricted_client.user_id) # Provide bots with a way to access the full, unstripped message message['full_content'] = message['content'] # Strip at-mention botname from the message if is_mentioned: # message['content'] will be None when the bot's @-mention is not at the beginning. # In that case, the message shall not be handled. message['content'] = extract_query_without_mention(message=message, client=restricted_client) if message['content'] is None: return if is_private_message or is_mentioned: message_handler.handle_message( message=message, bot_handler=restricted_client ) signal.signal(signal.SIGINT, exit_gracefully) logging.info('starting message handling...') def event_callback(event: Dict[str, Any]) -> None: if event['type'] == 'message': handle_message(event['message'], event['flags']) client.call_on_each_event(event_callback, ['message'])