# 8.2.3　流程数据

如果你曾经玩过那种老式的基于文字的冒险游戏的话，那么当从一个地方转移到另一个地方时，你会偶尔发现散布在周围的一些东西，你可以把它们捡起来并带上。有时候，你会马上需要一件东西。其他的时候，你会在整个游戏过程中带着这些东西而不知道它们是做什么用的 —— 直到你到达游戏结束的时候才会发现它是真正有用的。

在很多方面，流程与这些冒险游戏是很类似的。当流程从一个状态进行到另一个状态时，它会带走一些数据。有时候，这些数据只需要很短的时间（可能只要展现页面给用户）。有时候，这些数据会在整个流程中传递并在流程结束的时候使用。

**声明变量**

流程数据保存在变量中，而变量可以在流程的各个地方进行引用。它能够以多种方式创建。在流程中创建变量的最简单形式是使用 `<var>` 元素：

```markup
<var name="customer" class="com.springinaction.pizza.domain.Customer" />
```

这里，创建了一个新的 Customer 实例并将其放在名为 customer 的变量中。这个变量可以在流程的任意状态进行访问。

作为行为状态的一部分或者作为视图状态的入口，你有可能会使用 `<evaluate>` 元素来创建变量。例如：

```markup
<evaluate result="viewScope.topppingsList" expression="T(com.springinaction.pizza.domain.Topping).asList()" />
```

在本例中，`<evaluate>` 元素计算了一个表达式（SpEL 表达式）并将结果放到了名为 toppingsList 的变量中，这个变量是视图作用域的（我们将会在稍后介绍关于作用域的更多概念）。

类似地，`<set>` 元素也可以设置变量的值：

```markup
<set name="flowScope.pizza" value="new com.springinaction.pizza.domain.Pizza()" />
```

`<set>` 元素与 `<evaluate>` 元素很类似，都是将变量设置为表达式计算的结果。这里，我们设置了一个流程作用域内的 pizza 变量，它的值是 Pizza 对象的新实例。

当我们在 8.3 小节开始构建真实工作的 Web 流程时，你会看到这些元素是如何具体应用在实际流程中的。但首先，让我们看一下变量的流程作用域、视图作用域以及其他的一些作用域是什么意思。

**定义流程数据的作用域**

流程中携带的数据会拥有不同的生命作用域和可见性，这取决于保存数据的变量本身的作用域。Spring Web Flow 定义了五种不同作用域，如表 8.2 所示。

| 范围           | 生命作用域和可见性                                      |
| ------------ | ---------------------------------------------- |
| Conversation | 最高层级的流程开始时创建，在最高层级的流程结束时销毁。被最高层级的流程和其所有的子流程所共享 |
| Flow         | 当流程开始时创建，在流程结束时销毁。只有在创建它的流程中是可见的               |
| Request      | 当一个请求进入流程时创建，在流程返回时销毁                          |
| Flash        | 当流程开始时创建，在流程结束时销毁。在视图状态渲染后，它也会被清除              |
| View         | 当进入视图状态时创建，当这个状态退出时销毁。只在视图状态内是可见的              |

当使用 `<var>` 元素声明变量时，变量始终是流程作用域的，也就是在定义变量的流程内有效。当使用 `<set>` 或 `<evaluate>` 的时候，作用域通过 name 或 result 属性的前缀指定。例如，将一个值赋给流程作用域的 theAnswer 变量：

```markup
<set name="flowScope.theAnswer" value="42" />
```

到目前为止，我们已经看到了 Web 流程的所有原材料。是时候将其组装起来形成一个成熟且完整功能的 Web 流程了。当我们这样做的时候，请睁大你的眼睛观察，比如我是如何将数据存储在各作用域的变量中的。


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://potoyang.gitbook.io/spring-in-action-v4/untitled-2/untitled-3/untitled.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
