PowerShell Workflows: Механизм заданий – Hey, Scripting Guy! Blog

Резюме: Microsoft PowerShell MVP, Richard Siddaway продолжает свою серию статей рассказом о механизме заданий (job engine).

Microsoft Scripting Guy, Ed Wilson на связи. Сегодня я публикую четвертую часть в серии статей о рабочих процессах Windows PowerShell за авторством Windows PowerShell MVP и Honorary Scripting Guy Richard Siddaway.

Заметка: Первая статья, PowerShell Workflows: Основы рассказывает об основных концепциях рабочих процессов. Вторая, PowerShell Workflows: Ограничения, рассматривает ограничения, с которыми вы можете столкнуться при написании рабочих процессов. Третья статья, PowerShell Workflows: Вложения, рассказывает о вложении рабочих процессов. Перед тем как читать эту статью, вам стоит ознакомиться с предыдущими.

Richard Siddaway написал несколько гостевых постов, кроме этого он является автором двух книг по Windows PowerShell. Последняя его книга, PowerShell in Depth написана в соавторстве двумя другими MVP – Don Jones и Jeffrey Hicks.

Теперь слово тебе, Richard.

Давайте вспомним первый рабочий процесс в этой серии статей – “Hello World”.

workflow hello {

«Hello World»

}

Вы могли запустить его следующим образом:

PS> hello

Hello World

Запускаем рабочий процесс в качестве задания

Все рабочие процессы обладают способностью запускаться с качестве задания (Job) Windows PowerShell:

PS> hello -AsJob -JobName w1

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

9 w1 PSWorkflowJob NotStarted True localhost

Вы можете указать параметр –AsJob, который запускает рабочий процесс в виде задания, а также вы можете использовать параметр –JobName, который позволяет вам указать имя для задания. Заметьте, что в других командлетах, которые вы можете запустить в качестве задания, например, командлетах WMI, вы не можете указать имя для задания.

Еще одна важная деталь, это PSJobTypeName – он равен PSWorkflowJob. Это новая категория заданий, введенная в Windows PowerShell 3.0 специально для рабочих процессов.

После того, как вы запустите рабочий процесс в качестве задания, с ним можно взаимодействовать как с любым другим заданием.

PS> Get-Job

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

9 w1 PSWorkflowJob Completed True localhost

PS> Receive-Job -Name w1

Hello World

По определению, рабочие процессы – это достаточно длительные задания, интерактивное взаимодействие с которыми не требуется. Поэтому они идеально подходят для выполнения в качестве заданий Windows PowerShell.

Естественно это не все, что касается рабочих процессов и их взаимодействия с механизмом заданий Windows PowerShell – об этом я мог бы писать бесконечно.

Останавливаем и запускаем рабочие процессы

Рабочие процессы построены на основе заданий Windows PowerShell. Благодаря этому вам доступна такая возможность как приостанавливать и возобновлять рабочие процессы. Давайте сымитируем долгосрочный рабочий процесс:

workflow test-wfsuspension {

Start-Sleep -seconds 10

Suspend-Workflow

Get-ChildItem

}

Рабочий процесс подождет 10 секунд, а затем приостановит свое выполнение вызовом Suspend-Workflow.

После того как рабочий процесс приостановлен, вы можете увидеть нечто подобное:

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

7 Job7 PSWorkflowJob Suspended True localhost

Заметьте, что State установлен в Suspended. Данные и состояние рабочего процесса были сохранены на диск.

Вы можете возобновить выполнение рабочего процесса командлетом Resume-Job:

PS> Resume-Job -Id 7

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

7 Job7 PSWorkflowJob Suspended True localhost

PS> Get-Job

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

7 Job7 PSWorkflowJob Completed True localhost

Данные, выводимые командлетом Resume-Job могут сбить вас с толку. В качестве состояния он показывает Suspended. Однако, командлет сообщает о статусе задания до того, как он попытается возобновить его. После его возобновления задание завершает свою работу и его выходные данные становятся доступными как обычно.

Это полезное свойство, но куда более полезной является возможность приостановить задание рабочего процесса, а затем возобновить его из другой сессии Windows PowerShell! Если вы удалите старые задания и перезапустите test-wfsuspension, вы получите нечто подобное:

PS> test-wfsuspension

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

9 Job9 PSWorkflowJob Suspended True localhost

Я запускаю эту демонстрацию в ISE, однако это будет работать и в консоли Windows PowerShell.

А теперь закройте PowerShell ISE и не сохраняйте никаких файлов. Да, верно. Просто нажмите на маленькую кнопку в верхнем правом углу консоли PowerShell или ISE.

Теперь откройте новую сессию (вам нужно будет запустить ее в повышенными правами). Я снова запущу ISE, но вы можете воспользоваться и консолью PowerShell.

Теперь запускаем командлет Get-Job и… ничего не происходит.

Так, без паники. Импортируйте модуль рабочих процессов и вы снова увидите ваше задание.

PS> Get-Job

PS> Import-Module PSWorkflow

PS> Get-Job

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

8 Job9 PSWorkflowJob Suspended True localhost

Вы можете возобновить задание и после его завершения получить выдаваемые им данные.

Стоит заметить, что Job ID может измениться, хотя имя задания останется прежним.

Приостанавливаем задание рабочего процесса

Есть еще один способ приостановить рабочий процесс – используя командлет Suspend-Job. Начнем с создания рабочего процесса:

workflow test-wfsr {

Start-Sleep -seconds 30

Checkpoint-Workflow

Get-ChildItem

}

Запустим рабочий процесс как задание:

PS> test-wfsr -AsJob

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

11 Job11 PSWorkflowJob Running True localhost

PS> Suspend-Job -Id 11

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

11 Job11 PSWorkflowJob Suspending True localhost

После этого вы можете использовать командлет Suspend-Job, чтобы приостановить задание.

Задание будет находиться в состоянии Suspending, пока рабочий процесс не дойдет до инструкции CheckPoint-Workflow. После этого, статус задания изменится на Suspended.

PS> Get-Job

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

11 Job11 PSWorkflowJob Suspended True localhost

Затем вы можете возобновить задание:

PS> Resume-Job -id 11

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

11 Job11 PSWorkflowJob Suspended True localhost

PS> Get-Job

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

11 Job11 PSWorkflowJob Completed True localhost

В данном случае я возобновил задание в той же сессии.

Важная вещь: командлеты Suspend-Job и Resume-Job работают только с заданиями рабочих процессов. При попытке приостановить любое другое задание вы получите ошибку.

В последнем примере вам нужно было использовать активность Chekpoint-Workflow. Эта активность записывает копию данных и состояния рабочего процесса на диск, чтобы задание могло быть возобновлено. Другими словами, она создает снимок. Если не сделать этого, рабочий процесс не сможет приостановиться и проигнорирует команду приостановления.

Итак, мы рассмотрели две техники приостановления:

  • Если вы хотите приостановить выполнение изнутри рабочего процесса – используйте Suspend-Workflow.
  • Если команда на приостановку должна прийти извне – используйте Checkpoint-Workflow и Suspend-Job.

Контрольные точки

Контрольные точки (checkpoints) – это отличный способ сохранения текущего состояния рабочего процесса, чтобы можно было возобновить его в случае, если прервется сессия или что-то случится с компьютером. Вы можете возобновить выполнение рабочего процесса только с последней контрольной точки – вы не можете выбрать контрольную точку для использования.

Данные контрольных точек сохраняются в вашем пользовательском профиле на машине, с которой вы запустили рабочий процесс. Хотя вы можете создавать контрольные точки после каждой активности, рекомендуется соблюдать некий баланс между временем, необходимым для записи данных и состояния рабочего процесса на диск и временем работы самого рабочего процесса.

Вы уже видели, как используется Checkpoint-Workflow. Кроме него есть еще несколько способов создания контрольных точек:

  • Checkpoint-Workflow – может использоваться после каждой активности, но не внутри блока InlineScript. Немедленно создает контрольную точку.
  • PSPersist (параметр рабочего процесса) – создает контрольные точки перед началом выполнения рабочего процесса, после его завершения, а также после каждой активности. Не оказывает влияния на явным образом определенные контрольные точки рабочего процесса.
  • PSPersist (параметр активности) – создает снимок после завершения активности. Не применяется к выражениям или командам внутри блока InlineScript.
  • $PSPersistPreference (привилегированная переменная) – при установке в true, контрольная точка создается после каждой активности, пока переменная не будет установлена в false. Переменная оказывает влияние только на рабочие процессы.

Если активность находится внутри конвейера, контрольная точка не создается до тех пор, пока не завершится выполнение конвейера. Внутри блока parallel, контрольная точка не создается, пока параллельная обработка не завершится для всех данных, в отличие от блока sequence, где контрольные точки создаются после каждой активности.

Эти правила лучше проиллюстрировать на примере. Используя уже знакомую вам активность Checkpoint-Workflow вы можете создавать контрольные точки после любой активности:

workflow test-wfchkpnt {

Get-WmiObject -Class Win32_ComputerSystem

Checkpoint-Workflow

Get-WmiObject -Class Win32_OperatingSystem

Checkpoint-Workflow

Get-WmiObject -Class Win32_LogicalDisk

Checkpoint-Workflow

}

В следующем примере тот же результат, т.е. создание контрольной точки после каждой активности достигается использованием параметра рабочего процесса –PSPersist.

workflow test-wfchkpnt {

Get-WmiObject -Class Win32_ComputerSystem

Get-WmiObject -Class Win32_OperatingSystem

Get-WmiObject -Class Win32_LogicalDisk

}

test-wfchkpnt –PSPersist

В следующем примере параметр активности –PSPersist используется для создания контрольной точки после каждой активности.

workflow test-wfchkpnt {

Get-WmiObject -Class Win32_ComputerSystem -PSPersist

Get-WmiObject -Class Win32_OperatingSystem -PSPersist

Get-WmiObject -Class Win32_LogicalDisk -PSPersist

}

Подобного результата можно добиться и использованием привилегированной переменной (preference variable) $PSPersistPreference.

workflow test-wfchkpnt {

$pspersistpreference = $true

Get-WmiObject -Class Win32_ComputerSystem

Get-WmiObject -Class Win32_OperatingSystem

Get-WmiObject -Class Win32_LogicalDisk

$pspersistpreference = $false

}

Лично я предпочитаю использовать Checkpoint-Workflow для явного указания мест, где мне нужно создать контрольную точку.

Давайте посмотрим как это работает. Этот простой рабочий процесс создает контрольную точку после каждой итерации цикла.

workflow test-wfchkpnt {

$i = 0

while ($true){

$i++

$i

Checkpoint-Workflow

}

}

Вам нужно запустить рабочий процесс в качестве задания.

PS> test-wfchkpnt -AsJob

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

7 Job7 PSWorkflowJob Running True localhost

PS> Get-Job

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

7 Job7 PSWorkflowJob Running True localhost

После того, как задание проработает несколько секунд, закройте Windows PowerShell.

Откройте новую сессию (с повышенными привилегиями), импортируйте модуль PSWorkflow и просмотрите существующие задания.

PS> Import-Module PSWorkflow

PS> Get-Job

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

8 Job7 PSWorkflowJob Suspended True localhost

PS> Resume-Job -Id 8

Id Name PSJobTypeName State HasMoreData Location

— —- ————- —— ———— ———

8 Job7 PSWorkflowJob Suspended True localhost

PS> Stop-Job -Id 8

PS> Receive-Job -Id 8 -Keep | select -f 3

WARNING: The workflow job «Job7» was stopped. Receive-Job is only displaying par

tial results.

1

2

3

Возобновите задание и дайте ему проработать несколько секунд. Так как наш рабочий процесс – это бесконечный цикл, нам потребуется остановить выполнение задания вручную. Для получения данных введите Receive-Job.

Резюме

Рабочие процессы Windows PowerShell работают с механизмом задач Windows PowerShell. Вы можете запускать рабочие процессы в качестве заданий. Рабочие процессы предоставляют возможность приостанавливать и возобновлять их задания. Создание контрольной точки сохраняет состояние рабочего процесса, что дает возможность возобновить его работу после закрытия сессии Windows PowerShell.

В следующий раз я покажу вам как рабочий процесс можете пережить перезагрузку компьютера.

~Richard.

Автор:

Ed Wilson, Microsoft Scripting Guy

Оригинал:

http://blogs.technet.com/b/heyscriptingguy/archive/2013/01/16/powershell-workflows-job-engine.aspx


Страницы в социальных сетях:

Twitter: https://twitter.com/vsseth
Facebook: https://fb.com/inpowershell
VKontakte: https://vk.com/inpowershell


Реклама

Добавить комментарий

Заполните поля или щелкните по значку, чтобы оставить свой комментарий:

Логотип WordPress.com

Для комментария используется ваша учётная запись WordPress.com. Выход /  Изменить )

Google+ photo

Для комментария используется ваша учётная запись Google+. Выход /  Изменить )

Фотография Twitter

Для комментария используется ваша учётная запись Twitter. Выход /  Изменить )

Фотография Facebook

Для комментария используется ваша учётная запись Facebook. Выход /  Изменить )

w

Connecting to %s