我有一个正在调试的PowerShell脚本,希望将所有Write-Host语句重定向到一个文件。有什么简单的方法可以做到这一点吗?
发布于 2011-04-22 14:32:48
直到PowerShell 4.0,
Write-Host都会将对象发送到主机。它不返回任何对象。
从PowerShell 5.0和更高版本开始,Write-Host是Write-Information的包装器,它允许输出到信息流并使用6>> file_name重定向它。
http://technet.microsoft.com/en-us/library/hh849877.aspx
但是,如果您有很多Write-Host语句,请将它们全部替换为Write-Log,它允许您决定是输出到控制台、文件还是事件日志,还是全部输出到这三个。
另请检查:
像>, >>, 2>, 2>, 2>&1
Write-Log
Start-Transcript.一样的
Add-Content发布于 2012-08-21 02:28:17
您可以为Write-Host创建一个代理函数,该函数将对象发送到标准输出流,而不仅仅是打印它们。我写了下面的cmdlet就是为了这个目的。它将在运行中创建一个代理,该代理仅在当前管道的持续时间内持续。
完整的文章在我的博客here上,但我已经包含了下面的代码。使用-Quiet开关抑制控制台写入。
用法:
PS> .\SomeScriptWithWriteHost.ps1 | Select-WriteHost | out-file .\data.log # Pipeline usage
PS> Select-WriteHost { .\SomeScriptWithWriteHost.ps1 } | out-file .\data.log # Scriptblock usage (safer)
function Select-WriteHost
{
[CmdletBinding(DefaultParameterSetName = 'FromPipeline')]
param(
[Parameter(ValueFromPipeline = $true, ParameterSetName = 'FromPipeline')]
[object] $InputObject,
[Parameter(Mandatory = $true, ParameterSetName = 'FromScriptblock', Position = 0)]
[ScriptBlock] $ScriptBlock,
[switch] $Quiet
)
begin
{
function Cleanup
{
# Clear out our proxy version of write-host
remove-item function:\write-host -ea 0
}
function ReplaceWriteHost([switch] $Quiet, [string] $Scope)
{
# Create a proxy for write-host
$metaData = New-Object System.Management.Automation.CommandMetaData (Get-Command 'Microsoft.PowerShell.Utility\Write-Host')
$proxy = [System.Management.Automation.ProxyCommand]::create($metaData)
# Change its behavior
$content = if($quiet)
{
# In quiet mode, whack the entire function body,
# simply pass input directly to the pipeline
$proxy -replace '(?s)\bbegin\b.+', '$Object'
}
else
{
# In noisy mode, pass input to the pipeline, but allow
# real Write-Host to process as well
$proxy -replace '(\$steppablePipeline\.Process)', '$Object; $1'
}
# Load our version into the specified scope
Invoke-Expression "function ${scope}:Write-Host { $content }"
}
Cleanup
# If we are running at the end of a pipeline, we need
# to immediately inject our version into global
# scope, so that everybody else in the pipeline
# uses it. This works great, but it is dangerous
# if we don't clean up properly.
if($pscmdlet.ParameterSetName -eq 'FromPipeline')
{
ReplaceWriteHost -Quiet:$quiet -Scope 'global'
}
}
process
{
# If a scriptblock was passed to us, then we can declare
# our version as local scope and let the runtime take
# it out of scope for us. It is much safer, but it
# won't work in the pipeline scenario.
#
# The scriptblock will inherit our version automatically
# as it's in a child scope.
if($pscmdlet.ParameterSetName -eq 'FromScriptBlock')
{
. ReplaceWriteHost -Quiet:$quiet -Scope 'local'
& $scriptblock
}
else
{
# In a pipeline scenario, just pass input along
$InputObject
}
}
end
{
Cleanup
}
}发布于 2011-12-23 09:18:11
使用重定向将导致Write-Host挂起。这是因为Write-Host处理特定于当前使用的终端的各种格式化问题。如果你只想让你的脚本能够像平常一样灵活地输出(默认是shell,支持>、2>等),那么可以使用Write-Output。
否则,如果您真的想要捕捉当前终端的特性,那么Start-Transcript是一个很好的起点。否则,您将不得不手动测试或编写一些复杂的测试套件。
https://stackoverflow.com/questions/5588689
复制相似问题