第一部分demo仅仅介绍了简单的页面跳转,接下来我们要实现与业务逻辑相关的功能。

业务的逻辑涉及到数据的获取、传递、保存。相关的业务功能函数的调用等内容,这些功能的实现都可用Java 代码来完毕,但定义 Spring Web Flow 的语法与 Java 是无关的,这就要求 Spring Web Flow 提供与 Java代码的整合机制。

要了解这样的机制。关键在于搞清楚两个问题:

  • 业务逻辑代码在什么时候被调用?
  • 业务逻辑代码在调用后得到的数据怎样保存、传递?

业务逻辑代码在什么时候被调用?

在 Spring Web Flow中,业务逻辑代码的运行可由以下三种情形来触发:

  • client请求中包括了 _eventId 參数
  • 运行到框架自己定义的切入点
  • 运行到 <action-state> 元素

1。client请求中包括了 _eventId參数

这样的方式一般用在state 之间的 transition ,通过指定 _eventId 參数的值,表明了客户的行为,从而导致相应事件的发生,在 Spring Web Flow的定义文件里能够通过 evaluate 元素来指定要处理的业务逻辑

<transition on="submit">
<evaluate expression="validator.validate()" />
</transition>

当client的请求中包括“_eventId=submit ”,则 evaluate 元素中 expression 属性所指明的表达式会被运行,即 validator对象的validate 方法会得到调用。

2。运行到框架自己定义的切入点

SpringWeb Flow 定义了 5 个切入点,通过 flow 定义文件的配置,可在这 5 个切入点插入相关业务逻辑代码。

SpringWeb Flow 自己定义的切入点

切入点名称

XML 元素名称

触发时刻

flow start

on-start

flow 运行之前

state entry

on-entry

进入某个 state 之后,做其它事情之前

view render

on-render

在进入 view 的 render 流程之后。在 view 真正 render出来之前

state exit

on-exit

在退出 state 之前

flow end

on-end

flow 运行结束之后

on-render 元素

<view-state id="viewCart" view="viewCart" >
<on-render>
<evaluate expression="productService.getProducts()" result="viewScope.products"/>
</on-render>
</view-state>

兴许会具体介绍,以下的demo即使用此种方式与业务逻辑建立关系。

3,运行到<action-state> 元素

SpringWeb Flow 中的这个 <action-state> 是专为运行业务逻辑而设的 state 。

假设某个应用的业务逻辑代码既不适合放在transition 中由client来触发,也不适合放在 Spring Web Flow 自己定义的切入点,那么就能够考虑加入<action-state> 元素专用于该业务逻辑的运行。

action-state 演示样例

<action-state id="addToCart">
<evaluate expression="cart.addItem(productService.getProduct(productId))"/>
<transition to="productAdded"/>
</action-state>

兴许会具体介绍,在下篇博客中会介绍。

业务逻辑代码在调用后得到的数据怎样保存、传递?

Spring Web Flow的定义中可直接使用表达式语言( Expression Language )。前面的代码都是用的 Unified EL ,对于习惯用 OGNL的开发者,可通过 flow-builder-services 的配置改成使用 OGNL 。无论是哪一种表达式语言。 Spring Web Flow都提供了一些固定名称的变量,用于数据的保存、传递。

在 Spring Web Flow的解决方式中。我们知道 Spring Web Flow 所着力解决的问题即是数据存取范围的问题,为此, Spring Web Flow提供了两种比較重要的范围,一是 flow 范围,另一个是 conversation 范围。通过 flowScope 和 conversationScope这两个变量。 Spring Web Flow 提供了在这两种范围里存取数据的方法。

<evaluate expression="productService.getProducts()" result="flowScope.products" />  

注意:Spring Web Flow 2.0 在默认配置下,flowScope 和 conversationScope的实现依赖于 Java 序列化和反序列化技术,因此存放于 flowScope 或 conversationScope 中的对象须要实现java.io.Serializable 接口。

注:

  1. flow 范围。

    此范围内的对象在 flow 開始时创建, flow 结束时销毁,在 flow 定义文件里可通过“ flowScope ”变量名来訪问。

  2. conversation 范围。此范围内的对象与 flow 范围对象基本类似,唯一不同在于 conversation 范围内的对象所在的 flow 假设调用了其它 subflow ,那么在 subflow 中也可訪问该对象。(也就是说:subflow中能够訪问conversation中的对象)

SpringWeb Flow 还提供了大量其它的变量。以方便数据的存取。如 viewScope 范围即是从进入 view-state 至退出 view-state 结束,requestScope 即和一般的 request 范围没什么差别,等等。另外另一些用于获取 flow 以外数据的变量,如requestParameters 、 messageContext 等等。具体变量的列表可參看 Spring Web Flow自带的文档。

Demo实现:

ProductService类

package samples.webflow;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map; import org.springframework.stereotype.Service; @Service("productService")
public class ProductService { private Map<Integer, Product> products = new HashMap<Integer, Product>(); public ProductService() {
products.put(1, new Product(1, "Bulldog", 1000));
products.put(2, new Product(2, "Chihuahua", 1500));
products.put(3, new Product(3, "Labrador", 2000));
} public List<Product> getProducts() {
return new ArrayList<Product>(products.values());
} public Product getProduct(int productId) {
return products.get(productId);
}
}

Service 注解表示 Spring IoC容器会初始化一个名为 productService 的 Bean 。这个 Bean 可在 Spring Web Flow的定义中直接訪问。(这也是为什么在web-application-config.xml中加入注解的原因)

改动shopping.xml 文件

要在 viewCart 页面中显示商品,仅仅需在view-state 元素的 on-render 切入点调用 productService 的 getProducts 方法,并将所得结果保存到viewScope 中就可以。

改动后的shopping.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"> <!-- view-state中的view相应jsp目录中的jsp页面,on是触发事件,to相应state id -->
<view-state id="viewCart" view="viewCart">
<on-render>
<!-- 要在 viewCart 页面中显示商品,仅仅需在 view-state 元素的 on-render 切入点调用 productService 的
getProducts 方法。并将所得结果保存到 viewScope 中就可以 -->
<!-- productService 的 getProducts 方法所得的结果会存放在 viewScope 中名为 products 的变量中, jsp 页面的代码可直接訪问该变量。 -->
<!-- 通过 evaluate 元素来指定要处理的业务逻辑 -->
<evaluate expression="productService.getProducts()" result="viewScope.products" />
</on-render>
<transition on="submit" to="viewOrder">
</transition>
</view-state> <view-state id="viewOrder" view="viewOrder">
<transition on="confirm" to="orderConfirmed">
</transition>
</view-state> <view-state id="orderConfirmed" view="orderConfirmed">
<transition on="returnToIndex" to="returnToIndex">
</transition>
</view-state>
<end-state id="returnToIndex" view="externalRedirect:servletRelative:/index.jsp">
</end-state>
</flow>

改动viewCart.jsp 页面

productService的 getProducts 方法所得的结果会存放在 viewScope 中名为 products 的变量中, jsp 页面的代码可直接訪问该变量。

改动后的 viewCart.jsp 页面

<?xml version="1.0" encoding="utf-8" ?>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>View Cart</title>
</head>
<body>
<h1>View Cart</h1>
<a href="${flowExecutionUrl}&_eventId=submit">Submit</a>
<h2>Products for Your Choice</h2>
<table>
<c:forEach var="product" items="${products}">
<tr>
<td>${product.description}</td>
<td>${product.price}</td>
</tr>
</c:forEach>
</table>
</body>
</html>

訪问地址:http://localhost:8080/CartApp4/spring/index.jsp

View Cart页面效果图:

源代码下载

总结:

以上的代码实现是结合第一篇博客后融合业务逻辑来操作,主要介绍了业务和Spring Web Flow的结合方式。下篇博客将陆续介绍流程的嵌套。

Spring Web Flow 入门demo(二)与业务结合 附源代码的更多相关文章

  1. Spring Web Flow 入门demo(三)嵌套流程与业务结合 附源代码

    上篇博客我们说Spring web Flow与业务结合的方式主要有三种,以下我们主要介绍一下第三种的应用方式 3,运行到<action-state> 元素 SpringWeb Flow 中 ...

  2. spring web flow 2.0入门(转)

    Spring Web Flow 2.0 入门 一.Spring Web Flow 入门demo(一)简单页面跳转 附源码(转) 二.Spring Web Flow 入门demo(二)与业务结合 附源码 ...

  3. Spring Web Flow 2.0 入门

    转载: https://www.ibm.com/developerworks/cn/education/java/j-spring-webflow/index.html 开始之前 关于本教程 本教程通 ...

  4. Spring Web Flow实例教程

    目录: 参考文献 购物车用例 什么情况下可以使用 Spring Web Flow? 配置 Spring Web MVC 配置 Spring Web Flow 2.0 的基础 在购物车示例应用中配置 S ...

  5. 笔记42 Spring Web Flow——Demo(2)

    转自:https://www.cnblogs.com/lyj-gyq/p/9117339.html 为了更好的理解披萨订购应用,再做一个小的Demo. 一.Spring Web Flow 2.0新特性 ...

  6. 笔记41 Spring Web Flow——Demo

    订购披萨的应用整体比较比较复杂,现拿出其中一个简化版的流程:即用户访问首页,然后输入电话号(假定未注册)后跳转到注册页面,注册完成后跳转到配送区域检查页面,最后再跳转回首页.通过这个简单的Demo用来 ...

  7. Spring Web Flow 简介

    Spring Web Flow 简介 博客分类: 转载 SSH 最近在TSS上看到了一片介绍Spring Web Flow的文章,顺便就翻译了下来,SWF的正式版估计要到6月份才能看到了,目前的例子都 ...

  8. Spring Web Flow

    Spring Web Flow是一个Web框架,它适用于元素按规定流程运行的程序.Spring Web Flow是Spring MVC的扩展,它支持开发基于流程的应用程序.它将流程的定义与实现流程行为 ...

  9. 第8章—使用Spring Web Flow—Spring Web Flow的配置

    Spring中配置Web Flow Spring Web Flow 是 Spring 的一个子项目,其最主要的目的是解决跨越多个请求的.用户与服务器之间的.有状态交互问题,比较适合任何比较复杂的.有状 ...

随机推荐

  1. 简单谈谈MySQL中的int(m)

    转载地址:https://www.jb51.net/article/93760.htm 设置int型的时候,需要设置int(M),以前知道这个M最大是255,但是到底应该设置多少并没有在意.注意zer ...

  2. Windows 2008 防火墙开放端口

    当我们使用新服务器架设新主机时,经常会遇到网站无法访问的情况,当问及客服时,经常会告知,操作系统默认不打开80端口,请先确定80是否打开并确定没有被占用.那么,我们该如何打开80端口呢? 方法/步骤 ...

  3. centos上安装supervisor来管理dotnetcore等应用程序

    supervisor 介绍: 这是一款用python编写的进程管理工具,可以守护他管理的所有进程,防止异常退出,以及提供一个可视化的web界面来手动管理,打开关闭重启各种应用,界面如下: 关于在cen ...

  4. java读取03、07版EXCEL

    03版excel,需要用到jxl.jar这个jar包 package test.poi; import java.io.File; import java.io.IOException; import ...

  5. 编写Java脚本统计工程代码总行数

    在新公司工作将近一年了,一直独自一人负责服务端集群的运维和代码的编写.不知不觉从一个Project发展到了七八个Project. 看着越来越多的代码,今天突然想统计一下一共写了多少代码.[这里只统计完 ...

  6. 模块挂载、切换,uml模式、流程图模式

    模块挂载.切换,uml模式.流程图模式

  7. Jenkins系列之Jenkins的工具配置和插件(二)

    上一篇我们介绍了Jenkins的安装,这一篇我们介绍如何配置Jenkins的工具和如何下载插件. 首先我们先来看如何配置工具,这里的工具是指JDK.Ant.Maven.Git等. 一.如图,点击系统管 ...

  8. 并发编程学习笔记(12)----Fork/Join框架

    1. Fork/Join 的概念 Fork指的是将系统进程分成多个执行分支(线程),Join即是等待,当fork()方法创建了多个线程之后,需要等待这些分支执行完毕之后,才能得到最终的结果,因此joi ...

  9. arx升级

    如果你打算升级你的ARX或者想在同一个IDE(譬如vs2010)编译多个版本的ARX,那么我希望这篇帖子对你有帮助首先你应该简单了解Objectarx开发的版本对应情况:R15   --- 2000- ...

  10. RabbitMQ系列(八)--顺序消费模式和迅速消息发送模式

    MQ使用过程中,有些业务场景需要我们保证顺序消费,而如果一个Producer,一个Queue,多个Consumer的情况下是无法保证顺序的 举例: 1.业务上产生三条消息,分别是对数据的增加.修改.删 ...