Index: channels/__init__.py ================================================================== --- channels/__init__.py +++ channels/__init__.py @@ -44,11 +44,11 @@ # Only export plugin classes __all__ = [ "GenericChannel", "ChannelPlugin", "use_rx", "entity_decode", "strip_tags", "nl", "unhtml", "to_int" ] -#__path__.insert(0, "plugins")#conf.plugin_dir) +__path__.insert(0, conf.dir + "/plugins") # generic channel module --------------------------------------- class GenericChannel(object): Index: config.py ================================================================== --- config.py +++ config.py @@ -367,8 +367,8 @@ # tie in pluginconf.* pluginconf.log_WARN = log.WARN pluginconf.log_ERR = log.ERR pluginconf.module_base = "config" -pluginconf.plugin_base = ["channels", "plugins", conf.share+"/channels", conf.dir+"/plugins"] +pluginconf.plugin_base = ["channels", "plugins"]#, conf.share+"/channels", conf.dir+"/plugins"] Index: pluginconf.py ================================================================== --- pluginconf.py +++ pluginconf.py @@ -2,11 +2,11 @@ # api: python # type: handler # category: io # title: Plugin configuration # description: Read meta data, pyz/package contents, module locating -# version: 0.5 +# version: 0.6 # priority: core # doc: http://fossil.include-once.org/streamtuner2/wiki/plugin+meta+data # config: - # # Provides plugin lookup and meta data extraction utility functions. @@ -59,11 +59,24 @@ # ‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾ # Probes a new plugins` depends: list against installed base modules. # Very crude and tied to streamtuner2 base names. # # +# Generally this scheme concerns itself more with plugin basenames. +# That is: module scripts in a package like `ext.plg1` and `ext.plg2`. +# It can be initialized by injecting the plugin-package basename into +# plugin_base = []. The associated paths will be used for module +# lookup via pkgutil.iter_modules(). +# +# And a central module can be extended with new lookup locations best +# by attaching new locations itself via module.__path__ + ["./local"] +# for example. # +# Plugin loading thus becomes as simple as __import__("ext.local"). +# The attachaed plugin_state config dictionary in most cases can just +# list module basenames, if there's only one set to manage. + import sys import os import re @@ -80,17 +93,16 @@ # Injectables # ‾‾‾‾‾‾‾‾‾‾‾ log_ERR = lambda *x:None -# File lookup relation for get_data(), should name a top-level module/package +# File lookup relation for get_data(), should name a top-level package. module_base = "config" -# Package names or base paths for module_list() and plugin_meta() lookups +# Package/module names for module_list() and plugin_meta() lookups. +# All associated paths will be scanned for module/plugin basenames. plugin_base = ["channels"] - # [conf.share+"/channels", conf.dir+"/plugins"]) - # Resource retrieval # ‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾ @@ -114,16 +126,24 @@ # Plugin name lookup # ‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾ # Search through ./plugins/ (and other configured plugin_base -# names or paths) and get module basenames. +# names → paths) and get module basenames. # -def module_list(extra_base=[]): +def module_list(extra_paths=[]): + + # Convert plugin_base package names into paths for iter_modules + paths = [] + for mp in plugin_base: + if sys.modules.get(mp): + paths += sys.modules[mp].__path__ + elif os.path.exists(mp): + paths.append(mp) # Should list plugins within zips as well as local paths - ls = pkgutil.iter_modules(plugin_base + extra_base) + ls = pkgutil.iter_modules(paths + extra_paths) return [name for loader,name,ispkg in ls] # Plugin => meta dict