检查PowerShell中是否处于调试模式
如果脚本在调试模式下运行,如何签入PowerShell?我目前正在安装PowerShell工具的Visual Studio 2015中进行调试 脚本的一部分使用Send MailMessage发送电子邮件。我想做一些类似于下面的事情检查PowerShell中是否处于调试模式,powershell,debugging,Powershell,Debugging,如果脚本在调试模式下运行,如何签入PowerShell?我目前正在安装PowerShell工具的Visual Studio 2015中进行调试 脚本的一部分使用Send MailMessage发送电子邮件。我想做一些类似于下面的事情 If (Debug) { $messageProperties.To = "$env:username@company.com" } Else { $messageProperties.To = "prodmailbox@company.com" }
If (Debug)
{
$messageProperties.To = "$env:username@company.com"
}
Else
{
$messageProperties.To = "prodmailbox@company.com"
}
我知道在C#中,我可以做下面这样的事情。我想知道PowerShell是如何处理这一问题的
#if DEBUG
// Debug code
#endif
在PowerShell中“调试”可能意味着几件事。1) 程序在调试器下运行,2)cmdlet/函数被传递-Debug
标志或$DebugPreferences
不是SilentlyContinue
3)PowerShell跟踪打开,4)Set-PSDebug用于切换跟踪(与#3不同的跟踪类型)
如果您还没有选择其中一个,我建议您选择#2。这很简单(检查-Debug
是否在PSBoundVariables
中,或者$DebugPreferences
的值是否不是SilentlyContinue
)。它支持Write-Debug
cmdlet。一般来说,这是PowerShell风格的切换调试输出的方式
如果您确实需要#1,那么正如所解释的,在其核心实现PowerShell调试器将处理两个事件(debugger.BreakpointUpdated
和debugger.DebuggerStop
),因此您需要查看这些事件是否有处理程序
如果您需要#4,您可能需要访问私有数据。唯一以PSDebug
作为名词的PowerShell 3.0命令是Set PSDebug
,这意味着没有cmdlet返回PSDebug
的状态
如果需要#3,则情况类似于#4。没有用于返回跟踪内容信息的cmdlet。这里有一个函数,可以让您轻松检查;以及一些改变行为的选项
function Test-Debug {
[CmdletBinding()]
param (
[Parameter(Mandatory = $false)]
[switch]$IgnorePSBoundParameters
,
[Parameter(Mandatory = $false)]
[switch]$IgnoreDebugPreference
,
[Parameter(Mandatory = $false)]
[switch]$IgnorePSDebugContext
)
process {
((-not $IgnoreDebugPreference.IsPresent) -and ($DebugPreference -ne "SilentlyContinue")) -or
((-not $IgnorePSBoundParameters.IsPresent) -and $PSBoundParameters.Debug.IsPresent) -or
((-not $IgnorePSDebugContext.IsPresent) -and ($PSDebugContext))
}
}
下面是一些代码,用于演示特定场景中的输出:
#region 'Test Functions'
function Test-InheritExplicit {
[CmdletBinding()]
param (
[Parameter(Mandatory = $false)]
[switch]$IgnorePSBoundParameters
,
[Parameter(Mandatory = $false)]
[switch]$IgnoreDebugPreference
,
[Parameter(Mandatory = $false)]
[switch]$IgnorePSDebugContext
)
process {
#if we weren't splatting all vars over, we could use this trick:
#[switch]$DebugCopy = $PSBoundParameters.Debug
#Test-Debug -Debug:$DebugCopy
Test-Debug @PSBoundParameters
}
}
function Test-InheritImplicit {
[CmdletBinding()]
param (
[Parameter(Mandatory = $false)]
[switch]$IgnorePSBoundParameters
,
[Parameter(Mandatory = $false)]
[switch]$IgnoreDebugPreference
,
[Parameter(Mandatory = $false)]
[switch]$IgnorePSDebugContext
)
process {
Test-Debug -IgnorePSBoundParameters:$IgnorePSBoundParameters -IgnorePSDebugContext:$IgnorePSDebugContext -IgnoreDebugPreference:$IgnoreDebugPreference
}
}
#endregion 'Test Functions'
#region 'Test Cases'
[hashtable[]]$testCases = 0..15 | %{
[hashtable]$new = @{}
if ($_ -band 1) {$new.Debug = [switch]$true}
if ($_ -band 2) {$new.IgnorePSBoundParameters = [switch]$true}
if ($_ -band 4) {$new.IgnoreDebugPreference = [switch]$true}
if ($_ -band 8) {$new.IgnorePSDebugContext = [switch]$true}
$new
}
[int]$t = 0
$testCases | %{
[hashtable]$testCase = $_
(New-Object -TypeName PSObject -Property @{
TestId = ++$t
Debug = [bool]$_.Debug
IgnorePSBoundParameters = [bool]$_.IgnorePSBoundParameters
IgnoreDebugPreference = [bool]$_.IgnoreDebugPreference
IgnorePSDebugContext = [bool]$_.IgnorePSDebugContext
TD = (Test-Debug @testCase)
TIE = (Test-InheritExplicit @testCase)
TII = (Test-InheritImplicit @testCase)
})
} | Format-Table TestId, Debug, IgnorePSBoundParameters, IgnoreDebugPreference, IgnorePSDebugContext, TD, TIE, TII -AutoSize
以下是上面的输出:
TestId Debug IgnorePSBoundParameters IgnoreDebugPreference IgnorePSDebugContext TD TIE TII
------ ----- ----------------------- --------------------- -------------------- -- --- ---
1 False False False False False False False
2 True False False False True True True
3 False True False False False False False
4 True True False False True True True
5 False False True False False False False
6 True False True False True True False
7 False True True False False False False
8 True True True False False False False
9 False False False True False False False
10 True False False True True True True
11 False True False True False False False
12 True True False True True True True
13 False False True True False False False
14 True False True True True True False
15 False True True True False False False
16 True True True True False False False
具有向后兼容性的示例模板脚本(以及一些注释) 所以,就像我们做检查一样,你可以做如下事情:
[CmdletBinding()]
Param()
# ... some code here creating variables or whatnot ...
if ($DebugPreference -ne "SilentlyContinue") {
# in debug
$messageProperties.To = "$env:username@company.com"
} else {
# not debug
$messageProperties.To = "prodmailbox@company.com"
}
您能否在PowerShell脚本中为这些选项中的每一个提供一个示例?让我提出建议,更符合SO的精神(作为解决特定编程问题的程序员到程序员资源):使用web搜索查找示例(如有必要),编写一个脚本。如果脚本有问题,请将其添加到OP并更新您的问题。与猜测不同,您是否可以向脚本传递一个开关,告诉它当前状态(即“调试”或“发布”)。您可以将开关的默认值设置为“Debug”
[CmdletBinding()]
Param()
# ... some code here creating variables or whatnot ...
if ($DebugPreference -ne "SilentlyContinue") {
# in debug
$messageProperties.To = "$env:username@company.com"
} else {
# not debug
$messageProperties.To = "prodmailbox@company.com"
}