mirror of
				https://github.com/solero/houdini.git
				synced 2025-11-03 22:21:54 +00:00 
			
		
		
		
	Remove all code related to "hot-reloading"
Support is being dropped for now and until further notice.
This commit is contained in:
		@@ -5,7 +5,8 @@ from abc import abstractmethod
 | 
			
		||||
import asyncio
 | 
			
		||||
import enum
 | 
			
		||||
import logging
 | 
			
		||||
import copy
 | 
			
		||||
import importlib
 | 
			
		||||
import pkgutil
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class StatusField(enum.IntEnum):
 | 
			
		||||
@@ -19,7 +20,7 @@ class StatusField(enum.IntEnum):
 | 
			
		||||
    HasWalkedPuffleFirstTime = 65536
 | 
			
		||||
    HasWalkedPuffleSecondTime = 131072
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
            package_modules = package_modules + sub_package_modules
 | 
			
		||||
class ConflictResolution(enum.Enum):
 | 
			
		||||
    Silent = 0
 | 
			
		||||
    Append = 1
 | 
			
		||||
@@ -45,24 +46,15 @@ class _AbstractManager(dict):
 | 
			
		||||
        self.server = server
 | 
			
		||||
        self.logger = logging.getLogger('houdini')
 | 
			
		||||
 | 
			
		||||
        self.__backup = None
 | 
			
		||||
        super().__init__()
 | 
			
		||||
 | 
			
		||||
    @abstractmethod
 | 
			
		||||
    def load(self, module):
 | 
			
		||||
        """Loads entries from module"""
 | 
			
		||||
    async def setup(self, module):
 | 
			
		||||
        """Setup manager class"""
 | 
			
		||||
 | 
			
		||||
    @abstractmethod
 | 
			
		||||
    def remove(self, module):
 | 
			
		||||
        """Removes all entries by module"""
 | 
			
		||||
 | 
			
		||||
    def backup(self):
 | 
			
		||||
        self.__backup = copy.copy(self)
 | 
			
		||||
 | 
			
		||||
    def restore(self):
 | 
			
		||||
        if self.__backup is not None:
 | 
			
		||||
            self.update(self.__backup)
 | 
			
		||||
            self.__backup = None
 | 
			
		||||
    async def load(self, module):
 | 
			
		||||
        """Loads entries from module"""
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class PenguinStringCompiler(OrderedDict):
 | 
			
		||||
 
 | 
			
		||||
@@ -64,6 +64,7 @@ player_in_room = handlers.player_in_room
 | 
			
		||||
 | 
			
		||||
class CommandManager(_AbstractManager):
 | 
			
		||||
    def load(self, module):
 | 
			
		||||
    async def load(self, module):
 | 
			
		||||
        command_objects = inspect.getmembers(module, is_command)
 | 
			
		||||
        if not isinstance(module, plugins.IPlugin):
 | 
			
		||||
            raise TypeError('Commands can only be loaded from plugins')
 | 
			
		||||
@@ -94,12 +95,6 @@ class CommandManager(_AbstractManager):
 | 
			
		||||
                else:
 | 
			
		||||
                    parent_commands[name] = [command_object]
 | 
			
		||||
 | 
			
		||||
    def remove(self, module):
 | 
			
		||||
        for command_name, command_handlers in self.items():
 | 
			
		||||
            for command_handler in command_handlers:
 | 
			
		||||
                if module.__name__ == command_handler.callback.__module__:
 | 
			
		||||
                    command_handlers.remove(command_handler)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def is_command(command_object):
 | 
			
		||||
    return issubclass(type(command_object), _Command)
 | 
			
		||||
 
 | 
			
		||||
@@ -1,41 +0,0 @@
 | 
			
		||||
import os
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def evaluate_listener_file_event(listener_file_event):
 | 
			
		||||
    # Ignore all directory events
 | 
			
		||||
    if listener_file_event.is_directory:
 | 
			
		||||
        return False
 | 
			
		||||
 | 
			
		||||
    listener_module_path = listener_file_event.src_path[2:]
 | 
			
		||||
 | 
			
		||||
    # Ignore non-Python files
 | 
			
		||||
    if listener_module_path[-3:] != ".py":
 | 
			
		||||
        return False
 | 
			
		||||
 | 
			
		||||
    # Ignore package index files
 | 
			
		||||
    if '__init__.py' in listener_module_path:
 | 
			
		||||
        return False
 | 
			
		||||
 | 
			
		||||
    listener_module = listener_module_path.replace(os.path.sep, ".")[:-3]
 | 
			
		||||
 | 
			
		||||
    return listener_module_path, listener_module
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def evaluate_plugin_file_event(plugin_file_event):
 | 
			
		||||
    # Ignore all directory events
 | 
			
		||||
    if plugin_file_event.is_directory:
 | 
			
		||||
        return False
 | 
			
		||||
 | 
			
		||||
    plugin_module_path = plugin_file_event.src_path[2:]
 | 
			
		||||
 | 
			
		||||
    # Ignore non-Python files
 | 
			
		||||
    if plugin_module_path[-3:] != ".py":
 | 
			
		||||
        return False
 | 
			
		||||
 | 
			
		||||
    # Remove file extension and replace path separator with dots. Then make like a banana.. and split.
 | 
			
		||||
    plugin_module_tokens = plugin_module_path.replace(os.path.sep, ".")[:-3].split(".")
 | 
			
		||||
 | 
			
		||||
    if plugin_module_tokens.pop() == "__init__":
 | 
			
		||||
        return plugin_module_path, ".".join(plugin_module_tokens)
 | 
			
		||||
 | 
			
		||||
    return False
 | 
			
		||||
@@ -1,88 +0,0 @@
 | 
			
		||||
import sys
 | 
			
		||||
import importlib
 | 
			
		||||
import logging
 | 
			
		||||
from watchdog.events import FileSystemEventHandler
 | 
			
		||||
 | 
			
		||||
from houdini.events import evaluate_listener_file_event
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class ListenerFileEventHandler(FileSystemEventHandler):
 | 
			
		||||
 | 
			
		||||
    def __init__(self, server):
 | 
			
		||||
        self.server = server
 | 
			
		||||
        self.logger = logging.getLogger('houdini')
 | 
			
		||||
 | 
			
		||||
    def on_created(self, event):
 | 
			
		||||
        listener_module_details = evaluate_listener_file_event(event)
 | 
			
		||||
 | 
			
		||||
        if not listener_module_details:
 | 
			
		||||
            return
 | 
			
		||||
 | 
			
		||||
        listener_module_path, listener_module = listener_module_details
 | 
			
		||||
 | 
			
		||||
        self.logger.debug('New listener module detected {}'.format(listener_module))
 | 
			
		||||
 | 
			
		||||
        try:
 | 
			
		||||
            module = importlib.import_module(listener_module)
 | 
			
		||||
            self.server.xt_listeners.load(module)
 | 
			
		||||
            self.server.xml_listeners.load(module)
 | 
			
		||||
 | 
			
		||||
            self.logger.info('New listener module loaded {}'.format(listener_module))
 | 
			
		||||
        except Exception as import_error:
 | 
			
		||||
            self.logger.error('{} detected in {}, not importing'.format(
 | 
			
		||||
                import_error.__class__.__name__, listener_module))
 | 
			
		||||
 | 
			
		||||
    def on_deleted(self, event):
 | 
			
		||||
        listener_module_details = evaluate_listener_file_event(event)
 | 
			
		||||
 | 
			
		||||
        if not listener_module_details:
 | 
			
		||||
            return
 | 
			
		||||
 | 
			
		||||
        listener_module_path, listener_module = listener_module_details
 | 
			
		||||
 | 
			
		||||
        if listener_module not in sys.modules:
 | 
			
		||||
            return
 | 
			
		||||
 | 
			
		||||
        listener_module_object = sys.modules[listener_module]
 | 
			
		||||
 | 
			
		||||
        self.logger.debug('Deleting listener module {}'.format(listener_module))
 | 
			
		||||
 | 
			
		||||
        self.server.xt_listeners.remove(listener_module_object)
 | 
			
		||||
        self.server.xml_listeners.remove(listener_module_object)
 | 
			
		||||
        del sys.modules[listener_module]
 | 
			
		||||
 | 
			
		||||
        self.logger.info('Deleted listener module {}'.format(listener_module))
 | 
			
		||||
 | 
			
		||||
    def on_modified(self, event):
 | 
			
		||||
        listener_module_details = evaluate_listener_file_event(event)
 | 
			
		||||
 | 
			
		||||
        if not listener_module_details:
 | 
			
		||||
            return
 | 
			
		||||
 | 
			
		||||
        listener_module_path, listener_module = listener_module_details
 | 
			
		||||
 | 
			
		||||
        if listener_module not in sys.modules:
 | 
			
		||||
            return False
 | 
			
		||||
 | 
			
		||||
        self.logger.info('Reloading listener module {}'.format(listener_module))
 | 
			
		||||
 | 
			
		||||
        self.server.xt_listeners.backup()
 | 
			
		||||
        self.server.xml_listeners.backup()
 | 
			
		||||
 | 
			
		||||
        listener_module_object = sys.modules[listener_module]
 | 
			
		||||
 | 
			
		||||
        self.server.xt_listeners.remove(listener_module_object)
 | 
			
		||||
        self.server.xml_listeners.remove(listener_module_object)
 | 
			
		||||
 | 
			
		||||
        try:
 | 
			
		||||
            module = importlib.reload(listener_module_object)
 | 
			
		||||
            self.server.xt_listeners.load(module)
 | 
			
		||||
            self.server.xml_listeners.load(module)
 | 
			
		||||
 | 
			
		||||
            self.logger.info('Successfully reloaded listener module {}!'.format(listener_module))
 | 
			
		||||
        except Exception as rebuild_error:
 | 
			
		||||
            self.logger.error('{} detected in {}, not reloading.'.format(
 | 
			
		||||
                rebuild_error.__class__.__name__, listener_module))
 | 
			
		||||
 | 
			
		||||
            self.server.xt_listeners.restore()
 | 
			
		||||
            self.server.xml_listeners.restore()
 | 
			
		||||
@@ -1,87 +0,0 @@
 | 
			
		||||
import sys
 | 
			
		||||
import importlib
 | 
			
		||||
import os.path
 | 
			
		||||
import logging
 | 
			
		||||
from watchdog.events import FileSystemEventHandler
 | 
			
		||||
 | 
			
		||||
from houdini.events import evaluate_plugin_file_event
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class PluginFileEventHandler(FileSystemEventHandler):
 | 
			
		||||
 | 
			
		||||
    def __init__(self, server):
 | 
			
		||||
        self.server = server
 | 
			
		||||
        self.logger = logging.getLogger('houdini')
 | 
			
		||||
 | 
			
		||||
    def on_created(self, event):
 | 
			
		||||
        plugin_module_details = evaluate_plugin_file_event(event)
 | 
			
		||||
 | 
			
		||||
        if not plugin_module_details:
 | 
			
		||||
            return
 | 
			
		||||
 | 
			
		||||
        plugin_module_path, plugin_module = plugin_module_details
 | 
			
		||||
 | 
			
		||||
        self.logger.debug('New plugin detected {}'.format(plugin_module))
 | 
			
		||||
 | 
			
		||||
        try:
 | 
			
		||||
            plugin_module_object = importlib.import_module(plugin_module)
 | 
			
		||||
 | 
			
		||||
            self.server.plugins.load(plugin_module_object)
 | 
			
		||||
 | 
			
		||||
            self.logger.info('New plugin {} has been loaded'.format(plugin_module))
 | 
			
		||||
        except Exception as import_error:
 | 
			
		||||
            self.logger.error('{} detected in {}, not importing'.format(
 | 
			
		||||
                import_error.__class__.__name__, plugin_module))
 | 
			
		||||
 | 
			
		||||
    def on_deleted(self, event):
 | 
			
		||||
        plugin_module_path = event.src_path[2:]
 | 
			
		||||
 | 
			
		||||
        plugin_module = plugin_module_path.replace(os.path.sep, ".")
 | 
			
		||||
 | 
			
		||||
        if plugin_module not in sys.modules:
 | 
			
		||||
            return
 | 
			
		||||
 | 
			
		||||
        self.logger.debug('Deleting plugin {}'.format(plugin_module))
 | 
			
		||||
 | 
			
		||||
        plugin_module_object = sys.modules[plugin_module]
 | 
			
		||||
 | 
			
		||||
        self.server.plugins.remove(plugin_module_object)
 | 
			
		||||
        del sys.modules[plugin_module]
 | 
			
		||||
 | 
			
		||||
        self.logger.info('Plugin {} has been removed'.format(plugin_module))
 | 
			
		||||
 | 
			
		||||
    def on_modified(self, event):
 | 
			
		||||
        plugin_module_details = evaluate_plugin_file_event(event)
 | 
			
		||||
        if not plugin_module_details:
 | 
			
		||||
            return
 | 
			
		||||
 | 
			
		||||
        plugin_module_path, plugin_module = plugin_module_details
 | 
			
		||||
 | 
			
		||||
        if plugin_module not in sys.modules:
 | 
			
		||||
            return
 | 
			
		||||
 | 
			
		||||
        self.logger.info('Reloading plugin {}'.format(plugin_module))
 | 
			
		||||
 | 
			
		||||
        plugin_module_object = sys.modules[plugin_module]
 | 
			
		||||
 | 
			
		||||
        self.server.xt_listeners.backup()
 | 
			
		||||
        self.server.xml_listeners.backup()
 | 
			
		||||
        self.server.commands.backup()
 | 
			
		||||
 | 
			
		||||
        self.server.plugins.remove(plugin_module_object)
 | 
			
		||||
 | 
			
		||||
        try:
 | 
			
		||||
            new_plugin_module = importlib.reload(plugin_module_object)
 | 
			
		||||
 | 
			
		||||
            self.server.plugins.load(new_plugin_module)
 | 
			
		||||
 | 
			
		||||
            self.logger.info('Successfully reloaded plugin {}'.format(plugin_module))
 | 
			
		||||
        except LookupError as lookup_error:
 | 
			
		||||
            self.logger.warning('Did not reload plugin \'{}\': {}'.format(plugin_module, lookup_error))
 | 
			
		||||
        except Exception as rebuild_error:
 | 
			
		||||
            self.logger.error('{} detected in {}, not reloading'.format(
 | 
			
		||||
                rebuild_error.__class__.__name__, plugin_module))
 | 
			
		||||
 | 
			
		||||
            self.server.xt_listeners.restore()
 | 
			
		||||
            self.server.xml_listeners.restore()
 | 
			
		||||
            self.server.commands.restore()
 | 
			
		||||
@@ -118,16 +118,12 @@ class _ListenerManager(_AbstractManager):
 | 
			
		||||
 | 
			
		||||
        super().__init__(server)
 | 
			
		||||
 | 
			
		||||
    def setup(self, module, strict_load=None, exclude_load=None):
 | 
			
		||||
    async def setup(self, module, strict_load=None, exclude_load=None):
 | 
			
		||||
        self.strict_load, self.exclude_load = strict_load, exclude_load
 | 
			
		||||
        for handler_module in self.server.get_package_modules(module):
 | 
			
		||||
            module = sys.modules[handler_module] if handler_module in sys.modules.keys() \
 | 
			
		||||
                else importlib.import_module(handler_module)
 | 
			
		||||
            self.load(module)
 | 
			
		||||
        for handler_module in get_package_modules(module):
 | 
			
		||||
            await self.load(handler_module)
 | 
			
		||||
 | 
			
		||||
        self.logger.debug('Loaded {} listeners'.format(len(self)))
 | 
			
		||||
 | 
			
		||||
    def load(self, module):
 | 
			
		||||
    async def load(self, module):
 | 
			
		||||
        module_name = module.__module__ if isinstance(module, plugins.IPlugin) else module.__name__
 | 
			
		||||
        if not (self.strict_load and module_name not in self.strict_load or
 | 
			
		||||
                self.exclude_load and module_name in self.exclude_load):
 | 
			
		||||
@@ -159,12 +155,6 @@ class _ListenerManager(_AbstractManager):
 | 
			
		||||
                for override in listener_object.overrides:
 | 
			
		||||
                    self[override.packet].remove(override)
 | 
			
		||||
 | 
			
		||||
    def remove(self, module):
 | 
			
		||||
        for handler_id, handler_listeners in self.items():
 | 
			
		||||
            for handler_listener in handler_listeners:
 | 
			
		||||
                if module.__name__ == handler_listener.callback.__module__:
 | 
			
		||||
                    handler_listeners.remove(handler_listener)
 | 
			
		||||
 | 
			
		||||
    @classmethod
 | 
			
		||||
    def is_listener(cls, listener):
 | 
			
		||||
        return issubclass(type(listener), _Listener)
 | 
			
		||||
 
 | 
			
		||||
@@ -1,8 +1,6 @@
 | 
			
		||||
import asyncio
 | 
			
		||||
import os
 | 
			
		||||
import sys
 | 
			
		||||
import pkgutil
 | 
			
		||||
import importlib
 | 
			
		||||
import copy
 | 
			
		||||
 | 
			
		||||
from houdini.spheniscidae import Spheniscidae
 | 
			
		||||
@@ -15,7 +13,6 @@ from logging.handlers import RotatingFileHandler
 | 
			
		||||
 | 
			
		||||
import aioredis
 | 
			
		||||
from aiocache import SimpleMemoryCache, caches
 | 
			
		||||
from watchdog.observers import Observer
 | 
			
		||||
 | 
			
		||||
from houdini.data import db
 | 
			
		||||
from houdini.data.item import ItemCrumbsCollection
 | 
			
		||||
@@ -37,8 +34,6 @@ except ImportError:
 | 
			
		||||
 | 
			
		||||
import houdini.handlers
 | 
			
		||||
import houdini.plugins
 | 
			
		||||
from houdini.events.listener_file_event import ListenerFileEventHandler
 | 
			
		||||
from houdini.events.plugin_file_event import PluginFileEventHandler
 | 
			
		||||
 | 
			
		||||
from houdini.handlers import XTListenerManager, XMLListenerManager
 | 
			
		||||
from houdini.plugins import PluginManager
 | 
			
		||||
@@ -170,11 +165,12 @@ class Houdini:
 | 
			
		||||
            PenguinStringCompiler.setup_default_builder(self.penguin_string_compiler)
 | 
			
		||||
            PenguinStringCompiler.setup_anonymous_default_builder(self.anonymous_penguin_string_compiler)
 | 
			
		||||
 | 
			
		||||
            self.xml_listeners.setup(houdini.handlers, exclude_load='houdini.handlers.login.login')
 | 
			
		||||
            self.xt_listeners.setup(houdini.handlers)
 | 
			
		||||
            await self.xml_listeners.setup(houdini.handlers, exclude_load='houdini.handlers.login.login')
 | 
			
		||||
            await self.xt_listeners.setup(houdini.handlers)
 | 
			
		||||
            await self.dummy_event_listeners.setup(houdini.handlers)
 | 
			
		||||
            self.logger.info('World server started')
 | 
			
		||||
        else:
 | 
			
		||||
            self.xml_listeners.setup(houdini.handlers, 'houdini.handlers.login.login')
 | 
			
		||||
            await self.xml_listeners.setup(houdini.handlers, 'houdini.handlers.login.login')
 | 
			
		||||
            self.logger.info('Login server started')
 | 
			
		||||
 | 
			
		||||
        self.items = await ItemCrumbsCollection.get_collection()
 | 
			
		||||
@@ -218,11 +214,6 @@ class Houdini:
 | 
			
		||||
 | 
			
		||||
        self.permissions = await PermissionCrumbsCollection.get_collection()
 | 
			
		||||
 | 
			
		||||
        handlers_path = os.path.join(os.path.dirname(__file__), 'handlers')
 | 
			
		||||
        plugins_path = os.path.join(os.path.dirname(__file__), 'plugins')
 | 
			
		||||
        self.configure_observers([handlers_path, ListenerFileEventHandler],
 | 
			
		||||
                                 [plugins_path, PluginFileEventHandler])
 | 
			
		||||
 | 
			
		||||
        self.logger.info('Multi-client support is {}'.format(
 | 
			
		||||
            'enabled' if self.config.client['MultiClientSupport'] else 'disabled'))
 | 
			
		||||
        self.logger.info('Listening on {}:{}'.format(self.server_config['Address'], self.server_config['Port']))
 | 
			
		||||
@@ -231,7 +222,7 @@ class Houdini:
 | 
			
		||||
            self.logger.warning('The static key has been changed from the default, '
 | 
			
		||||
                                'this may cause authentication issues!')
 | 
			
		||||
 | 
			
		||||
        self.plugins.setup(houdini.plugins)
 | 
			
		||||
        await self.plugins.setup(houdini.plugins)
 | 
			
		||||
 | 
			
		||||
        async with self.server:
 | 
			
		||||
            await self.server.serve_forever()
 | 
			
		||||
@@ -239,31 +230,3 @@ class Houdini:
 | 
			
		||||
    async def client_connected(self, reader, writer):
 | 
			
		||||
        client_object = self.client_class(self, reader, writer)
 | 
			
		||||
        await client_object.run()
 | 
			
		||||
 | 
			
		||||
    def get_package_modules(self, package):
 | 
			
		||||
        package_modules = []
 | 
			
		||||
 | 
			
		||||
        for importer, module_name, is_package in pkgutil.iter_modules(package.__path__):
 | 
			
		||||
            full_module_name = '{0}.{1}'.format(package.__name__, module_name)
 | 
			
		||||
 | 
			
		||||
            if is_package:
 | 
			
		||||
                subpackage_object = importlib.import_module(full_module_name, package=package.__path__)
 | 
			
		||||
                subpackage_object_directory = dir(subpackage_object)
 | 
			
		||||
 | 
			
		||||
                if houdini.plugins.IPlugin.__name__ in subpackage_object_directory:
 | 
			
		||||
                    package_modules.append(subpackage_object)
 | 
			
		||||
                    continue
 | 
			
		||||
 | 
			
		||||
                sub_package_modules = self.get_package_modules(subpackage_object)
 | 
			
		||||
 | 
			
		||||
                package_modules = package_modules + sub_package_modules
 | 
			
		||||
            else:
 | 
			
		||||
                package_modules.append(full_module_name)
 | 
			
		||||
 | 
			
		||||
        return package_modules
 | 
			
		||||
 | 
			
		||||
    def configure_observers(self, *observer_settings):
 | 
			
		||||
        for observer_path, observer_class in observer_settings:
 | 
			
		||||
            event_observer = Observer()
 | 
			
		||||
            event_observer.schedule(observer_class(self), observer_path, recursive=True)
 | 
			
		||||
            event_observer.start()
 | 
			
		||||
 
 | 
			
		||||
@@ -2,9 +2,8 @@ from abc import ABC
 | 
			
		||||
from abc import abstractmethod
 | 
			
		||||
 | 
			
		||||
import inspect
 | 
			
		||||
import asyncio
 | 
			
		||||
 | 
			
		||||
from houdini import _AbstractManager
 | 
			
		||||
from houdini import _AbstractManager, get_package_modules
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class IPlugin(ABC):
 | 
			
		||||
@@ -37,11 +36,11 @@ class IPlugin(ABC):
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class PluginManager(_AbstractManager):
 | 
			
		||||
    def setup(self, module):
 | 
			
		||||
        for plugin_package in self.server.get_package_modules(module):
 | 
			
		||||
            self.load(plugin_package)
 | 
			
		||||
    async def setup(self, module):
 | 
			
		||||
        for plugin_package in get_package_modules(module):
 | 
			
		||||
            await self.load(plugin_package)
 | 
			
		||||
 | 
			
		||||
    def load(self, module):
 | 
			
		||||
    async def load(self, module):
 | 
			
		||||
        plugin_class, plugin_type = inspect.getmembers(module, is_plugin).pop()
 | 
			
		||||
 | 
			
		||||
        if self.server.server_config['Plugins'] is not True and \
 | 
			
		||||
@@ -51,19 +50,12 @@ class PluginManager(_AbstractManager):
 | 
			
		||||
        plugin_object = plugin_type(self.server)
 | 
			
		||||
        self[module.__name__] = plugin_object
 | 
			
		||||
 | 
			
		||||
        self.server.commands.load(plugin_object)
 | 
			
		||||
        self.server.xt_listeners.load(plugin_object)
 | 
			
		||||
        self.server.xml_listeners.load(plugin_object)
 | 
			
		||||
        await self.server.commands.load(plugin_object)
 | 
			
		||||
        await self.server.xt_listeners.load(plugin_object)
 | 
			
		||||
        await self.server.xml_listeners.load(plugin_object)
 | 
			
		||||
        await self.server.dummy_event_listeners.load(plugin_object)
 | 
			
		||||
 | 
			
		||||
        asyncio.run_coroutine_threadsafe(plugin_object.ready(), self.server.server.get_loop())
 | 
			
		||||
 | 
			
		||||
    def remove(self, module):
 | 
			
		||||
        if module.__name__ in self:
 | 
			
		||||
            del self[module.__name__]
 | 
			
		||||
 | 
			
		||||
            self.server.commands.remove(module)
 | 
			
		||||
            self.server.xt_listeners.remove(module)
 | 
			
		||||
            self.server.xml_listeners.remove(module)
 | 
			
		||||
        await plugin_object.ready()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def is_plugin(plugin_class):
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user