Service Pack 2 prevents an on-change workflow from starting itself

Пакет обновления 2 (SP2) запрещает рабочему процессу, запускаемому при изменении, запускать самого себя

Всем привет, с вами снова Стивен. Я пишу о SharePoint Designer. Я расскажу об исправлении, включенном в пакет обновления 2 для Office SharePoint Server 2007 и Windows SharePoint Services 3.0. Это исправление влияет на рабочие процессы, разработанные в SharePoint Designer 2007. После этого я покажу, как можно специально создать цикл рабочего процесса, используя два процесса вместо одного.

До появления пакета обновления 2 было слишком легко непреднамеренно разработать рабочий процесс, который запускает сам себя и таким образом создает бесконечный цикл. Например, рассмотрим такой сценарий:

1) Рабочий процесс запускается при изменении элемента.

2) Рабочий процесс обновляет (или изменяет) текущий элемент (например, с помощью задания поля в действии текущего элемента).

3) Поскольку рабочий процесс изменяет элемент, он запускает сам себя.

Таким образом, если имеется рабочий процесс, запускаемый при изменении, который отправляет сообщение электронной почты, а затем обновляет текущий элемент, вы можете быстро получить в свой почтовый ящик несколько сотен сообщений.

После установки на сервер пакета обновления 2 становится невозможной ситуация, при которой рабочий процесс, запускающийся при изменении элемента, запускает сам себя, изменяя или обновляя текущий элемент. Такой сценарий бесконечного цикла невозможен:

clip_image002

Однако многие разработчики создавали рабочие процессы, которые фактически использовали бесконечные циклы. Например, можно было разработать рабочий процесс, запускаемый при изменении, который выполняет в бесконечном цикле элемент задачи, отправляя соответствующие ежедневные напоминания, пока задача не будет помечена как завершенная. Рабочий процесс запускает сам себя, обновляя столбец счетчика, который добавлен в список только для этой цели. И рабочий процесс содержит правило, которое останавливает или "замыкает" его при выполнении некоторого условия — в данном случае рабочий процесс останавливается без изменения текущего элемента, если выполняется условие "состояние задачи" = "завершена". После появления пакета обновления 2 этот рабочий процесс будет фактически прерван, так как не сможет запускать сам себя.

Пакет обновления 2 не блокирует бесконечные циклы, которые могут быть полезны, но для воссоздания того, что работало раньше, следует разработать два (или более) рабочих процессов, запускаемых при изменении, которые будут запускать друг друга. Два рабочих процесса, запускаемых при изменении, которые запускают друг друга, обновляя или изменяя текущий элемент, — это сценарий "совместной рекурсии":

clip_image004

Кроме того, очень распространена реализация рабочего процесса , основанного на состоянии, с помощью нескольких более коротких рабочих процессов, которые запускают друг друга. Например, может использоваться список с полем состояния и несколько рабочих процессов, запускаемых при изменении, прикрепленных к этому списку. В конце каждого из этих рабочих процессов содержится действие, которое обновляет поле состояния. Таким образом один рабочий процесс запускает несколько других, обновляя состояние, а затем эти рабочие процессы проверяют значение в поле состояния, чтобы определить, должны ли они продолжить выполнение или остановиться. Такой основанный на состоянии рабочий процесс также является сценарием "совместной рекурсии", поскольку один рабочий процесс запускает множество других рабочих процессов, запускаемых при изменении, изменяя или обновляя текущий элемент. Пакет обновления 2 не блокирует этот тип рабочих процессов, основанных на состоянии, который, в свою очередь, основан на совместной рекурсии.

Краткий обзор

· До появления пакета обновления 2 одиночный рабочий процесс, запускаемый при изменении, мог войти в бесконечный цикл, обновляя текущий элемент и таким образом запуская самого себя.

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

· Напомню, что никогда не было возможности создать бесконечный цикл с помощью рабочего процесса, запускаемого при создании, создающего элемент в текущем списке. У каждого рабочего процесса есть свойство, содержащее "список рабочих процессов, которые он не может запустить", — это свойство используется для предотвращения зацикливания рабочих процессов, которые запускаются при создании элемента.

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

Создание циклов до появления пакета обновления 2

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

Предположим, что для списка задач с именем "Задачи группы" (Team Tasks) необходимо разработать рабочий процесс, который будет ежедневно отправлять напоминания, пока задача не будет помечена как завершенная.

Сначала добавим в список столбец с именем "Счетчик" (Counter) и значением по умолчанию 0.

clip_image006

Необходимо скрыть столбец счетчика в формах списка ("Создать элемент" (New Item), "Изменить элемент" (Edit Item)), чтобы только данный рабочий процесс мог осуществлять доступ к нему и обновлять его. На странице параметров списка щелкните "Дополнительные параметры" (Advanced Settings) и разрешите управление типами контента.

clip_image008

На странице параметров списка щелкните тип контента и на следующей странице щелкните столбец счетчика. Сделайте столбец счетчика скрытым. Выполните эти действия для каждого типа контента в списке.

clip_image010

После создания столбца счетчика и скрытия его отображения в формах все готово для разработки рабочего процесса.

Рабочий процесс "Ежедневное напоминание" (Daily Reminder) должен запускаться при каждом создании или изменении элемента.

clip_image012

На первом этапе проверяются два условия: (1) если задача помечена как завершенная, рабочий процесс останавливается. Это правило "замыкает" цикл, когда задача помечается как завершенная. (2) Если задача не завершена, рабочий процесс проверяет, находится ли дата выполнения в будущем (дата выполнения больше, чем текущая дата). Если это так, рабочий процесс приостанавливается до наступления даты выполнения, так как до этого момента отправка напоминаний не требуется.

clip_image014

На втором этапе снова проверяется условие завершения задачи (в случае, если рабочий процесс был приостановлен до наступления даты выполнения на предыдущем этапе и задача была завершена за этот промежуток времени). Если задача все еще не завершена, рабочий процесс приостанавливается на один день.

clip_image016

На третьем этапе проверяется условие завершения задачи, пока рабочий процесс был приостановлен; если это так, рабочий процесс останавливается.

Если задача не завершена, рабочий процесс: (1) отправляет напоминание по электронной почте; (2) задает переменную CurrentCount, выполняя поиск элемента счетчика или поля счетчика; (3) добавляет 1 к переменной CurrentCount и сохраняет это значение в переменной NewCount; (4) задает для столбца счетчика значение, сохраненное в переменной NewCount.

По существу этот этап увеличивает значение столбца счетчика на 1 при каждом выполнении рабочего процесса, поэтому по столбцу счетчика можно определить, сколько напоминаний было отправлено. Самое важное, что действие "Задать поле в текущем элементе" (Set Field in Current Item) в конце этого этапа "изменяет" текущий элемент, таким образом заставляя рабочий процесс запустить самого себя и создать цикл.

clip_image018

Создание циклов после появления пакета обновления 2

После появления пакета обновления 2 эффект зацикливания все же может быть достигнут, но для этого требуется разработка двух рабочих процессов, которые запускают друг друга (совместная рекурсия), вместо одного рабочего процесса, запускающего самого себя.

Здесь будет использоваться (1) рабочий процесс "Счетчик" (Counter), увеличивающий значение счетчика, и (2) рабочий процесс "Исполнитель" (Worker), фактически отправляющий напоминание по электронной почте.

Первый рабочий процесс — "Счетчик"

Как было указано выше, в списке необходимо создать столбец "Счетчик" (Counter) со значением по умолчанию 0, разрешить управление типами контента и сделать это поле скрытым для всех типов контента в списке.

clip_image006[1]

Для данного проекта с двумя рабочими процессами требуется второй столбец, SendMail, который будет действовать как флаг для рабочего процесса "Исполнитель" (Worker). Значением по умолчанию должно быть "Нет" (No) — в противном случае любое изменение элемента задачи приведет к отправке напоминания.

clip_image020

Рабочий процесс "Счетчик" (Counter) будет запускаться при создании или изменении элемента.

clip_image022

На первом этапе проверяется состояние задачи — если задача завершена, рабочий процесс счетчика останавливается.

clip_image024

Если дата выполнения задачи еще не наступила (больше, чем текущая дата), второй этап приостанавливается до наступления даты выполнения, поскольку до наступления срока выполнения задачи отправка напоминаний не требуется.

clip_image026

На третьем этапе проверяется завершение задачи за то время, на которое рабочий процесс был приостановлен на предыдущем этапе. Если задача все еще не завершена, рабочий процесс приостанавливается на один день.

clip_image028

На последнем этапе снова проверяется состояние, чтобы определить, была ли задача завершена во время предыдущей приостановки на день. Если нет, рабочий процесс обновляет текущий элемент, (1) увеличивая значение столбца счетчика на 1 и (2) задавая для флага SendMail значение "Да" (Yes) (значение по умолчанию "Нет").

clip_image030

Второй рабочий процесс — "Исполнитель" (Worker)

Рабочий процесс "Счетчик" (Counter) завершается обновлением (изменением) текущего элемента. Эти обновления запускают рабочий процесс "Исполнитель" (Worker), который настроен на запуск при изменении элемента.

clip_image032

Рабочий процесс "Исполнитель" просто проверяет значение флага SendMail; при значении "Да" (Yes) рабочий процесс отправляет сообщение напоминания и снова задает для флага значение "Нет" (No).

Присваивание флагу SendMail значения "Нет" (No) — это изменение, которое запускает рабочий процесс "Счетчик". Рабочие процессы "Счетчик" и "Исполнитель" будут запускать друг друга, отправляя ежедневные напоминания, пока задача не будет помечена как завершенная.

clip_image034

Альтернативным образом вместо бесконечного цикла можно предписать рабочему процессу "Исполнитель" увеличить количество уведомлений о задаче при достижении определенного значения столбца счетчика — скажем, 5 напоминаний. На следующем этапе выполняются разные ветви в зависимости от значения счетчика напоминаний. При достижении счетчиком напоминаний значения 5 рабочий процесс отправляет сообщение руководителю, адрес электронной почты которого можно либо "жестко задать" в действии отправки сообщения, либо получить из списка с помощью поиска рабочего процесса.

clip_image036

Также можно предписать рабочему процессу "Исполнитель" переназначить задачу для другого исполнителя или группы после отправки определенного числа напоминаний. В данном действии рабочий процесс переназначает задачу для группы SharePoint, состоящей из участников группы, ответственных за отслеживание таких медленно выполняемых задач.

clip_image038

Если необходимо завершить цикл при достижении определенного значения счетчика, не забудьте также добавить ветвь в первый этап рабочего процесса "Счетчик", а не в рабочий процесс "Исполнитель". Эта ветвь останавливает цикл, когда столбец счетчика достигает значения 6.

clip_image040

Надеюсь, эта информация окажется для вас полезной.

— Стивен

Это локализованная запись блога. Исходная статья находится по адресу Service Pack 2 prevents an on-change workflow from starting itself

!>

!-->