以与Python异步的方式从管道子流程获取流
我想直接在以与Python异步的方式从管道子流程获取流,python,python-3.x,subprocess,python-asyncio,Python,Python 3.x,Subprocess,Python Asyncio,我想直接在Python中运行以下命令: dumpcap -q -f http -i eth0 -w - | tshark -l -n -T json -r - | my_app.py 我想通过使用子流程和asyncio来运行它,以便在async中运行它 因此,首先我想运行: dumpcap -q -f http -i eth0 -w - 此命令的输出应通过管道传输到下一个命令,该命令应/可能不同步运行: tshark -l -n -T json -r - 这个输出应该通过管道传输到我可以使
Python
中运行以下命令:
dumpcap -q -f http -i eth0 -w - | tshark -l -n -T json -r - | my_app.py
我想通过使用子流程
和asyncio
来运行它,以便在async
中运行它
因此,首先我想运行:
dumpcap -q -f http -i eth0 -w -
此命令的输出应通过管道传输到下一个命令,该命令应/可能不同步运行:
tshark -l -n -T json -r -
这个输出应该通过管道传输到我可以使用的流中
有没有一个简单的解决方案
有没有一个简单的解决方案
子流程文档中的说明也应适用于异步IO子流程。例如(未经测试):
async def process():
p1=等待asyncio.create_subprocess_shell(
“dumpcap-q-f http-i eth0-w-”,stdout=asyncio.subprocess.PIPE)
p2=等待asyncio.create_subprocess_shell(
“tshark-l-n-tjson-r-”,
stdin=p1.stdout,stdout=asyncio.subprocess.PIPE)
p1.stdout.close()#我们不再需要它了
尽管如此:
line=wait p2.stdout.readline()
如果不是直线:
打破
打印(行)
除了@user4815162342的答案之外,请注意,您只需将完整的shell命令传递给子流程,并使用管道与子流程的两端进行通信:
例如:
proc=wait asyncio.create\u subprocess\u shell(
“tr a-z a-z |头-c-2 |尾-c+3”,
stdin=asyncio.subprocess.PIPE,
stdout=asyncio.subprocess.PIPE,
)
stdout,等待程序通信(b“**你好**”)
断言stdout==b“HELLO”
addfirst我得到了无效语法
,因此更改为放入async def run():您的代码
,然后使用asyncio.run(run())
运行。现在,我在冒号:
@AlfredBalle处得到了行的无效语法…行:=wait p2.stdout.readline…
,您需要Python3.8来实现,您可能使用的是3.7或更早版本。我现在修改了代码,不使用它,并添加了一个显式的async def
proc.communicate()
将尝试读取所有数据,而不是逐行流式传输。这不利于内存使用(想象一下,如果您期望子标准输出大于主RAM),也不利于性能(在子标准输出完成之前,不会处理第一行)@inetknght当然,这确实取决于正在运行的命令。例如,communicate()
如果命令已经包含一些聚合并产生一个小的输出(例如tail-n1
,wc
,等等),则可以使用communicate()。