Como encontrar todos os módulos de criança em Python?
-
06-09-2019 - |
Pergunta
Embora seja bastante trivial em Python para importar um módulo de "criança" em outro módulo e lista de seus atributos, ele se torna um pouco mais difícil quando você deseja importar todas módulos de criança.
Estou construindo uma biblioteca de ferramentas para uma aplicação 3D existente. Cada ferramenta tem seus próprios menus de itens de menu e sub. Eu gostaria que a ferramenta seja responsável por criar os seus próprios menus como muitos deles mudam com base no contexto e modelos. Eu gostaria de minha módulo base para ser capaz de encontrar todos os módulos de criança e verificar se há uma função create_menu()
e chamá-lo se ele encontra-lo.
O que é a maneira mais fácil de descobrir todos os módulos de criança?
Solução
Outras dicas
Eu acho que a melhor maneira de fazer esse tipo de plugin de coisa está usando entry_points
eo API para consultar-lhes .
Quando eu era um tipo e de programação apenas começando em Python Eu escrevi isso para o meu bot IRC modular:
# 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]
Não é seguro ou caminho "certo", mas talvez vamos ser útil, no entanto. É de muito Código de idade, então por favor não me bater.
A solução acima atravessando o sistema de arquivos para encontrar submódulos é ok, desde que você implementar todos os plug-in como um módulo de base do sistema de arquivos.
A forma mais flexível seria uma lista de plugins explícita no seu módulo principal, e tem todo o plug-in (se um módulo criado por arquivo, de forma dinâmica, ou instância, mesmo de uma classe) somando-se a essa lista explicitamente. Talvez através de uma função registerPlugin.
Lembre-se:. "Explícito é melhor do que implícito" é parte do zen de python
Você pode tentar glob
bing o diretório:
import os
import glob
modules = glob.glob(os.path.join('/some/path/to/modules', '*.py'))
Então você pode tentar importá-los:
checked_modules
for module in modules:
try:
__import__(module, globals(), locals()) # returns module object
except ImportError:
pass
else:
checked_modules.append(module)