运行多个shell命令并等待结果的Python脚本

2024-04-29 02:51:30 发布

您现在位置:Python中文网/ 问答频道 /正文

我正在尝试编写一个python包装器来构建一些软件。我需要用不同的配置自动构建它数百次,这意味着我不能仅仅autogen.sh ; ./configure ; make ; make install。我使用的一些配置需要运行一个脚本,该脚本有条件地设置一些环境变量。我想要的是能够做这样的事情:

command = './autogen.sh'
ret = subprocess.call(command.split())
if ret != 0:
  sys.exit(ret)

command = './script.sh ; ./configure <configure-flags>'
ret = subprocess.call(command.split())
if ret != 0:
  sys.exit(ret)

command = 'make'
ret = subprocess.call(command.split())
if ret != 0:
  sys.exit(ret)

command = 'make install'
ret = subprocess.call(command.split())
if ret != 0):
  sys.exit(ret)

我遇到的问题是,script.sh中设置的环境变量没有为configure保留。我在Sending multiple commands to a bash shell which must share an environment中看到了一个部分解决方案,但这涉及到将命令刷新到stdin并轮询一个结果,当您有一个很长的makefile(我的需要大约10-20分钟)时,这个结果实际上不起作用,而且它也没有给您返回值,我需要知道构建是否成功。你知道吗

有人知道更好的方法吗?你知道吗


Tags: install脚本makeifconfigureshsysexit
2条回答

如果有一个脚本设置了以后要访问的变量,则必须对其进行源代码设置(类似于其他语言所称的“include”)。你知道吗

而不是

command = './script.sh ; ./configure <configure-flags>'
ret = subprocess.call(command.split())

你能做到的

command = ["bash", "-c", "source script.sh; ./configure"]
subprocess.call(command)

这里的基本问题是,环境变量只能“向下”(从父到子)复制,而不能“向上”(从子到父)。您的python脚本是父级脚本。它运行一个shell命令,因此它是一个子命令;shell运行更多命令,这些命令是shell的子命令(因此也是Python进程的孙子命令)。你知道吗

要使环境变量保持不变,您需要以某种方式向上导入它们。具体怎么办取决于你。一种常见的技术(在shell脚本和Python中都使用)是让导出器打印它想要设置的值,然后让shell或Python进程读取该输出并进行设置。(我知道你链接的帖子就是这么做的。)

例如,子进程可能会打印:

CONFIG_PATH=/path/to/config/file

(或与添加export相同)然后外壳将简单地eval这个。这意味着大量的信任:例如,如果子进程打印rm -rf /,该怎么办?可以在执行输出之前将规则(例如,正则表达式匹配)应用于输出,甚至可以手动(或自动)解析输出,但在验证步骤之后才执行结果。你知道吗

另一种方法是将配置写入文件,并让父级读取该文件。这几乎是相同的技术,但是使用一个通信仓库的文件,而不是摆弄stdin和stdout。它还有几个问题(命名文件,以及知道何时读取文件)。你知道吗

(当然,有许多构建和/或测试框架是用Python编写的。我不打算推荐任何具体的,因为我没有太多的经验。)

相关问题 更多 >