我创建了一个导入钩子(基于PEP 302),以从数据库中动态加载 python 字节码(编译后的 python 代码)。
import dyn_imports.test #@UnresolvedImport
这很好用,但是如果我更改模块并重新加载模块,模块会重新加载,但我看不到更改。
这就是我创建字节码的方式:
code_object = compile(db.Text(dyn.py_source).encode(), dyn.name.encode(), 'exec')
key_name = 'dyn_imports.' + name
dynmod = models.Dynmods(key_name = key_name, name = key_name, bytecode = db.Blob(marshal.dumps(code_object)))
dynmod.put()
reload(sys.modules[key_name]) # reload the updated code
reload() 执行导入钩子的 load_module 部分。
这是导入钩子类中 load_module 函数的简化版本:
def load_module(self, mod_name):
mod = imp.new_module(mod_name)
mod.__loader__ = self
dynmod = models.Dynmods.get_by_key_name(mod_name) # load from DB
mod.__file__ = mod_name
exec marshal.loads(db.Blob(dynmod.bytecode)) in mod.__dict__
sys.modules[mod_name] = mod
return mod
当我关闭实例时,它工作正常。
更新:我还使用 py 源代码而不是字节码测试了导入加载器。这也不起作用。我已经在开发服务器上完成了大部分测试。
我之前创建了一个 Jinja2模块加载器,它从数据存储区加载 Jinja 编译的模板(= py 源)。当我重新创建 Jinja 环境并从 sys.modules 中删除模块(已编译的模板)时,会重新加载新模块,而无需重新启动实例。那么我在这里做错了什么?