简体   繁体   English

如何执行shell命令获取Python后命令后的输出和pwd

[英]How to execute shell command get the output and pwd after the command in Python

How can I execute a shell command, can be complicated like normal command in bash command line, get the output of that command and pwd after execution? 如何执行shell命令,可以像bash命令行中的普通命令一样复杂,在执行后得到该命令的输出和pwd?

I used function like this: 我用过这样的函数:

import subprocess as sub

def execv(command, path):
    p = sub.Popen(['/bin/bash', '-c', command],
                    stdout=sub.PIPE, stderr=sub.STDOUT, cwd=path)
    return p.stdout.read()[:-1]

And I check if user use cd command but that will not work when user use symlink to cd or other wierd way to change directory. 我检查用户是否使用cd命令,但是当用户使用符号链接以cd或其他更改方式更改目录时,这将不起作用。

and I need a dictionary that hold {'cwd': '<NEW PATH>', 'result': '<COMMAND OUTPUT>'} 我需要一个字典,其中包含{'cwd': '<NEW PATH>', 'result': '<COMMAND OUTPUT>'}

If you use subprocess.Popen , you should get a pipe object that you can communicate() for the command output and use .pid() to get the process id. 如果使用subprocess.Popen ,则应该获得一个管道对象,您可以对命令输出进行communicate() ,并使用.pid()来获取进程ID。 I'd be really surprised if you can't find a method to get the current working directory of a process by pid... 如果你找不到一个通过pid获取进程当前工作目录的方法,我会感到非常惊讶...

eg: http://www.cyberciti.biz/tips/linux-report-current-working-directory-of-process.html 例如: http//www.cyberciti.biz/tips/linux-report-current-working-directory-of-process.html

To get output of an arbitrary shell command with its final cwd (assuming there is no newline in the cwd): 要获得带有最终cwd的任意shell命令的输出(假设cwd中没有换行符):

from subprocess import check_output

def command_output_and_cwd(command, path):
    lines = check_output(command + "; pwd", shell=True, cwd=path).splitlines()
    return dict(cwd=lines[-1], stdout=b"\n".join(lines[:-1]))

I redirect stdout to stderr of pwd command. 我将stdout重定向到pwd命令的stderr。 if stdout is empty and stderr is not a path then stderr is error of the command 如果stdout为空并且stderr不是路径,则stderr是该命令的错误

import subprocess as sub

def execv(command, path):
    command = 'cd %s && %s && pwd 1>&2' % (path, command)
    proc = sub.Popen(['/bin/bash', '-c', command],
                     stdout=sub.PIPE, stderr=sub.PIPE)
    stderr = proc.stderr.read()[:-1]
    stdout = proc.stdout.read()[:-1]
    if stdout == '' and not os.path.exists(stderr):
        raise Exception(stderr)
    return {
        "cwd": stderr,
        "stdout": stdout
    }

UPDATE : here is better implemention (using last line for pwd and don't use stderr) 更新 :这里是更好的实现(使用pwd的最后一行,不要使用stderr)

def execv(command, path):
    command = 'cd %s && %s 2>&1;pwd' % (path, command)
    proc = sub.Popen(['/bin/bash', '-c', command],
                     env={'TERM':'linux'},
                     stdout=sub.PIPE)
    stdout = proc.stdout.read()
    if len(stdout) > 1 and stdout[-1] == '\n':
        stdout = stdout[:-1]
    lines = stdout.split('\n')
    cwd = lines[-1]
    stdout = '\n'.join(lines[:-1])
    return {
        "cwd": cwd,
        "stdout": man_to_ansi(stdout)
    }

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

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