Write-Error 在 class 方法内部使用时不会产生有用的信息 |电源外壳
Write-Error doesn't result useful information when used inside class methods | Powershell
我使用了有和没有 class 的方法,Write-Error 似乎产生了不同的输出。在 class 的情况下,它不指定 函数并且行号始终为 1,1
function oper1() {
Try {
[string] $cmd = ".\some_exe_which_does_not_exist.exe"
iex $cmd
}
Catch {
Write-Error $_.Exception.Message
}
}
oper1
上面的输出:
oper1 : The term '.\some_exe_which_does_not_exist.exe' is not
recognized as the name of a cmdlet, function, script file, or operable
program. Check the spelling of the name, or if a path was included,
verify that the path is correct and try again. At
F:\debug\encryption_concat_tests\Untitled1.ps1:11 char:1
+ oper1
+ ~~~~~
+ CategoryInfo : NotSpecified: (:) [Write-Error], WriteErrorException
+ FullyQualifiedErrorId : Microsoft.PowerShell.Commands.WriteErrorException,oper1
当我在 class 中包含相同的函数时,我得到了这个:
class Operator {
[void] oper1() {
Try {
[string] $cmd = ".\some_exe_which_does_not_exist.exe"
iex $cmd
}
Catch {
Write-Error $_.Exception.Message
}
}
}
[Operator] $operator = New-Object Operator
$operator.oper1()
The term '.\some_exe_which_does_not_exist.exe' is not recognized as
the name of a cmdlet, function, script file, or operable program.
Check the spelling of the name, or if a path was included, verify
that the path is correct and try again. At line:1 char:1
+ F:\debug\encryption_concat_tests\Untitled1.ps1
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : NotSpecified: (:) [Write-Error], WriteErrorException
+ FullyQualifiedErrorId : Microsoft.PowerShell.Commands.WriteErrorException
classes 中的方法出现这种行为的原因可能是什么?
顺便说一句:Invoke-Expression
(iex
) should generally be avoided; definitely - 只需直接调用它,如下所示。
在 PowerShell class 方法中:
不要使用 Write-Error
,因为 classes 不是为了发出 非终止 错误而设计的。
- 您看到任何输出的唯一原因是 错误 从 PowerShell Core 7.0.0-rc.3 开始,方法的 return 类型发生成为
[void]
- 参见 GitHub issue #5331.
相反,仅通过使用 Throw
语句 抛出 或 不 捕获错误来传达错误终止 错误(包括使用 -ErrorAction Stop
调用 .NET 方法和 cmdlet 的异常)。
- 注意:
Throw
和 -ErrorAction Stop
(或 $ErrorActionPreference = 'Stop'
)创建 script-terminating(线程终止)错误,而抛出异常通过 .NET 方法(未在 class 方法中捕获并重新抛出)仅创建 statement-terminating 错误;也就是说,虽然 class 方法主体立即终止,但默认情况下在调用者中继续执行;后者也适用于未找到可执行文件的调用运算符 (&
)、1 / 0
等表达式中的错误以及发出语句终止错误(它们可以报告的最严重错误类型)的 cmdlet 调用没有他们被提升为脚本-终止-ErrorAction Stop
;有关 PowerShell 复杂错误处理的全面概述,请参阅 this GitHub docs issue。
请参阅 了解更多关于 class 方法中的错误处理和流输出行为的信息。
这是您的代码的更正版本。
class Operator {
[void] oper1() {
Try {
# Try to invoke a non-existent executable.
& ".\some_exe_which_does_not_exist.exe"
}
Catch {
# Re-throw the error.
# Alternatively, don't use try / catch, but the error
# then only aborts the method call, not the entire script.
Throw
}
}
}
$operator = [Operator]::new()
$operator.oper1()
我也有这个问题!但我真的很想弄清楚如何从函数中输出信息和 return 所需的信息类型!
我使用 Write-Warning
解决了这个问题
[bool] hidden AddUserToGroup([Microsoft.ActiveDirectory.Management.ADGroup]$group, [Microsoft.ActiveDirectory.Management.ADUser]$user)
{
try
{
Add-ADGroupMember -Server $this.server -Identity $group -Members $user;
return $true;
}
catch [System.SystemException]
{
Write-Warning $_.Exception.Message;
return $false;
}
}
我使用了有和没有 class 的方法,Write-Error 似乎产生了不同的输出。在 class 的情况下,它不指定 函数并且行号始终为 1,1
function oper1() {
Try {
[string] $cmd = ".\some_exe_which_does_not_exist.exe"
iex $cmd
}
Catch {
Write-Error $_.Exception.Message
}
}
oper1
上面的输出:
oper1 : The term '.\some_exe_which_does_not_exist.exe' is not recognized as the name of a cmdlet, function, script file, or operable program. Check the spelling of the name, or if a path was included, verify that the path is correct and try again. At F:\debug\encryption_concat_tests\Untitled1.ps1:11 char:1 + oper1 + ~~~~~ + CategoryInfo : NotSpecified: (:) [Write-Error], WriteErrorException + FullyQualifiedErrorId : Microsoft.PowerShell.Commands.WriteErrorException,oper1
当我在 class 中包含相同的函数时,我得到了这个:
class Operator {
[void] oper1() {
Try {
[string] $cmd = ".\some_exe_which_does_not_exist.exe"
iex $cmd
}
Catch {
Write-Error $_.Exception.Message
}
}
}
[Operator] $operator = New-Object Operator
$operator.oper1()
The term '.\some_exe_which_does_not_exist.exe' is not recognized as the name of a cmdlet, function, script file, or operable program. Check the spelling of the name, or if a path was included, verify that the path is correct and try again. At line:1 char:1 + F:\debug\encryption_concat_tests\Untitled1.ps1 + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + CategoryInfo : NotSpecified: (:) [Write-Error], WriteErrorException + FullyQualifiedErrorId : Microsoft.PowerShell.Commands.WriteErrorException
classes 中的方法出现这种行为的原因可能是什么?
顺便说一句:Invoke-Expression
(iex
) should generally be avoided; definitely
在 PowerShell class 方法中:
不要使用
Write-Error
,因为 classes 不是为了发出 非终止 错误而设计的。- 您看到任何输出的唯一原因是 错误 从 PowerShell Core 7.0.0-rc.3 开始,方法的 return 类型发生成为
[void]
- 参见 GitHub issue #5331.
- 您看到任何输出的唯一原因是 错误 从 PowerShell Core 7.0.0-rc.3 开始,方法的 return 类型发生成为
相反,仅通过使用
Throw
语句 抛出 或 不 捕获错误来传达错误终止 错误(包括使用-ErrorAction Stop
调用 .NET 方法和 cmdlet 的异常)。- 注意:
Throw
和-ErrorAction Stop
(或$ErrorActionPreference = 'Stop'
)创建 script-terminating(线程终止)错误,而抛出异常通过 .NET 方法(未在 class 方法中捕获并重新抛出)仅创建 statement-terminating 错误;也就是说,虽然 class 方法主体立即终止,但默认情况下在调用者中继续执行;后者也适用于未找到可执行文件的调用运算符 (&
)、1 / 0
等表达式中的错误以及发出语句终止错误(它们可以报告的最严重错误类型)的 cmdlet 调用没有他们被提升为脚本-终止-ErrorAction Stop
;有关 PowerShell 复杂错误处理的全面概述,请参阅 this GitHub docs issue。
- 注意:
请参阅
这是您的代码的更正版本。
class Operator {
[void] oper1() {
Try {
# Try to invoke a non-existent executable.
& ".\some_exe_which_does_not_exist.exe"
}
Catch {
# Re-throw the error.
# Alternatively, don't use try / catch, but the error
# then only aborts the method call, not the entire script.
Throw
}
}
}
$operator = [Operator]::new()
$operator.oper1()
我也有这个问题!但我真的很想弄清楚如何从函数中输出信息和 return 所需的信息类型!
我使用 Write-Warning
[bool] hidden AddUserToGroup([Microsoft.ActiveDirectory.Management.ADGroup]$group, [Microsoft.ActiveDirectory.Management.ADUser]$user)
{
try
{
Add-ADGroupMember -Server $this.server -Identity $group -Members $user;
return $true;
}
catch [System.SystemException]
{
Write-Warning $_.Exception.Message;
return $false;
}
}