Using powershell call native command-line app and capture STDERR
I'm using a port of a cygwin tool on Windows which writes normal status messages to STRERR. This produces ugly output when run from PowerShell:
PS> dos2unix.exe -n StartApp.sh StartApp_fixed.sh
dos2unix.exe : dos2unix: converting file StartApp.sh to file StartApp_fixed.sh in UNIX format ...
At line:1 char:13
+ dos2unix.exe <<<< -n StartApp.sh StartApp_fixed.sh
+ CategoryInfo : NotSpecified: (dos2unix: conve...UNIX format ...:String) [], RemoteException
+ FullyQualifiedErrorId : NativeCommandError
Is there a better way?
P.S. I intend to post one solution I've found and compare it to answers from others.
Solution 1:
No, alas. This ugliness is an by-design feature of Powershell :( If an application prints to standard error (and anything else is listening), then Powershell wraps each line in an obfuscating 'NativeCommandError' object. See https://stackoverflow.com/questions/1394084/ignoring-an-errorlevel-0-in-windows-powershell for more detail
You could silence the ugly objects, but then you'd lose the useful content too.
Solution 2:
I believe I've just stumbled upon a slightly cleaner solution than @yzorg's. The redirect of stdout to stderr is not enough as it's still an ErrorRecord object at this point, not a string. Instead, it needs to be processes and the following seems to extract just what's needed with a minimum of effort:
PS> dos2unix.exe -n StartApp.sh StartApp_fixed.sh 2>&1 | %{"$_"}
dos2unix: converting file StartApp.sh to file StartApp_fixed.sh in Unix format...
Solution 3:
This is one solution I've found. Please post your answer if you have a better answer (this is intended only for command-line utilities that send status messages to STDERR instead of normal output stream):
PS> $output = dos2unix.exe -n StartApp.sh StartApp_fixed.sh 2>&1
$output.CategoryInfo.TargetName | Out-Default
dos2unix: converting file StartApp.sh to file StartApp_fixed.sh in UNIX format ...