我相信一般来说,我理解这样做的一种方式:
Command
Stdio::piped()
创建一对新的输出流command.stdout()
和command.stderr()
这听起来不错吗?
我的两个实际问题:
每个流程是否有更简单的方法不涉及“读取线程”?
如果没有更简单的方法,Read::read()
需要&mut self
;你怎么把它传递给远程线程?
请提供具体示例,了解如何实际流式传输输出,而不仅仅是有关如何进行输出的一般性建议......
更具体地说,这是the default example of using spawn
:
use std::process::Command;
let mut child = Command::new("/bin/cat")
.arg("file.txt")
.spawn()
.expect("failed to execute child");
let ecode = child.wait()
.expect("failed to wait on child");
assert!(ecode.success());
如何更改上面的示例以将child的输出流式传输到控制台,而不是仅仅等待退出代码?
答案 0 :(得分:2)
虽然接受的答案是正确的,但它不包括非平凡的案例。
要流式输出并手动处理,请使用Stdio::piped()
并手动处理通过调用.stdout
返回的子项的spawn
属性,如下所示:
use std::process::{Command, Stdio};
use std::path::Path;
use std::io::{BufReader, BufRead};
pub fn exec_stream<P: AsRef<Path>>(binary: P, args: Vec<&'static str>) {
let mut cmd = Command::new(binary.as_ref())
.args(&args)
.stdout(Stdio::piped())
.spawn()
.unwrap();
{
let stdout = cmd.stdout.as_mut().unwrap();
let stdout_reader = BufReader::new(stdout);
let stdout_lines = stdout_reader.lines();
for line in stdout_lines {
println!("Read: {:?}", line);
}
}
cmd.wait().unwrap();
}
#[test]
fn test_long_running_process() {
exec_stream("findstr", vec!("/s", "sql", "C:\\tmp\\*"));
}
另见Merge child process stdout and stderr关于同时从stderr和stdout捕获输出。