Я использую Ново-объектную Систему. Управление. Автоматизация. PipelineStoppedException Для остановки конвейера хорошо.. работы..
Но как я могу протестировать в следующем cmdlet, если был остановлен?
Foo1 | foo2 | foo3
Остановитесь в foo1, но переходит к foo2. Я хочу протестировать, если был остановлен в foo1 для остановки также в каждой функции
function foo1 {
process {
try {
#do
} catch {
New-Object System.Management.Automation.PipelineStoppedException
}
}
}
и все еще идя в следующий cmdlet, как зашел в ошибку, которую я хочу остановить в каждом затем cmdlets..:)
Спасибо!!!
Вы неправильно поняли, как работают конвейеры. Когда последовательность объектов отправляется в конвейер, каждый отдельный объект проходит через весь конвейер до обработки следующего объекта. Рассмотрим следующие функции:
function First() {
process {
Write-Host "First: $_";
$_
}
}
function Second() {
process {
Write-Host "Second: $_";
}
}
Первая функция выводит «First» и значение объекта конвейера, а затем передает объект. Второй просто выводит «Second» и объект конвейера. Теперь, когда вы отправляете массив в конвейер, состоящий из этих двух функций, что вы ожидаете увидеть?
Фактический результат таков:
PS C:\Users\Lauri> ,1,2,3 | first | second
First: 1
Second: 1
First: 2
Second: 2
First: 3
Second: 3
Теперь, имея под рукой эту информацию, мы можем сделать вывод, что когда функция или командлет в конвейере вызывает исключение, чтобы остановить обработку, весь конвейер останавливается. Но это тоже легко проверить.Давайте изменим First следующим образом:
function First() {
process {
throw New-Object System.Management.Automation.PipelineStoppedException
}
}
, а затем снова попробуем тот же конвейер:
PS C:\Users\Lauri> ,1,2,3 | first | second
Результат пуст, потому что в момент, когда первый объект передается в «First», он генерирует исключение, и весь конвейер прерывается.
Таким образом, вы не можете проверить, была ли обработка прервана дальше по конвейеру,потому что казнь никогда не дойдет до этого.
[Edit] Еще один интересный лакомый кусочек: блоки Begin всех функций запускаются первыми, а блоки End все запускаются последними, поэтому, если вы генерируете исключение в блоке Process выше по конвейеру, блок Begin все функции конвейера уже будут запущены:
function First() {
begin {
Write-Host "First begin"
}
process {
throw New-Object System.Management.Automation.PipelineStoppedException
}
end {
Write-Host "First end"
}
}
function Second() {
begin {
Write-Host "Second begin"
}
process {
Write-Host "Second: $_"
}
end {
Write-Host "Second end"
}
}
PS C:\Users\Lauri> ,1,2,3 | first | second
First begin
Second begin
[Edit 2]
Еще одно потенциально интересное последствие состоит в том, что если возникает исключение и вы хотите, чтобы конвейер продолжался после этого, вам нужно будет вернуть что-то в блоке catch, который его улавливает:
function CauseException {
throw New-Object Exception
}
function First() {
process {
try {
CauseException
} catch {
"Error"
}
}
}
function Second() {
process {
Write-Host "Second: $_"
}
}
PS C:\Users\Lauri> ,1,2,3 | first | second
Second: Error
Second: Error
Second: Error