Как работает перезагрузка модуля в python3.7? - PullRequest
0 голосов
/ 09 февраля 2019

Как перезагрузка модуля работает в python 3.7.1?

Настройка и сводка

Я использую python 3.7.1 в Linux.Я занимаюсь разработкой модуля C, и было бы очень удобно перезагрузить модуль после его изменения.Я следовал Как выгрузить (перезагрузить) модуль Python? , но я не могу заставить его работать в этой среде.

Для демонстрации своей проблемы я написал простой модуль на основена примере СПАМА в учебнике, который возвращает время сборки модуля.Он никогда не будет перезагружен.

Код

Реализация - пример спама из учебника.Он имеет единственную функцию hello, которая возвращает время сборки:

return Py_BuildValue("s", __TIME__);

Я компилирую и загружаю с помощью следующего скрипта Python:

import os
import helloworld
print(helloworld.hello('test'))
os.system("touch helloworld.c")
os.system("python3 setup.py build")
os.system("python3 setup.py install --user")
from importlib import reload
helloworld=reload(helloworld)
print(helloworld.hello('test'))

Модуль импортирован, основной файлкоснулся, он компилируется и устанавливается, а затем перезагружается.

Вывод

Модуль должен показывать новое время компиляции после перезагрузки, но вывод не меняется (я пропускаю некоторые сообщения отладки, выходные данные - первая / последняя строка, 08:04:20):

python driver.py
08:04:20
running build
running build_ext
building 'helloworld' extension
gcc ...
running install
running build
running build_ext
running install_lib
copying build/lib.linux-x86_64-3.7/helloworld.cpython-37m-x86_64-linux-gnu.so -> /home/wuebbel/.local/lib/python3.7/site-packages
running install_egg_info
Removing /home/wuebbel/.local/lib/python3.7/site-packages/HelloWorld-2.1-py3.7.egg-info
Writing /home/wuebbel/.local/lib/python3.7/site-packages/HelloWorld-2.1-py3.7.egg-info
08:04:20

Повторный запуск скрипта загружает правильный модуль и показывает новое время:

wuebbel@02e267406db3:~/Projekte/Mandelbrot Demos/helloworld$ python driver.py
08:16:58
...
08:16:58

Itкажется, что мой модуль никогда не перезагружается.Как правильно это сделать?

1 Ответ

0 голосов
/ 09 февраля 2019

У меня есть сомнения по поводу возможности перезагрузки модуля, содержащего скомпилированный код, прочитав этот ответ: https://stackoverflow.com/a/48814213/6451573, что говорит о том, что PEP 489 изменил перезагрузку модуля (между питоном 3.6 и 3.7), возможно«разрыв» перезагрузки разделяемой библиотеки.

Из-за ограничений в загрузке разделяемой библиотеки (как dlopen в POSIX, так и в LoadModuleEx в Windows), как правило, невозможно загрузить измененную библиотеку после ее изменения на диске..

Это может объяснить проблему, с которой вы столкнулись.

Если это рабочий случай, я предлагаю, чтобы у вас была главная программа на Python, которая создает пакет, а затем используйте отдельныйPython обрабатывает его для загрузки.

subprog.py:

import helloworld
print(helloworld.hello('test'))

master.py

import os,subprocess,sys
def runit():
   subprocess.run([sys.executable,os.path.join(os.path.dirname(__file__),"subprog.py")])

runit()

os.system("touch helloworld.c")
os.system("python3 setup.py build")
os.system("python3 setup.py install --user")

runit()

Использование sys.executable гарантирует, что для запуска будет использоваться тот же исполняемый файл pythonосновной процесс Python и подпроцесс, так что это более прозрачно.

...