I am trying to start a process with the Command
API and redirect its standard output to standard error. The following fails:
Command::new("tput").arg("rc")
.stdout(io::stderr())
.status()
.expect("failed to run tput");
because Command::new("tput").arg("rc").stdout(<XXX>)
expects a std::process::Stdio
:
expected struct `std::process::Stdio`, found struct `std::io::Stderr`
The equivalent in Bash would probably be tput rc > /dev/stderr
.
I would like to know how to do this properly.
The regular output is sent to Standard Out (STDOUT) and the error messages are sent to Standard Error (STDERR). When you redirect console output using the > symbol, you are only redirecting STDOUT. In order to redirect STDERR, you have to specify 2> for the redirection symbol.
Warnings (and other human readable diagnostics) should be printed to stderr while program output (the updated configuration) should be printed to stderr, so the updated yaml can be e.g. redirected to a file or captured by a program.
As of Rust 1.15.0, Stdio
doesn't expose this functionality in a portable API, but there are platform-specific extension traits that you can use for this purpose.
On Unix-like platforms, the std::os::unix::io::FromRawFd
trait is implemented on Stdio
. This trait provides a single method, from_raw_fd
, that can turn a file descriptor into the type that implements the trait. Since standard error is defined as file descriptor 2, you could simply use .stdout(Stdio::from_raw_fd(2))
.
On Windows, there's a similar trait called FromRawHandle
implemented on Stdio
. Unfortunately, it's not listed in the online documentation; it only contains the Unix-specific variants. You would call GetStdHandle(STD_ERROR_HANDLE)
to obtain a handle to the standard error.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With