Spring Web Flow — выполнение действий (executing actions)

6. Выполнение действий (execution actions)

6.1. Введение

Эта глава покажет вам как использовать элемент action-state для управления выполнения действия в определенной точке внутри потока. Так же будет показано использование элемента decision-state, позволяющего создавать маршрутизация потока на основе принятого решения. В конце будут показаны несколько примеров внедрения действий из различных возможных точек внутри потока.

6.2. Определение состояний действия (action states)

Используйте элемент action-state, когда вы желаете внедрить действие, на основании результата которого будет выполнен переход в другое состояние:

Полный пример ниже иллюстрирует поток interview, который использует action-state из примера выше для определения нужно ли больше вопросов для завершения интервью:

6.3. Определение состояний решения (decision states)

Используйте элемент decision-state как альтернативу элементу action-state для маршрутизации выбора, используя удобный синтаксис if/else. Пример ниже демонстрирует состояние moreAnswersNeeded из примера выше, которое теперь реализуется через decision-state вместо action-state:

6.4. Маппинг результата действия

Действия часто вызывают методы для обычных Java объектов. Когда они вызываются из action-state или decision-state, возвращаемый результат может быть использован для управления переходами состояния. Поскольку переход был запущен событием, то необходимо, чтобы возвращаемое методом значение сначала было преобразовано в Event объект. Следующая таблица поясняет как общие типы возвращаемых значений преобразовывают к Event объектам:

Таблица 6.1. Преобразование возвращаемого значения метода Action к event id

Возвращаемое значение метода Преобразованный Event идентификатор выражения
java.lang.String the String value
java.lang.Boolean yes (for true), no (for false)
java.lang.Enum the Enum name
any other type success

 

Это проиллюстрировано в следующем примере с использованием action-state, который вызывает метод, возвращающий значение типа boolean:

6.5. Реализация действий

В то время, как написание кода действий используя логику POJO, является наиболее распространенным, есть несколько других вариантов реализации действий. Иногда нужно написать код действия, которому будет необходим доступ к контексту потока. Вы всегда можете вызвать POJO метод и передать ему значение flowRequestContext в качестве переменной EL. Кроме того, вы можете реализовать интерфейс Action или расширить класс от базового класса MultiAction. Эти варианты обеспечивают полную безопасность типов, когда имеется естественная связь между вашим кодом и API Spring Web Flow. Примеры каждого из этих подходов приведены ниже.

6.5.1. Вызов действий POJO

6.5.2. Вызов пользовательской реализации Action

6.5.3. Вызов реализации MultiAction

6.6. Исключения в действиях

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

6.6.1 Перехват служебных исключений в действиями POJO

В следующем примере вызванное действие перехватывает служебное исключение, добавляет сообщение об ошибке в контекст и возвращает идентификатор события:

6.6.2. Перехват служебных исключений с MultiAction

Этот пример эквивалентен предыдущему, но выполняется с помощью расширения от MultiAction вместо обычного POJO действия. MultiAction требует, чтобы методы действия имели сигнатуру Event${methodName}(RequestContext), что позволит обеспечить безопасность типов, в то время как действия POJO позволяют большую свободу.

6.6.3. Использование элемента exception-handler

В целом, для перехвата исключений в действиях и возвращения результата события, который управлять стандартными переходами, рекомендуется добавлять подэлемент exception-handler для любого состояния с указанием бина в качестве атрибута, который ссылается на бин типа FlowExecutionExceptionHandler. Это дополнительная возможность, которая при неправильном использовании, может привести выполнение потока в недопустимое состояние. Посмотрите встроенную реализацию TransitionExecutingFlowExecutionExceptionHandler в качестве примера корректной реализации.

6.7. Другие примеры выполнения действий

6.7.1. on-start

В примере показано действие, которое создает новый объект Booking вызовом сервисного метода:

6.7.2. on-entry

Пример показывает действие на входе в состояние, которое устанавливает специальную переменную fragments, которая позволит view-state частично обновлять фрагмент его представления:

6.7.3. on-exit

Следующий пример показывает действие при выходе из состояния, которое реализует блокирование в момент выполнения редактирования:

6.7.4. on-end

Здесь показано эквивалентное поведение по блокировке объекта, используя действия при старте и выходе:

6.7.5. on-render

В данном примере показывается действие on-render, которое загружает список отелей для отображения до того как представление будет отрисовано:

6.7.6. on-transition

Ниже показано действие при переходе, в котором добавляется атрибут результата события подпотока в коллекцию:

6.7.7. Названные действия

Следующий пример демонстрирует как выполнить цепочку действий в action-state. Имя каждого действия становится квалификатором для результата события действия.

В этом примере поток выполнит переход к showResults, когда thingTwo успешно завершится.

6.7.8. Поточные действия

Иногда действие должно выдавать поток (stream) в обратном ответе клиенту. В качестве примера можно привести поток, создающий PDF документ при вызове события печати. Это может быть достигнуто с помощью действия, преобразующего контент в поток и записывающего статус «Response Complete» в ExternalContext. Флаг responseComplete говорит приостановить обновление ответа от view-state, потому что этим займется другой объект.

В этом примере, когда будет вызвано событие печати, поток вызовет printBoardingPassAction. Действие будет создавать PDF и затем отметит ответ как выполненный.

6.7.9. Обработка загрузки файлов

Другой частой задачей при использовании Web Flow является обработка многокомпонентной загрузки файлов в комбинации с Spring MVC MultipartResolver. Один раз правильно зарегистрировав обработчик (см. здесь) и сконфигурировав сабмит HTML формы с enctype=»multipart/form-data», вы можете легко обрабатывать загрузку файлов в действиях при переходах.

Обратите внимание, что пример выше не подходит при использовании Spring Web Flow и JSF. Как это сделать с JSF смотрите в  Section 13.10, “Handling File Uploads with JSF”.

Создав такую форму:

и объект в java коде для обработки загрузки:

вы можете выполнять загрузку файлов, используя действия при переходе, как это показано в следующем примере:

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

Share Button
0
5407 Total Views 1 Views Today

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