繁体   English   中英

这是在Python中运行shell脚本的正确方法吗?

[英]Is this the right way to run a shell script inside Python?

import subprocess
retcode = subprocess.call(["/home/myuser/go.sh", "abc.txt", "xyz.txt"])

当我运行这两行时,我会这样做吗?:

/home/myuser/go.sh abc.txt xyz.txt

为什么我会收到此错误? 但是当我正常运行go.sh时,我没有得到那个错误。

File "/usr/lib/python2.6/subprocess.py", line 480, in call
    return Popen(*popenargs, **kwargs).wait()
  File "/usr/lib/python2.6/subprocess.py", line 633, in __init__
    errread, errwrite)
  File "/usr/lib/python2.6/subprocess.py", line 1139, in _execute_child
    raise child_exception
OSError: [Errno 8] Exec format error

OSError:[Errno 8] Exec格式错误

这是操作系统在尝试运行/home/myuser/go.sh时报告的错误。

它看起来像go.sh的shebang( #! )行无效。

这是一个从shell运行但不是从Popen运行的示例脚本:

#\!/bin/sh
echo "You've just called $0 $@."

从第一行删除\\可以解决问题。

将代码更改为以下内容:

retcode = subprocess.call(["/home/myuser/go.sh", "abc.txt", "xyz.txt"], shell=True,)

注意“shell = True”

来自: http//docs.python.org/library/subprocess.html#module-subprocess

在Unix上,shell = True:如果args是一个字符串,它指定要通过shell执行的命令字符串。 这意味着字符串的格式必须与在shell提示符下键入时完全相同。

我最近用一个看起来像这样的脚本遇到了这个问题:

% cat /tmp/test.sh
                              <-- Note the empty line
#!/bin/sh
mkdir /tmp/example

该脚本从命令行运行正常,但失败了

OSError: [Errno 8] Exec format error

通过执行时

subprocess.Popen(['/tmp/test.sh']).communicate()

(解决方案当然是删除空行)。

In :call??
Signature: call(*popenargs, **kwargs)
Source:   
def call(*popenargs, **kwargs):
    """Run command with arguments.  Wait for command to complete, then
    return the returncode attribute.

    The arguments are the same as for the Popen constructor.  Example:

    retcode = call(["ls", "-l"])
    """
    return Popen(*popenargs, **kwargs).wait()
File:      /usr/lib64/python2.7/subprocess.py
Type:      function

调用刚刚调用Popen,使用wait()方法等待popenargs完成

是的,如果你所做的只是调用shell脚本,等待它完成,并收集它的退出状态,同时让它的stdin,stdout和stderr从你的Python进程继承,那就完全没问题了。 如果您需要对这些因素中的任何一个进行更多控制,那么您只需使用更通用的subprocess.Popen ,否则您所拥有的就可以了。

我在Mac OS上遇到此错误,同时尝试使用subprocess.call调用单行脚本。 从命令行调用时脚本运行正常。 添加shebang line #!/usr/bin/env sh ,它也通过subprocess.call运行良好。

看来,虽然shell有一个标记为executable的文本文件的默认执行程序,但subprocess.Popen却没有。

是的,这是执行某些事情的首选方式..

由于您通过一个数组传递所有参数(将在内部使用gor一个exec() - 样式调用)而不是作为shell评估的参数字符串,所以它也非常安全,因为无法注入shell命令。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM