将输出流以外的两个或多个 Powershell 流重定向到同一文件 [英] Redirect two or more Powershell streams other than output stream to the same file

查看:18
本文介绍了将输出流以外的两个或多个 Powershell 流重定向到同一文件的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在 Powershell 中,我们可以将标准输出流与任何其他流结合起来,然后将结果重定向(写入)到同一个文件中.

示例:

Powershell -File "C:myscript.ps1" 2>&1>"C:log.txt"Powershell -File "C:myscript.ps1" 3>&2>&1>"C:log.txt"

假设我在 myscript.ps1 中使用 Write-ErrorWrite-Warning 语句,并且我只想将错误和警告写入同一个文件.

注意:如果我没记错的话,1 是输出流,2 是错误流,3 是警告流.

我的第一个合乎逻辑的尝试是使用 3>&2> - 如果组合 1 和 2 有效,为什么 3 和 2 不行?见下文:

Powershell -File "C:myscript.ps1" 3>&2>"C:log.txt"

但是,3>&2> 不能用作有效的重定向运算符.

我可以尝试:

Powershell -File "C:myscript.ps1" 3>"C:warninglog.txt" 2>"C:errorlog.txt"
但我真的很想写入同一个文件.

如果我尝试运行:

Powershell -File "C:myscript.ps1" 3>"C:log.txt" 2>"C:log.txt"

似乎错误流 (2) 从未被写入 log.txt,因为文件已被警告流锁定.

有没有办法将两个(或多个)输出流组合成一个流并将结果重定向到同一个文件?

解决方案

当您通过

运行 PowerShell 脚本时,详细、警告和调试流将合并到 STDOUT 中

powershell -File "C:myscript.ps1"

所以你不能再单独重定向它们了.只有错误流不同,因为它似乎同时进入 STDOUT 和 STDERR,在那里它可以被 1>2> 重定向.

演示:

<前>C:>输入 test.ps1$DebugPreference = "继续"$VerbosePreference = "继续"写输出输出消息"写错误错误信息"写详细详细消息"写警告警告信息"写调试调试消息"C:>powershell -File . est.ps1输出消息C: est.ps1:错误信息+ CategoryInfo : NotSpecified: (:) [Write-Error], WriteErrorException+ FullQualifiedErrorId : Microsoft.PowerShell.Commands.WriteErrorException,test.ps1VERBOSE:详细信息警告:警告信息DEBUG:调试信息C:>powershell -File . est.ps1 2>nul 3>nul 4>nul 5>nul输出消息VERBOSE:详细信息警告:警告信息DEBUG:调试信息C:>powershell -File . est.ps1 1>nulC:>_

如果您想单独重定向详细、警告或调试流,您必须使用 -Command 而不是 -File 并在 PowerShell 中进行重定向:

<前>C:>powershell -Command ". est.ps1 2>$null 3>$null 5>$null"输出消息VERBOSE:详细信息

然而,虽然在 CMD 您可以将任何句柄重定向到任何其他句柄(3>&21>&5、...)、PowerShell 重定向 仅支持重定向到任一文件 (3>C:out.txt) 或成功输出流 (3>&1).尝试重定向到任何其他流将引发错误:

<前>C:>powershell -Command ". est.ps1 2>out.txt 3>&2"在行:1 字符:22+ . est.ps1 2>out.txt 3>&2+ ~~~~'3>&2' 运算符保留供将来使用.+ CategoryInfo : ParserError: (:) [], ParentContainsErrorRecordException+ FullQualifiedErrorId : RedirectionNotSupported

将不同的流重定向到同一个文件:

<前>C:>powershell -Command ". est.ps1 2>out.txt 3>>out.txt"out-file : 进程无法访问文件C:out.txt",因为它正在被另一个进程使用.在行:1 字符:1+ . est.ps1 2>out.txt 3>>out.txt+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~+ CategoryInfo : OpenError: (:) [Out-File], IOException+ FullQualifiedErrorId : FileOpenFailure,Microsoft.PowerShell.Commands.OutFileCommand

如果您可以选择合并警告和成功输出,您可以执行以下操作:

powershell -Command ".	est.ps1 >out.txt 3>&1 2>error.log"

或者像这样:

powershell -Command ".	est.ps1 >out.txt 3>&1 2>&1"

或(重定向所有流)像这样:

powershell -Command ".	est.ps1 *>out.txt"

否则我看到的唯一选择是重定向到不同的文件:

powershell -Command ".	est.ps1 3>warning.log 2>error.log"

In Powershell, we can combine the standard output stream with any other stream and then redirect (write) the result to the same file.

Examples:

Powershell -File "C:myscript.ps1" 2>&1> "C:log.txt"  
Powershell -File "C:myscript.ps1" 3>&2>&1> "C:log.txt"

Suppose I use Write-Error and Write-Warning statements in myscript.ps1 and I want to write only the errors and the warnings to the same file.

Note: if I am not mistaken, 1 is the output stream, 2 is the error stream and 3 the warning stream.

My first logical try was then to use 3>&2> - if combining 1 and 2 works, why would not 3 and 2 ? See below:

Powershell -File "C:myscript.ps1" 3>&2> "C:log.txt"

However, 3>&2> does not work as a valid redirect operator.

I could get around trying:

Powershell -File "C:myscript.ps1" 3>"C:warninglog.txt" 2>"C:errorlog.txt"
but I really want to write to the same file.

If I try to run:

Powershell -File "C:myscript.ps1" 3>"C:log.txt" 2>"C:log.txt" 

it seems the error stream (2) never gets written to log.txt because file is locked by the warning stream.

Is there a way to combine two (or more) output streams into a single stream and redirect the result to the same file ?

解决方案

The verbose, warning, and debug streams are merged into STDOUT when you run PowerShell scripts via

powershell -File "C:myscript.ps1"

so you can't redirect them separately anymore. Only the error stream is different, since it seems to go to both STDOUT and STDERR, where it can be redirected by 1> as well as 2>.

Demonstration:

C:>type test.ps1
$DebugPreference = "Continue"
$VerbosePreference = "Continue"
Write-Output "Output message"
Write-Error "Error message"
Write-Verbose "Verbose message"
Write-Warning "Warning message"
Write-Debug "Debug message"

C:>powershell -File .	est.ps1
Output message
C:	est.ps1 : Error message
    + CategoryInfo          : NotSpecified: (:) [Write-Error], WriteErrorException
    + FullyQualifiedErrorId : Microsoft.PowerShell.Commands.WriteErrorException,test.ps1

VERBOSE: Verbose message
WARNING: Warning message
DEBUG: Debug message

C:>powershell -File .	est.ps1 2>nul 3>nul 4>nul 5>nul
Output message
VERBOSE: Verbose message
WARNING: Warning message
DEBUG: Debug message

C:>powershell -File .	est.ps1 1>nul

C:>_

If you want to redirect the verbose, warning, or debug stream separately you must use -Command instead of -File and do the redirection within PowerShell:

C:>powershell -Command ".	est.ps1 2>$null 3>$null 5>$null"
Output message
VERBOSE: Verbose message

However, while in CMD you can redirect any handle to any other handle (3>&2, 1>&5, ...), PowerShell redirection only supports redirection to either a file (3>C:out.txt) or the success output stream (3>&1). Trying to redirect to any other stream will throw an error:

C:>powershell -Command ".	est.ps1 2>out.txt 3>&2"
At line:1 char:22
+ .	est.ps1 2>out.txt 3>&2
+                      ~~~~
The '3>&2' operator is reserved for future use.
    + CategoryInfo          : ParserError: (:) [], ParentContainsErrorRecordException
    + FullyQualifiedErrorId : RedirectionNotSupported

as will redirecting different streams to the same file:

C:>powershell -Command ".	est.ps1 2>out.txt 3>>out.txt"
out-file : The process cannot access the file 'C:out.txt' because it is being
used by another process.
At line:1 char:1
+ .	est.ps1 2>out.txt 3>>out.txt
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : OpenError: (:) [Out-File], IOException
    + FullyQualifiedErrorId : FileOpenFailure,Microsoft.PowerShell.Commands.OutFileCommand

If merging warning and success output is an option for you, you could do something like this:

powershell -Command ".	est.ps1 >out.txt 3>&1 2>error.log"

or like this:

powershell -Command ".	est.ps1 >out.txt 3>&1 2>&1"

or (redirecting all streams) like this:

powershell -Command ".	est.ps1 *>out.txt"

Otherwise the only option I see is to redirect to different files:

powershell -Command ".	est.ps1 3>warning.log 2>error.log"

这篇关于将输出流以外的两个或多个 Powershell 流重定向到同一文件的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆