Write-Error не дает полезной информации при использовании внутри методов класса | Powershell
Я использовал метод с классом и без него, и похоже, что Write-Error дает разные результаты. В случае класса он не указывает функцию, а номер строки всегда 1,1
function oper1() {
Try {
[string] $cmd = ".\some_exe_which_does_not_exist.exe"
iex $cmd
}
Catch {
Write-Error $_.Exception.Message
}
}
oper1
Вывод для выше:
oper1: термин '.\some_exe_which_does_not_exist.exe' не распознается как имя командлета, функции, файла сценария или работающей программы. Проверьте написание имени или, если был включен путь, проверьте правильность пути и повторите попытку. В F:\debug\encryption_concat_tests\Untitled1.ps1:11 символов: 1 + oper1 + ~~~~~ + CategoryInfo: NotSpecified: (:) [Write-Error], WriteErrorException + FullyQualifiedErrorId: Microsoft.PowerShell.Commands.WriteErrorException,oper1
Когда я включил ту же функцию в класс, я получил следующее:
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()
Термин '.\ Some_exe_which_does_not_exist.exe' не распознается как имя командлета, функции, файла сценария или работающей программы. Проверьте написание имени или, если путь был включен, убедитесь, что путь правильный, и повторите попытку. В строке: 1 символ: 1 + F:\debug\encryption_concat_tests\Untitled1.ps1 + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + CategoryInfo: NotSpecified: (:) [Write-Error], WriteErrorException + FullyQualifiedErrorId: Microsoft.PowerShell.Commands.WriteErrorException
В чем может быть причина такого поведения методов внутри классов?
2 ответа
Как в сторону: Invoke-Expression
(iex
) обычно следует избегать; определенно не используйте его для вызова внешней программы - просто вызывайте ее напрямую, как показано ниже.
В методах класса PowerShell:
Не использовать
Write-Error
, поскольку классы не предназначены для выдачи непрекращающихся ошибок.- Единственная причина, по которой вы вообще видите какой-либо вывод, - это ошибка PowerShell Core 7.0.0-rc.3 с методами, возвращаемым типом которых является
[void]
- см. эту проблему на GitHub.
- Единственная причина, по которой вы вообще видите какой-либо вывод, - это ошибка PowerShell Core 7.0.0-rc.3 с методами, возвращаемым типом которых является
Вместо этого сообщайте об ошибках, просто бросая их
Throw
оператор или не обнаруживая завершающие ошибки (которые включают исключения из методов.NET и вызовов командлетов с-ErrorAction Stop
).- Примечание:
Throw
а также-ErrorAction Stop
(или$ErrorActionPreference = 'Stop'
) создавать ошибки, завершающие сценарий(завершающие пространство выполнения), в то время как исключения, создаваемые методом.NET (не перехваченные и не генерируемые повторно в методе класса), создают только ошибки, завершающие выполнение оператора; то есть, хотя тело метода класса завершается сразу, выполнение по умолчанию продолжается в вызывающей программе; последнее также относится к оператору вызова (&
) не удается найти исполняемый файл, ошибки в таких выражениях, как1 / 0
, и вызовы командлетов, которые выдают ошибки завершения оператора (наиболее серьезный тип ошибки, о котором они могут сообщить) без их повышения до ошибок завершения сценария с помощью-ErrorAction Stop
; см. этот выпуск документации GitHub, чтобы получить исчерпывающий обзор сложной обработки ошибок PowerShell.
- Примечание:
См. Этот ответ для получения дополнительной информации об обработке ошибок и поведении потокового вывода, в частности, в методах класса.
Вот исправленная версия вашего кода.
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-Object Operator
$operator.oper1()
у меня тоже такая проблема! Но очень хотелось разобраться, как выводить информацию и возвращать нужный тип информации из функции! Я решил проблему с помощью
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;
}
}