流控制文件很简单,就是根元素是<view>,然后用<view-state>来代表一个一个的页面,用<transition>来代表从一个状态到另外一个状态的跳转,如果有动作要执行就会加在其中。
对于一个普通的java工程师,一般不需要超过1小时就可以熟知这个文件的编写方法,可查阅相关文档。
对于我们的flow,大体上如下所示:
因为图片实在太长,所以我没办法吧整个图片都截下来,这里只截取部分,对于flow定义的xml文件,我完整列在这里,可以供读者参考:
- <?xml version="1.0" encoding="UTF-8"?>
- <flow xmlns="http://www.springframework.org/schema/webflow"
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xsi:schemaLocation="http://www.springframework.org/schema/webflow http://www.springframework.org/schema/webflow/spring-webflow-2.0.xsd">
- <!-- initialize all the variables in the flowScope -->
- <on-start>
- <evaluate expression="envProvisionInitService.initialize(flowRequestContext)" />
- <!-- initialize the flowScope variable:gridList to render the grid list -->
- <!-- <evaluate expression="aerEnvGridService.listAppEnvRequests()"
- result="flowScope.gridListInfoJSONData" />
- -->
- <!-- initialize the flowScope variable: availableServices to be used in hostvip info -->
- <evaluate expression="defineHostVipService.listAvailableServices()"
- result="flowScope.availableServicesInfoJSONData" />
- <set name="flowScope.isViewAction" value="false" type="boolean" />
- </on-start>
- <view-state id="aerEnvList" >
- <on-render>
- <evaluate expression="aerEnvGridService.listAppEnvRequests()" result="flowScope.gridListInfoJSONData" />
- </on-render>
- <transition on="add" to="defineApp" />
- <transition on="confirm" to="aerRequestConfirm" >
- <!-- fetch the data from web service and ready for populating data -->
- <evaluate expression="aerEnvGridService.listEnvProvisionInfoByRequestId(requestParameters.requestId,flowRequestContext)"/>
- <set name="flowScope.isViewAction" value="true" type="boolean" />
- <set name="flowScope.requestId" value="requestParameters.requestId" type="string"/>
- </transition>
- <transition on="approve" to="aerEnvList">
- <evaluate expression="adminService.approve(requestParameters.requestId)" />
- </transition>
- <transition on="close" to="aerEnvList">
- <evaluate expression="adminService.close(requestParameters.requestId)" />
- </transition>
- <transition on="reject" to="aerEnvList">
- <evaluate expression="adminService.reject(requestParameters.requestId)" />
- </transition>
- <transition on="cmdb" to="aerEnvList">
- <evaluate expression="adminService.cmdb(requestParameters.requestId)" />
- </transition>
- </view-state>
- <view-state id="defineApp" >
- <transition on="next" to="defineProject">
- <evaluate expression="defineAppService.createAppInfo(requestParameters.appInfoJSONData)"
- result="flowScope.appInfo" />
- <set name="flowScope.appInfoJSONData" value="requestParameters.appInfoJSONData" type="string"/>
- <set name="flowScope.hasAppInfoData" value="true" type="boolean"/>
- </transition>
- <transition on="cancel" to="aerEnvList" >
- <evaluate expression="defineAppService.removeAppInfo(flowRequestContext)" />
- <evaluate expression="defineProjectService.removeProjectInfo(flowRequestContext)" />
- <evaluate expression="defineHostVipService.removeHostVipInfo(flowRequestContext)" />
- <evaluate expression="defineDBSrvService.removeDBServiceInfo(flowRequestContext)"/>
- </transition>
- </view-state>
- <view-state id="defineProject">
- <transition on="previous" to="defineApp"/>
- <transition on="next" to="defineHostVip">
- <evaluate expression="defineProjectService.createProjectInfo(requestParameters.projectInfoJSONData)"
- result="flowScope.projectInfo" />
- <set name="flowScope.projectInfoJSONData" value="requestParameters.projectInfoJSONData" type="string"/>
- <set name="flowScope.hasProjectInfoData" value="true" type="boolean"/>
- </transition>
- <transition on="cancel" to="aerEnvList">
- <evaluate expression="defineAppService.removeAppInfo(flowRequestContext)" />
- <evaluate expression="defineProjectService.removeProjectInfo(flowRequestContext)" />
- <evaluate expression="defineHostVipService.removeHostVipInfo(flowRequestContext)" />
- <evaluate expression="defineDBSrvService.removeDBServiceInfo(flowRequestContext)"/>
- </transition>
- </view-state>
- <view-state id="defineHostVip">
- <transition on="previous" to="defineProject"/>
- <transition on="next" to="defineDBService">
- <evaluate expression="defineHostVipService.createHostVipInfo(requestParameters.hostVipInfoJSONData, flowRequestContext)"
- result="flowScope.hostVipInfo" />
- <set name="flowScope.hostVipInfoJSONData" value="requestParameters.hostVipInfoJSONData" type="string"/>
- <!-- additional set one field to pass the service list to next page(defineDBService.jsp) -->
- <set name="flowScope.hasHostVipInfoData" value="true" type="boolean"/>
- <set name="flowScope.services" value="requestParameters.services" type="string" />
- </transition>
- <transition on="cancel" to="aerEnvList">
- <evaluate expression="defineAppService.removeAppInfo(flowRequestContext)" />
- <evaluate expression="defineProjectService.removeProjectInfo(flowRequestContext)" />
- <evaluate expression="defineHostVipService.removeHostVipInfo(flowRequestContext)" />
- <evaluate expression="defineDBSrvService.removeDBServiceInfo(flowRequestContext)"/>
- </transition>
- </view-state>
- <view-state id="defineDBService">
- <transition on="previous" to="defineHostVip"/>
- <transition on="next" to="aerRequestConfirm">
- <evaluate expression="defineDBSrvService.createDBServiceInfo(requestParameters.dbServiceInfoJSONData, flowRequestContext)"
- result="flowScope.dbServiceInfo" />
- <set name="flowScope.dbServiceInfoJSONData" value="requestParameters.dbServiceInfoJSONData" type="string"/>
- <set name="flowScope.hasDbServiceInfoData" value="true" type="boolean"/>
- <set name="flowScope.isSubmitted" value="false" type="boolean"/>
- <set name="flowScope.isViewAction" value="false" type="boolean" />
- </transition>
- <transition on="cancel" to="aerEnvList">
- <evaluate expression="defineAppService.removeAppInfo(flowRequestContext)" />
- <evaluate expression="defineProjectService.removeProjectInfo(flowRequestContext)" />
- <evaluate expression="defineHostVipService.removeHostVipInfo(flowRequestContext)" />
- <evaluate expression="defineDBSrvService.removeDBServiceInfo(flowRequestContext)"/>
- </transition>
- </view-state>
- <view-state id="aerRequestConfirm">
- <transition on="previous" to="defineDBService"/>
- <transition on="submit" to="aerRequestSummary">
- <evaluate expression="envProvisionRequestService.submitEnvProvisionRequest(flowRequestContext)"
- result="flowScope.submitResult" />
- </transition>
- <!--
- <transition on="submit" to="aerRequestSummary"/>
- -->
- <transition on="cancel" to="aerEnvList">
- <evaluate expression="defineAppService.removeAppInfo(flowRequestContext)" />
- <evaluate expression="defineProjectService.removeProjectInfo(flowRequestContext)" />
- <evaluate expression="defineHostVipService.removeHostVipInfo(flowRequestContext)" />
- <evaluate expression="defineDBSrvService.removeDBServiceInfo(flowRequestContext)"/>
- </transition>
- <transition on="adminSubmit" to="aerRequestSummary">
- <evaluate expression="envProvisionRequestService.updateEnvProvisionRequest(flowRequestContext)"
- result="flowScope.submitResult" />
- <set name="flowScope.isViewAction" value="false" type="boolean" />
- </transition>
- <!--
- <transition on="submit" to="aerRequestSummary"/>
- -->
- <transition on="adminCancel" to="aerEnvList">
- <evaluate expression="defineAppService.removeAppInfo(flowRequestContext)" />
- <evaluate expression="defineProjectService.removeProjectInfo(flowRequestContext)" />
- <evaluate expression="defineHostVipService.removeHostVipInfo(flowRequestContext)" />
- <evaluate expression="defineDBSrvService.removeDBServiceInfo(flowRequestContext)"/>
- <set name="flowScope.isViewAction" value="false" type="boolean" />
- </transition>
- <transition on="noAdminOK" to="aerEnvList">
- <evaluate expression="defineAppService.removeAppInfo(flowRequestContext)" />
- <evaluate expression="defineProjectService.removeProjectInfo(flowRequestContext)" />
- <evaluate expression="defineHostVipService.removeHostVipInfo(flowRequestContext)" />
- <evaluate expression="defineDBSrvService.removeDBServiceInfo(flowRequestContext)"/>
- <set name="flowScope.isViewAction" value="false" type="boolean" />
- </transition>
- <!--add 4 event to distingush different partin the request confirmation page-->
- <transition on="editApplicationInfo" to="defineApp"/>
- <transition on="editProjectInfo" to="defineProject"/>
- <transition on="editHostVipInfo" to="defineHostVip"/>
- <transition on="editDBServiceInfo" to="defineDBService"/>
- </view-state>
- <view-state id="aerRequestSummary">
- <transition on="ok" to="aerEnvList">
- <evaluate expression="defineAppService.removeAppInfo(flowRequestContext)" />
- <evaluate expression="defineProjectService.removeProjectInfo(flowRequestContext)" />
- <evaluate expression="defineHostVipService.removeHostVipInfo(flowRequestContext)" />
- <evaluate expression="defineDBSrvService.removeDBServiceInfo(flowRequestContext)"/>
- </transition>
- </view-state>
- <end-state id="finish"/>
- </flow>
这里,因为我们在这系列的第二篇文章中已经提及到,我们开启了包扫描机制,所以这些Spring的Bean在应用上下文创建的时候就已经实例化了,所以在这个流定义文件中可以轻松的使用这些bean.
其实在做架构的时候,我曾和我们团队其他开发者讨论到为什么我们用spring web flow,其实这种页面跳转我们也可以不用web flow做,最后采用web flow的架构是基于以下几个原因:
众所周知,一般web应用的scope有 request,session,application,因为在很多配置页面上都有数据,并且这些数据都要共享,还比较大(那些传递的vo动辄100+字段)而且业务流程也比较复杂,而且这些数据还是有状态的,所以我们无法放在request scope上,而如果放在session scope上,又会加重系统的内存负担,所以我们需要一种介于request,session范围之间的scope,而spring web flow刚好提供了flow scope来精确的满足我们的需求,所以我们使用spring web flow.
本文转自 charles_wang888 51CTO博客,原文链接:http://blog.51cto.com/supercharles888/1138856,如需转载请自行联系原作者