Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/346.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
pythonshell命令管道grep没有结果_Python_Subprocess_Pipe - Fatal编程技术网

pythonshell命令管道grep没有结果

pythonshell命令管道grep没有结果,python,subprocess,pipe,Python,Subprocess,Pipe,我正在尝试从python中的cpanel用户那里获取域名 这是我的密码: import subprocess user = "testuser" getuserdata = 'cat /var/cpanel/users/' + user getdnsline = 'grep "DNS="' test = 'wc -l' userdataprocess = subprocess.Popen(getuserdata.split(), stdout=subprocess.PIPE) testpro

我正在尝试从python中的cpanel用户那里获取域名

这是我的密码:

import subprocess
user = "testuser"
getuserdata = 'cat /var/cpanel/users/' + user
getdnsline = 'grep "DNS="'
test = 'wc -l'

userdataprocess = subprocess.Popen(getuserdata.split(), stdout=subprocess.PIPE)

testprocess = subprocess.Popen(test.split(), stdin=userdataprocess.stdout, stdout=subprocess.PIPE)

test, error = testprocess.communicate()
print(test)

dnslineprocess = subprocess.Popen(getdnsline.split(), stdin=userdataprocess.stdout, stdout=subprocess.PIPE)

website, error = dnslineprocess.communicate()
print(website.decode('utf-8').splitlines())
我的输出是:

b'60\n'
[]
这意味着wc-l命令返回60行。因此,将第一个getuserdata命令的输出传递给wc-l命令是有效的

但是,grep命令始终返回空白。不管它是什么,我都会输入“DNS=”或“=”甚至“a”。该文件是正常的cpanel用户文件,我已经验证了DNS是否在该文件中

当我刚从第一个进程userdataprocess输出数据时,我可以手动检查DNS条目


当以这种方式使用grep命令时,我需要做什么不同的事情吗

这是因为
wc-l
命令的
testprocess.communicate()
已经消耗了
userdataprocess.stdout
的所有输出,并且事实上关闭了它,所以
dnslineprocess.communicate()
没有任何内容可供读取


您应该将
userdataprocess.stdout
的输出读入变量,然后将其用作
testprocess.communicate()
dnslineprocess.communicate()的输入

另外,正如@pyb所指出的,您在
grep
命令中不必要地引用了
DNS=
,如果没有shell,该命令将传递给
grep
,并在要过滤的字符串中包含双引号。您应该简单地删除它们,因为过滤器字符串中没有特殊字符

import subprocess
user = "testuser"
getuserdata = 'cat /var/cpanel/users/' + user
getdnsline = 'grep DNS='
test = 'wc -l'

userdataprocess = subprocess.Popen(getuserdata.split(), stdout=subprocess.PIPE)

userdata = userdataprocess.stdout.read()

testprocess = subprocess.Popen(test.split(), stdin=subprocess.PIPE, stdout=subprocess.PIPE)

test, error = testprocess.communicate(userdata)
print(test)

dnslineprocess = subprocess.Popen(getdnsline.split(), stdin=subprocess.PIPE, stdout=subprocess.PIPE)

website, error = dnslineprocess.communicate(userdata)
print(website.decode('utf-8').splitlines())

由于
DNS=
周围的引号,脚本失败

您可以使用
shell=True
使脚本正常工作:

dnslineprocess=subprocess.Popen(getdnsline,stdin=userdataprocess.stdout,stdout=subprocess.PIPE,shell=True)

来源:

userdataprocess.stdout
在运行
dnslineprocess
时为空,因为
testprocess
已经消耗了所有数据。我不知道有什么简单的解决方法,但是你使用
子流程
是完全没有必要的:你用它做的每件事(读取文件、计算行数、检查这些行中的特定文本)都可以在Python中直接完成。那是行不通的。我也想到了这一点,并对调用
wc-l
的部分进行了注释,得到了相同的结果。它确实有效,但第二个问题是正如pyb所指出的,OP不必要地引用了
DNS=
。我已相应地编辑了答案。