【问题标题】:python subprocess module to call shell (Bash) scriptpython子进程模块调用shell(Bash)脚本
【发布时间】:2013-09-26 11:21:35
【问题描述】:

我正在尝试从 python 调用 shell (Bash) 脚本。该脚本位于我的 /home/user/bin 目录中,具有组和用户的执行权限,即-rwxr-xr--。我正在使用subprocess.check_call(["/home/user/bin/script.sh %s %s" % (subj,-6)],shell=True),这正在生成退出状态 127 代码。将stderr=subprocess.STDOUT 添加到命令中没有任何意义。这是确切的输出:

CalledProcessError: 命令 '['/home/.../bin/MNE_setup_source_space.sh kubi_td104 -6']' 返回非零退出状态 127`

我相信这可能是与 PATH 相关的问题,对吗?我不知道如何解决这个问题。如果我已经在传递可执行文件的绝对路径,怎么会有 PATH 问题?

提前致谢

【问题讨论】:

    标签: python bash subprocess


    【解决方案1】:

    不要使用shell=True。不要将参数作为argv[0] 的一部分传递。将参数向量作为向量传递——也就是说,在 Python 中,是一个列表:

    subprocess.check_call(["/home/user/bin/script.sh", str(subj), "-6"])
    

    如果你要使用shell=True,你会这样做:

    subprocess.check_call("/home/user/bin/script.sh %s %s" % (subj,-6), shell=True)
    

    ...也就是说,你根本不会使用列表形式。


    为了澄清您当前尝试失败的原因——因为您使用的是shell=True,它试图仅将第一个列表元素作为脚本传递,并将其他参数作为额外的 argv 元素传递,这些元素只能被读取或在第一个参数中传递的脚本选择查看它们时进行解释(如引用"$1"、"$2" 等)。

    shell=True 仅在极少数情况下才需要,在这种情况下,您需要在启动您尝试运行的程序之前执行重定向或逻辑,并且如果将任何未经审查的输入合并到命令中,则会带来严重的安全问题。跑步。除非您非常非常确定需要,否则不要使用它。

    【讨论】:

    • subprocess.check_call(["/home/user/bin/script.sh", subj, str(-6)]) 其中subj 已经是工作区字符串变量会生成 OS Exec 格式错误 [Errno 8]。我在偶然发现 127 退出代码之前遇到过这种情况。
    • 这不过subprocess.check_call("/home/kambiz/bin/MNE_setup_source_space.sh %s %s" % (subj,str(-6)), shell=True) 只是吐出0。那是什么意思?我没有看到脚本的结果!
    • @Kambysese 在您的第一条评论中,您没有将subj 转换为字符串(如示例那样)。你需要这样做。
    • @Kambysese 您的问题没有说明您希望脚本中的 stdout 和 stderr 去哪里,所以我不知道“看不到结果”是什么意思。如果您使用了您实际上愿意向我们展示的命令,而不是不透明的 script.sh,那么我们可以重现您的问题和/或展示正确的行为——调用 shell 脚本与其他命令时没有什么不同。
    • @Kambysese ...顺便说一下,在这里举一个shell=True将创建的错误的示例-假设您的subj中有多个单词.例如,如果subj = "Hello world"、"script.sh %s %s" % (subj -6) 将评估为script.sh Hello world -6,而不是您希望的script.sh "Hello world" -6……那么subj="$(rm -rf ~/)" 的结果会更糟。使用shell=False 可以完全防止这一类错误,而不仅仅是让您越来越深入地对抗引用和评估规则。
    猜你喜欢
    • 2019-11-21
    • 2012-06-04
    • 2013-12-23
    • 1970-01-01
    • 2019-10-31
    • 2013-06-25
    • 1970-01-01
    • 1970-01-01
    • 2023-03-09
    相关资源
    最近更新 更多