Comment trouver tous les modules enfants en Python?
-
06-09-2019 - |
Question
Il est assez trivial en Python pour importer un module « enfant » dans un autre module et la liste de ses attributs, il devient un peu plus difficile quand vous voulez importer tous modules enfant.
Je construis une bibliothèque d'outils pour une application 3D existante. Chaque outil a ses propres menus de l'élément de menu et sous. Je voudrais que l'outil soit chargé de créer ses propres menus que beaucoup d'entre eux changent en fonction du contexte et des modèles. Je voudrais que mon module de base pour être en mesure de trouver tous les modules enfant et vérifier une fonction create_menu()
et l'appeler si elle le trouve.
Quelle est la meilleure façon de découvrir tous les modules enfant?
La solution
dir () et imp Module
Autres conseils
Je pense que la meilleure façon de faire ce genre de chose plugin utilise entry_points
et l'API pour les interroger .
Quand j'étais genre et la programmation en Python juste de commencer, je l'ai écrit pour mon robot modulaire IRC:
# Load plugins
_plugins = []
def ifName(name):
try:
return re.match('([^_.].+)\.[^.]+', a).group(1)
except:
return None
def isValidPlugin(obj):
from common.base import PluginBase
try:
if obj.__base__ == PluginBase:
return True
else:
return False
except:
return False
plugin_names = set(ifilter(lambda a: a!=None, [ifName(a) for a in os.listdir(os.path.join(os.getcwd(), 'plugins'))]))
for plugin_name in plugin_names:
try:
plugin = __import__('plugins.'+plugin_name, fromlist=['plugins'])
valid_plugins = filter(lambda a: isValidPlugin(a), [plugin.__getattribute__(a) for a in dir(plugin)])
_plugins.extend(valid_plugins)
except Exception, e:
logger.exception('Error loading plugin %s', plugin_name)
# Run plugins
_plugins = [klass() for klass in _plugins]
Il est pas sécurisé ou « bonne » façon, mais peut-être que nous allons être utile quand même. Il est très ancien code si s'il vous plaît ne me battez pas.
La solution ci-dessus traversant le système de fichiers pour trouver des sous-modules est ok aussi longtemps que vous mettre en œuvre tous les plug-in en tant que module à base de système de fichiers.
Une façon plus souple serait une liste de plug-in explicite dans votre module principal, et ont tous les plug-in (si un module créé par fichier, dynamiquement, ou même instance d'une classe) s'ajoutant à cette liste explicitement. Peut-être via une fonction registerPlugin.
Rappelez-vous:. « Explicite est mieux que implicite » fait partie du zen de python
Vous pouvez glob
bing le répertoire:
import os
import glob
modules = glob.glob(os.path.join('/some/path/to/modules', '*.py'))
Ensuite, vous pouvez essayer de les importer:
checked_modules
for module in modules:
try:
__import__(module, globals(), locals()) # returns module object
except ImportError:
pass
else:
checked_modules.append(module)