Я работаю над pypreprocessor, который является препроцессором, который принимает директивы c-style, и я смог сделать это работать как традиционный препроцессор (он самозатягивается и выполняет постпроцессированный код "на лету" ), за исключением того, что он прерывает импорт библиотеки.
Проблема заключается в следующем: препроцессор запускает файл, обрабатывает его, выдает во временный файл и exec() временный файл. Библиотеки, которые импортируются, нужно обрабатывать немного иначе, потому что они не выполняются, а скорее загружаются и становятся доступными для модуля вызывающего абонента.
Что мне нужно сделать, это: Прервать импорт (поскольку препроцессор выполняется в середине импорта), загружать постобрабованный код в качестве tempModule и заменять исходный импорт tempModule, чтобы обмануть вызывая script с импортом, полагая, что tempModule является исходным модулем.
Я искал везде и до сих пор и не имею решения.
Этот вопрос о переполнении стека является самым близким, который я видел до сих пор, чтобы дать ответ: Переопределить пространство имен в Python
Вот что у меня есть.
# Remove the bytecode file created by the first import
os.remove(moduleName + '.pyc')
# Remove the first import
del sys.modules[moduleName]
# Import the postprocessed module
tmpModule = __import__(tmpModuleName)
# Set first module reference to point to the preprocessed module
sys.modules[moduleName] = tmpModule
moduleName - это имя исходного модуля, а tmpModuleName - это имя файла постпроцессированного кода.
Странная часть этого решения по-прежнему работает совершенно нормально, как если бы первый модуль был загружен нормально; если вы не удалите последнюю строку, то вы получите сообщение об ошибке, не найденной.
Надеюсь, что кто-то из Qaru знает намного больше об импорте, чем я, потому что этот имеет меня в тупике.
Примечание. Я буду награждать только решение или, если это невозможно в Python; лучшее, самое подробное объяснение, почему это не невозможно.
Обновление: для любого, кто заинтересован, вот рабочий код.
if imp.lock_held() is True:
del sys.modules[moduleName]
sys.modules[tmpModuleName] = __import__(tmpModuleName)
sys.modules[moduleName] = __import__(tmpModuleName)
Часть "imp.lock_held" определяет, загружается ли модуль в виде библиотеки. Следующие строки делают все остальное.