I'm using the following code to test the operation of ConversationScoped, but I don't understand how it works. I open conversation, set the value of conversationBean.i = 1, then close conversation and open a new conversation, but the value of conversationBean.i is still 1, why? it was supposed to be null, wasn't it?
@WebServlet(value = "/tes")
public class MyTag extends HttpServlet {
@Inject
ConversationBean conversationBean;
@Override
protected void doGet(HttpServletRequest req,
HttpServletResponse resp) {
conversationBean.startConversation();
conversationBean.doSomething();
conversationBean.out();
conversationBean.endConversation();
conversationBean.startConversation();
conversationBean.out();
}
}
@ConversationScoped
class ConversationBean implements Serializable {
int i = 0;
@Inject
private Conversation conversation;
public void startConversation() {
conversation.begin();
}
public void doSomething() {
i++;
}
public void out() {
System.out.println(i);
}
public void endConversation() {
conversation.end();
}
}
Tell me, maybe I got it wrong? If so, could you provide an easy example where it really shows that when closing a conversation, all the resources associated with it are cleared?
@ConversationScopedis primarily about JSF, in which context the word "conversation" has a particular meaning. I haven't really used it, but I expect that it would sometimes make sense for the backing bean of a JSF component.Conversationobjects provide a way to access certain properties of JSF conversations.The injected
ConversationBeaninstance may change from request to request, but the one observed by a given invocation of one of your servlet's request-handling methods will not change during the execution of that method. Naturally, then, if you modify that bean's state duringdoGet()then you can observe that modification later indoGet().Moreover,
Conversation.startConversation()andConversation.endConversation()don't do what their names might lead you to think they do. They control whether the current conversation is "long-lived" or "transient", which affects its lifecycle, but they don't actually start or end a conversation. The names make a little more sense if you think in terms of starting and ending long-lived conversations specifically, but even then they're not really right. A singlesetLongLived(boolean)method would be more intuitive.No.
You have incorrect expectations.
And although it's valid, it doesn't usually make sense to switch the current conversation back and forth between transient and long-lived multiple times while servicing the same request. Request boundaries are inside conversation boundaries, so only the conversation type prevailing at the end of request processing matters.
That does not happen per se. If you have a
@ConversationScopedbean then you can expect to get different instances in different conversation contexts, butConversation.startConversation()andConversation.endConversation()don't get you a different conversation context for the current request. And if you hold on to a reference to a conversation-scoped bean past the end of the lifetime of the conversation context from which you obtained it, you should not expect that to cause its properties to be modified.