我编写了一个 Python 脚本来执行一些如下的 bash 脚本:
cmd = subprocess.Popen(['bash', 'script.sh'])
这样,尽管我没有使用 设置执行权限,它仍会执行脚本chmod
。我也可以在终端中写入bash script.sh
,其工作原理相同。我知道可以通过在脚本前面添加点斜杠来执行脚本,./
就像这样./script.sh
。
那么,我应该在 Python 脚本中使用哪种方法?为什么?
答案1
首先,关于 中的点./script.sh
,这表示可以在工作目录中找到 script.sh,它的意思类似于“在此目录中查找 script.sh”。这被称为点斜线,解释得很好这里。
我看到三种选择:
如果你打算限制文件仅在用户的当前的当他运行 Python 脚本时,如果要将工作目录设置为工作目录,则使用点斜杠。但是,这似乎不是最好的主意:大多数情况下它会导致异常。
如果你打算限制你的 shell 脚本仅在与 Python 脚本位于同一目录中时运行,那么你需要找到你的 Python 脚本的目录并将其作为脚本名称的前缀。
如果您打算将您的 shell 脚本放在 PATH 的其他位置,请不要使用点斜杠。
现在,将“bash”作为参数发送到 Popen 构造函数似乎更像是个人喜好问题。如果您不想将其作为参数发送,则需要添加舍邦对于 shell 脚本,#!/bin/bash
例如和您需要为其添加执行权限。这些都是完全可以接受的做法。
这样做的一个好处是,如果以后更改 shell 解释器,则不需要在不知道多少个 Python 脚本中修改对该脚本的每次调用。
你也可以像这样调用脚本:
cmd = subprocess.call('script.sh')
# or
cmd = subprocess.call(sdir + 'script.sh')
# Where sdir stands for the script's directory,
# which you would need to find before, as in option #2.
笔记:
即使你的脚本在没有shebang的情况下正常运行(在这种情况下它几乎肯定会被执行dash 而不是 bash在基于 Debian 的发行版上),当像这样从 python 调用它时,它将失败并引发 OSError 异常,errno 为 8(errno.ENOEXEC)。