我正在研究用Python编写的包装器脚本。包装器应该根据系统状态选择另一个Python脚本并执行它(使用绝对路径)。无需返回父脚本。
应该注意的是,我无法控制正在运行的脚本。他们可以使用__name__
检查,访问sys.argv
,如果脚本直接运行,它们的行为都应该如此。
现在,我正在使用os.execl()
:
import os, sys
# ...
os.execl(sys.executable, sys.executable, new_script, *sys.argv[1:])
但我至少可以解决三个问题:
python -v wrapper
在重新执行时停止冗长); sys.executable
有用,文档说:
如果Python无法检索其可执行文件的真实路径,
sys.executable
将为空字符串或None
。
os.execl
来解决所有问题。到目前为止,我可以说:
execfile()
可能会有效,但它已在Python3中删除并手动重新实现它AFAICS很难看(因为编码问题)。我不确定execfile()
会有什么其他影响; imp.load_module()
可能会有效,但它有点hacky并在Python3.3中被弃用。它也可能会遇到Python3编码问题。您建议我使用哪种解决方案?
答案 0 :(得分:1)
我只会使用execfile()
代替imp.load_module()
。虽然控制权将返回执行脚本,但一个很大的优点是,引用文档:
它与import语句的不同之处在于它不使用 模块管理 - 它无条件地读取文件而不是 创建一个新模块。
这意味着脚本文件可以在任何地方,可以具有任何(或没有)文件扩展名,并且不会浪费资源执行与模块导入相关的任务。
这样做会自动完成或避免您想要的事情:
sys.executable
答案 1 :(得分:-1)
你尝试过这样的事吗?
### wrapped script ###
import sys
print("__name__: {0}\nsys.argv: {1}".format(__name__, sys.argv))
### wrapper script ###
import builtins, sys
my_script = "wrapped_script.py"
print("Executing the wrapped script...")
sys.argv[0] = my_script
with open(my_script, 'r') as fd:
for line in fd:
exec(line)
结果:
$ python3 wrapped_script.py --foo --bar=quux
__name__: __main__
sys.argv: ['wrapped_script.py', '--foo', '--bar=quux']
$ python3 wrapper.py --foo --bar=quux
Executing the wrapped script...
__name__: __main__
sys.argv: ['wrapped_script.py', '--foo', '--bar=quux']