在Powershell脚本中跟踪输出来自何处
是否可以在Powershell脚本中跟踪输出(到控制台)的来源?我有一个脚本正在向我输出信息,但我不确定哪一行正在进行输出。例如,是否可以使用Set PSBreakpoint并在信息返回控制台时告诉它中断 干杯在Powershell脚本中跟踪输出来自何处,powershell,debugging,scripting,output,powershell-3.0,Powershell,Debugging,Scripting,Output,Powershell 3.0,是否可以在Powershell脚本中跟踪输出(到控制台)的来源?我有一个脚本正在向我输出信息,但我不确定哪一行正在进行输出。例如,是否可以使用Set PSBreakpoint并在信息返回控制台时告诉它中断 干杯 我收到数以百计的“假”回复。 以下是代码的输出部分: $ar = Function-which_returns_array_of_objects $gr = Function-which_returns_array_of_objects Write-Host
我收到数以百计的“假”回复。 以下是代码的输出部分:
$ar = Function-which_returns_array_of_objects
$gr = Function-which_returns_array_of_objects
Write-Host "To begin with..."
Write-Host "$($ar.count) assets"
Write-Host "$($gr.count) goods"
foreach($asset in $ar){
if(!(Test-NoNA -string $asset.Serial)){continue}
#See if the particular serial number exists in Goods Received
$found = @()
$gr | Where {$_.SerialNumber -eq $asset.serial} | %{
$found += $_
# and then mark the entry as one that has to be deleted from GR
$_.Delete = "YES"
}
if($found.count -eq 1){
#Serial Number has been found once in GR
#We want to check its PN...
if(Test-NoNA -string $found.PartNumber -and $found.PartNumber -ne $asset.Model){
#add it to the asset if its good and not the same as the model number...
$asset.PartNumber -eq $found.PartNumber
}
}elseif(!$found -or $found.count -eq 0){
#No entries found in GR
#Shouldn't be the case but doesn't actually do any damage as we'd be deleting the GR entry anyway
}elseif($found.count -gt 1){
#More than one match for the SN - probably means a SN like "N/A" has got through the earlier checks
Write-Warning "More than one match for SN: '$($asset.serial)'"
}else{
#Default catcher
Write-Warning "Unknown Error for SN: '$($asset.serial)'"
}
}
此外,以下是测试NoNA:
function Test-NoNA($string){
#check that the given string is not blank, N/A, ?, etc. Returns true if string is good
if($string -and $string -ne "" -and $string -ne "N/A" -and $string -ne "NA" -and $string -ne '?' -and $string -isnot [System.DBNull]){return $true}
}
是的,试试这个。这应该会在首次发现write语句时中断
Set-PSBreakpoint -Script Sample.ps1 -Command "write*"
此命令在Sample.ps1脚本中以write开头的每个命令上设置断点,例如write Host。更多
不幸的是
可以很好地处理显式cmdlet调用Set PSBreakpoint-Command
- 例如,调用脚本
中的/myscript.ps1
和写入输出
,将导致使用先前的写入主机
调用中断调试器)Set PSBreakpoint-Command Write-*./myscript.ps1
- 例如,调用脚本
- 但是不适用于隐式输出,这些语句的输出既不被捕获也不被重定向(例如,
,'foo'
,1+2
)获取日期
-eq
运算符(比较)与=
运算符(分配)混淆,如$asset.PartNumber-eq$之类的语句找到了.PartNumber
导致了不需要的输出,如所诊断的-eq
产生输出(比较的布尔结果),而=
不产生输出
变通办法:
- 在调用脚本之前运行
,脚本在生成输出之前打印每个源代码行<代码>-跟踪2提供了其他详细信息Set PSDebug-Trace 1
- 使用以下技巧,隐式或显式地告诉您生成成功输出的第一行的编号;但请注意,此时脚本执行将中止:
try { ./myscript.ps1 | Write-Error -EA Stop } catch { "$_"; $_.ScriptStackTrace }
- 脚本的成功输出通过管道传输到
,它将输出重定向(字符串化版本)到PowerShell的错误流,并使用Write Error
(缩写为-EA Stop
)导致发送到错误流的输出中止执行;然后,-ErrorAction Stop
块输出结果错误记录的字符串化版本(其本身就是原始输出的字符串化版本),然后是脚本调用堆栈跟踪,其第一行显示生成输出的行数catch
- 注意:如果脚本在第一次成功输出之前碰巧产生语句终止错误,那么这种技术将不起作用,但是这种情况很少发生
- 脚本的成功输出通过管道传输到
- 如果要检查给定行上脚本的运行时状态,请说
:15
Set PSBreakpoint-Script./myscript.ps1-第15行
- 或者,在PSv5+中,如果修改脚本(临时)是一个选项,则将脚本中的
调用放置在您希望进入调试器的位置Wait Debugger
- 使用的调试功能和设置断点和/或逐语句逐步执行脚本
- 或者,直接在PowerShell窗口中为等效操作使用
设置PSDebug-Step
- 或者,直接在PowerShell窗口中为等效操作使用
$asset.PartNumber-eq$found.PartNumber
似乎是问题的一部分。您的评论似乎表明您打算将-eq
设置为=
。[咧嘴笑]啊,就是这样!这也解释了脚本中的一些其他问题。库尔!很高兴知道你修好了。。。[咧嘴笑]