bastiat
bastiat

Reputation: 2071

spring webflow requestScope variables not visible in view

given

<view-state id="bstate" model="foo">
<on-entry>
    <evaluate expression="service.createPerson(22,'Adam', 'Hayek')"
            result="viewScope.person"></evaluate>
</on-entry>
...
</view-state>

in jsp view I can successfully get person by

${person}

but when I put into requestScope instead of viewScope

${person} is no longer available in jsp

Upvotes: 3

Views: 2337

Answers (2)

Aniket Thakur
Aniket Thakur

Reputation: 68935

As you know SWF uses POST-REDIRECT-GET to render views lets do a simple test to see how actions work. Change your configuration to something like -

<view-state id="bstate" model="foo">
    <on-entry>
        <evaluate expression="myBean.OnEntry()"></evaluate>
    </on-entry>
    <on-render>
        <evaluate expression="myBean.OnRender()"></evaluate>
    </on-render>
</view-state>

And access the flow and notice the logs

19:08:07.805 [tomcat-http--35] DEBUG o.s.webflow.execution.ActionExecutor - Executing [EvaluateAction@31865599 expression = myBean.onEntry(), resultExpression = [null]]
19:08:07.809 [tomcat-http--35] DEBUG o.s.w.mvc.servlet.FlowHandlerAdapter - Sending flow execution redirect to '/webflow-actions-test/mypath?execution=e3s1'
19:08:07.841 [tomcat-http--36] DEBUG o.s.webflow.execution.ActionExecutor - Finished executing [EvaluateAction@7584e5f9 expression = myBean.onRender(), resultExpression = [null]]; result = success

As you can see first onEntry() gets executed then redirect happens and then onRender() gets called. As these are two different requests you cannot access variable with request scope from one request to another.

So as Prasad mentioned you can move your logic to on-render

<on-render>
    <evaluate expression="service.createPerson(22,'Adam', 'Hayek')"
            result="requestScope.person"></evaluate>
</on-render>

and access it in your JSP

or you can change your scope to flashScope [NOTE : This gets cleared every time a view is rendered. This means it will survive the initial redirect but will not be available if you refresh page again] or you can use viewScope [variable will be accessible in your view-state]. if you want variables across state you can use viewScope.

More on scopes - http://docs.spring.io/autorepo/docs/webflow/2.3.x/reference/html/el.html#el-variables

Also interesting thread - http://forum.spring.io/forum/spring-projects/web/web-flow/68756-what-is-the-use-of-request-scope-and-flash-scope

Upvotes: 0

Prasad
Prasad

Reputation: 3795

Spring webflow follows POST-REDIRECT-GET approach for every request. 
i.e., initial request is split into 2 requests - 
POST processing and then REDIRECT-GET (render view)

In <on-entry>, action happens in first request and so request 
attribute will not survive when view is rendered.

In <on-render>, whole action happens in second request and so 
request attribute will survive when view is rendered.

So put it in <on-render> instead of <on-entry> for request scope. 
View scope value survives from entry to exit of view. 

Upvotes: 4

Related Questions