From d891e3f2ee8f0bf474c13b6a4542cde83a74fff0 Mon Sep 17 00:00:00 2001 From: Jan Vcelak Date: Tue, 9 Oct 2012 15:49:17 +0200 Subject: [PATCH] plugins, monitors: inherit from PluginLoader --- tuned/application.py | 2 +- tuned/monitors/repository.py | 25 ++++++++-------- tuned/plugins/__init__.py | 1 - tuned/plugins/exceptions.py | 22 --------------- tuned/plugins/repository.py | 51 +++++++++++++-------------------- tuned/units/unit.py | 2 +- tuned/utils/__init__.py | 1 - tuned/utils/plugin_loader.py | 44 +++++++++++++++++++++++++++++ tuned/utils/pluginloader.py | 55 ------------------------------------ 9 files changed, 78 insertions(+), 125 deletions(-) delete mode 100644 tuned/plugins/exceptions.py create mode 100644 tuned/utils/plugin_loader.py delete mode 100644 tuned/utils/pluginloader.py diff --git a/tuned/application.py b/tuned/application.py index 8ab87d4..fb5bb5b 100644 --- a/tuned/application.py +++ b/tuned/application.py @@ -38,8 +38,8 @@ class Application(object): self._storage_provider = storage.PickleProvider() self._storage_factory = storage.Factory(self._storage_provider) - self._plugins_repository = plugins.Repository(self._storage_factory) self._monitors_repository = monitors.Repository() + self._plugins_repository = plugins.Repository(self._storage_factory, self._monitors_repository) self._unit_manager = units.Manager(self._plugins_repository, self._monitors_repository) self._profile_loader = profiles.Loader() diff --git a/tuned/monitors/repository.py b/tuned/monitors/repository.py index 8645743..66dc84f 100644 --- a/tuned/monitors/repository.py +++ b/tuned/monitors/repository.py @@ -1,34 +1,33 @@ -import tuned.patterns -import tuned.utils import tuned.logs +import tuned.monitors +from tuned.utils.plugin_loader import PluginLoader log = tuned.logs.get() __all__ = ["Repository"] -class Repository(object): +class Repository(PluginLoader): + def __init__(self): super(self.__class__, self).__init__() - self._loader = tuned.utils.PluginLoader("tuned.monitors", "monitor_", tuned.monitors.Monitor) self._monitors = set() + def _set_loader_parameters(self): + self._namespace = "tuned.monitors" + self._prefix = "monitor_" + self._interface = tuned.monitors.Monitor + def create(self, plugin_name, devices): log.debug("creating monitor %s" % plugin_name) - # TODO: exception handling - monitor_cls = self._loader.load(plugin_name) + monitor_cls = self.load_plugin(plugin_name) monitor_instance = monitor_cls(devices) - - if not monitor_cls in self._monitors: - self._monitors.add(monitor_cls) + self._monitors.add(monitor_instance) return monitor_instance def delete(self, monitor): assert isinstance(monitor, self._loader.interface) monitor.cleanup() - - log.info(monitor._instances) - if len(monitor._instances) == 0: - self._monitors.remove(type(monitor)) + self._monitors.remove(monitor) def update(self): for monitor in self._monitors: diff --git a/tuned/plugins/__init__.py b/tuned/plugins/__init__.py index 841c91d..cb96099 100644 --- a/tuned/plugins/__init__.py +++ b/tuned/plugins/__init__.py @@ -1,2 +1 @@ from repository import * -from exceptions import * diff --git a/tuned/plugins/exceptions.py b/tuned/plugins/exceptions.py deleted file mode 100644 index e4b3737..0000000 --- a/tuned/plugins/exceptions.py +++ /dev/null @@ -1,22 +0,0 @@ -import tuned.exceptions - -class LoadPluginException(tuned.exceptions.TunedException): - def __init__(self, plugin_name, inner_exception = None): - super(self.__class__, self).__init__() - self._plugin_name = plugin_name - self._inner_exception = inner_exception - - @property - def plugin_name(self): - return self._plugin_name - - @property - def inner_exception(self): - return self._inner_exception - - def __str__(self): - message = "Unable to load plugin '%s'" % self._plugin_name - if self._inner_exception is not None: - message += " (%s)" % str(self._inner_exception) - - return message[0].lower() + message[1:] diff --git a/tuned/plugins/repository.py b/tuned/plugins/repository.py index 0f4a5ee..6c9047a 100644 --- a/tuned/plugins/repository.py +++ b/tuned/plugins/repository.py @@ -1,49 +1,38 @@ -import base -import exceptions - +from tuned.utils.plugin_loader import PluginLoader +import tuned.plugins.base import tuned.logs -import tuned.utils log = tuned.logs.get() __all__ = ["Repository"] -class Repository(object): +class Repository(PluginLoader): - __slots__ = ["_loader", "_plugins", "_storage_factory"] - - def __init__(self, storage_factory): + def __init__(self, storage_factory, monitor_repository): super(self.__class__, self).__init__() - self._loader = tuned.utils.PluginLoader("tuned.plugins", "plugin_", base.Plugin) self._plugins = set() self._storage_factory = storage_factory + self._monitor_repository = monitor_repository - def create(self, monitor_repository, plugin_name, devices, options): + def _set_loader_parameters(self): + self._namespace = "tuned.plugins" + self._prefix = "plugin_" + self._interface = tuned.plugins.base.Plugin + + def create(self, plugin_name, devices, options): log.debug("creating plugin %s" % plugin_name) - try: - plugin_cls = self._loader.load(plugin_name) - plugin_instance = plugin_cls(monitor_repository, self._storage_factory, devices, options) - self._plugins.add(plugin_instance) - return plugin_instance - except Exception as exception: - plugin_exception = exceptions.LoadPluginException(plugin_name, exception) - raise plugin_exception + plugin_cls = self.load_plugin(plugin_name) + plugin_instance = plugin_cls(self._monitor_repository, self._storage_factory, devices, options) + self._plugins.add(plugin_instance) + return plugin_instance def tunable_devices(self, plugin_name): - try: - plugin_cls = self._loader.load(plugin_name) - return plugin_cls.tunable_devices() - except Exception as e: - plugin_exception = exceptions.LoadPluginException(plugin_name, e) - raise plugin_exception + plugin_cls = self.load_plugin(plugin_name) + return plugin_cls.tunable_devices() def is_supported(self, plugin_name): - try: - plugin_cls = self._loader.load(plugin_name) - return plugin_cls.is_supported() - except Exception as e: - plugin_exception = exceptions.LoadPluginException(plugin_name, e) - raise plugin_exception + plugin_cls = self.load_plugin(plugin_name) + return plugin_cls.is_supported() def do_static_tuning(self): for plugin in self._plugins: @@ -53,7 +42,7 @@ class Repository(object): plugin.execute_commands() def delete(self, plugin): - assert isinstance(plugin, self._loader.interface) + assert isinstance(plugin, self._interface) log.debug("removing plugin %s" % plugin) plugin.cleanup_commands() plugin.cleanup() diff --git a/tuned/units/unit.py b/tuned/units/unit.py index efa3536..19715be 100644 --- a/tuned/units/unit.py +++ b/tuned/units/unit.py @@ -21,7 +21,7 @@ class Unit(object): self._name = name (devices, options) = self._get_plugin_params(config) - self._plugin = self._plugin_repository.create(monitor_repository, plugin_name, devices, options) + self._plugin = self._plugin_repository.create(plugin_name, devices, options) @property def name(self): diff --git a/tuned/utils/__init__.py b/tuned/utils/__init__.py index 0e9f0aa..b98594f 100644 --- a/tuned/utils/__init__.py +++ b/tuned/utils/__init__.py @@ -17,4 +17,3 @@ from signals import * from daemon import * -from pluginloader import * diff --git a/tuned/utils/plugin_loader.py b/tuned/utils/plugin_loader.py new file mode 100644 index 0000000..aa80e20 --- /dev/null +++ b/tuned/utils/plugin_loader.py @@ -0,0 +1,44 @@ +import tuned.logs + +__all__ = ["PluginLoader"] + +log = tuned.logs.get() + +class PluginLoader(object): + __slots__ = ["_namespace", "_prefix", "_interface"] + + def _set_loader_parameters(self): + """ + This method has to be implemented in child class and should + set _namespace, _prefix, and _interface member attributes. + """ + raise NotImplementedError() + + def __init__(self): + super(PluginLoader, self).__init__() + + self._set_loader_parameters() + assert type(self._namespace) is str + assert type(self._prefix) is str + assert type(self._interface) is type and issubclass(self._interface, object) + + def load_plugin(self, plugin_name): + assert type(plugin_name) is str + module_name = "%s.%s%s" % (self._namespace, self._prefix, plugin_name) + return self._get_class(module_name) + + def _get_class(self, module_name): + log.debug("loading module %s" % module_name) + module = __import__(module_name) + path = module_name.split(".") + path.pop(0) + + while len(path) > 0: + module = getattr(module, path.pop(0)) + + for name in module.__dict__: + cls = getattr(module, name) + if type(cls) is type and issubclass(cls, self._interface): + return cls + + raise ImportError("Cannot find the plugin class.") diff --git a/tuned/utils/pluginloader.py b/tuned/utils/pluginloader.py deleted file mode 100644 index 6ea80ae..0000000 --- a/tuned/utils/pluginloader.py +++ /dev/null @@ -1,55 +0,0 @@ -import tuned.logs - -__all__ = ["PluginLoader"] - -log = tuned.logs.get() - -class PluginLoader(object): - __slots__ = ["_namespace", "_prefix", "_interface"] - - def __init__(self, namespace, prefix, interface): - super(self.__class__, self).__init__() - - assert type(namespace) is str - assert type(prefix) is str - assert type(interface) is type and issubclass(interface, object) - - self._namespace = namespace - self._prefix = prefix - self._interface = interface - - @property - def namespace(self): - return self._namespace - - @property - def prefix(self): - return self._prefix - - @property - def interface(self): - return self._interface - - def load(self, plugin_name): - assert type(plugin_name) is str - - module_name = "%s.%s%s" % (self._namespace, self._prefix, plugin_name) - module = self._get_module(module_name) - return module - - def _get_module(self, module_name): - log.debug("loading module %s" % module_name) - module = __import__(module_name) - path = module_name.split(".") - path.pop(0) - - while len(path) > 0: - module = getattr(module, path.pop(0)) - - for name in module.__dict__: - obj = getattr(module, name) - if type(obj) is type and issubclass(obj, self._interface): - return obj - - raise ImportError("Cannot find the plugin class.") -