Хорошо, опираясь на эту идею:
Ответ Остина Филипа
# services/__init__.py
from .service1 import service1
from .service2 import service2
...
services = [service1, service2, ...]
__all__ = ['services']
И идея специально раскрытых методов и модулей из Factory Pattern , упомянутый в этого ответа , я придумал очень хакерское решение, которое работает без загромождения глобального пространства имен (еще одна вещь, которую критиковал @Austin Philp).
Решение
Мне пришла идея реализовать в каждом модуле метод, который ничего не делает, кроме создания экземпляра указанного модуля, и каждый модуль упоминается в services/__init__.py
:
#services/__init__.py
from .service1 import service1
from .service2 import service2
__all__=["service1", "service2", ...]
#services/service1.py
class service1(object):
def __init__(self, input):
...
...
#
def create_instance(input):
return service1(input) # create the object and return it.
Затем в main.py я просто делаю это (это очень хакерски, но это работает)
#main.py
import services
import sys
# use the __all__ method to get module names. actually
for name in services.__all__:
service = sys.modules[f'services.{name}'].create_instance( input )
# do whatever with service
Таким образом, я могу просто счастливо делать все, что нужно, не загромождая глобальное пространство имен, но все же перебирая или даже перебирая индивидуально вызывая модули. Единственное, что мне нужно отредактировать, чтобы добавить / удалить модуль, - это еще одна запись в переменной __all__
внутри services/__init__.py
. Это даже избавило от необходимости иметь массив serv_arr
, потому что services.__all__
уже имеет все интересующие меня имена и будет иметь ту же длину, что и используемые модули.