Вызов точки входа setuptools из библиотеки

#python #setuptools #packaging

#python #setuptools #упаковка

Вопрос:

У меня есть проект Python (3.5) на основе setuptools с несколькими сценариями в качестве точек входа, похожими на следующие:

 entry_points={
    'console_scripts': [
        'main-prog=scripts.prog:main',
        'prog-viewer=scripts.prog_viewer:main'
    ]}
  

Итак, предполагается, что должен быть основной скрипт, запускаемый как main-prog и вспомогательный скрипт prog-viewer (который выполняет некоторые функции Tk).

Проблема в том, что я хочу иметь возможность запускать prog-viewer Popen подпроцесс из main-prog (или, скорее, формировать свою библиотеку), не прибегая к ручному определению путей, а затем адаптироваться к другой ОС. Кроме того, что мне делать, если мой PATH содержит скрипт с тем же именем, который не принадлежит моей библиотеке? Могу ли я указать своей программе Popen(scripts.prog_viewer:main) ?

Комментарии:

1. Разве вы не можете просто сделать from scripts.prog_viewer import main; main() ?

2. @cel Однако мне нужно запустить его в подпроцессе.

Ответ №1:

Вы могли бы запустить команду python с Popen, например:

 Popen('python -c "from scripts.prog import main; main()"', shell=True)
  

Комментарии:

1. Я бы спал лучше, если бы знал, что это правильный способ сделать это, а не взлом, на который это похоже. 🙂

2. @Debilski Почему вы называете это взломом? Если вы хотите запустить его с помощью модуля подпроцесса и не хотите напрямую вызывать точку входа, то это правильный путь.

3. Без обид, я просто подумал бы, что что-то подобное уже есть в каком-то модуле setuptools или pkg_resources. Кроме того, если я когда-нибудь изменю точку входа, мне понадобится поиск этой строки. (И гораздо менее понятно, что выполняется, если просто посмотреть на таблицу процессов; это также может усложнить отладку, потому что argv [0] тогда является ‘-c’ вместо сценария.)

4. Popen([sys.executable, '-m', 'scripts.prog']) на самом деле может быть более приятной альтернативой. Однако не уверен в предостережениях.

Ответ №2:

Вы могли бы использовать модуль многопроцессорной обработки, который также будет запускать ваш код как подпроцесс. например,

 from multiprocessing import Process
from scripts.prog import main
# or 
# from pkg_resources import load_entry_point
# main = load_entry_point('your-package', 'console_scripts', 'main_prog')

p = Process(main)
p.start()
p.join()