Python 子进程调用不起作用

标签 python linux bash shell subprocess

我正在编写一个 Python 程序,我需要执行这个相当长的 shell 命令并在我的脚本中接收输出。

test = subprocess.Popen(shlex.split("find /home/disk1 -maxdepth 0 -name folder1* -o -name folder7*"), stdout=subprocess.PIPE, shell=True) 
test.communicate()

我已经尝试了所有可能的代码变体,比如在参数中添加“executable="/bin/bash",或者使用 subprocess.check_output 等。

每当我运行此程序并通过键入“test.communicate()”检查输出时,我都会获取“/home/disk1”目录中的所有文件,而不是我根据命令想要的文件。当我在 shell 中键入此查找搜索时,它工作正常。我不知道为什么它不起作用。我在互联网上浪费了最后两个小时。我在这里感到困惑,请帮助我。

编辑:根据评论,我还尝试从参数中省略“shell=True”,这种情况下的响应是: (b'',无) 我期待使用此命令的 4 个文件的名称。这还是不对。谢谢。

编辑:抱歉,我不是在寻找文件,我是在寻找文件夹。

最佳答案

  1. 命令

    find /home/disk1 -maxdepth 0 -name file1* -o -name file7*
    

    不会产生任何输出。深度 0 的唯一对象是 /home/disk1,它的名称与两个表达式都不匹配。所以运行该命令的预期结果是空的。您可能需要 -maxdepth 1。但是,如果您不需要递归搜索,find 就有点过分了;您可以对模式进行全局扩展。

  2. 当您在 subprocess.Popen 的构造函数中指定 shell=True 时,您应该传递包含整个命令的单个字符串,然后该字符串将传递给 shell 。您可以通过提供单个字符串参数或包含一个元素(字符串)的列表来执行此操作。对于 shell=False,您需要提供一个列表,其第一个元素是要运行的程序,其余元素是参数。因此,以下任何一项都会产生预期的结果:

    test = subprocess.Popen(
             "find /home/disk1 -maxdepth 1 -name file1* -o -name file7*"
             , stdout=subprocess.PIPE, shell=True) 
    test = subprocess.Popen(
             ["find /home/disk1 -maxdepth 1 -name file1* -o -name file7*"]
             , stdout=subprocess.PIPE, shell=True) 
    test = subprocess.Popen(
             shlex.split(
                 "find /home/disk1 -maxdepth 1 -name file1* -o -name file7*")
             , stdout=subprocess.PIPE) 
    test = subprocess.Popen(["find", "/home/disk1"
                                   , "-maxdepth", "1"
                                   , "-name", "file1*"
                                   , "-o"
                                   , "-name", "file7*"]
                            , stdout=subprocess.PIPE) 
    

    我会使用最后一个,我自己。

  3. shell=True 被指定时,subprocess.Popen 对一个以上元素的列表做了什么没有很好的记录,并且这种用法不是受到推崇的。 Posix 实现将列表的所有元素添加到 ["sh", "-c"],然后执行它。实际上,这将执行以下操作:

    sh -c find /home/disk1 -maxdepth 1 -name "file1*" -o -name "file7*"
    

    这里,-c 的参数只是find/home/disk1 变为$0,并且$1$7 设置为其余参数。最终结果是 find 执行时没有命令行参数(在名称为 /home/disk1 的进程中)。不带参数的 find 生成从当前工作目录开始的所有文件的递归列表。

关于Python 子进程调用不起作用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25416271/

相关文章:

linux - 为什么fork()在子进程中返回0?

linux - 模块无法启动 Ansible

regex - 只打印匹配正则表达式的部分

linux - Upstart 导致两个进程 - 为什么?

python - 如何在pyspark中保存没有日期的时间信息?

python - 如何使用参数检索挂起和正在执行的 Celery 任务?

python - 使用 python 保留关键字作为变量名

Python 项目与 Maven 的依赖关系 - ModuleNotFoundError : No module named 'xxx'

php - 如何安全地在虚拟主机上拥有多对多用户

c - 如何使用 C 在 linux 终端中显示 "help"命令?