• Post Reply Bookmark Topic Watch Topic
  • New Topic
programming forums Java Mobile Certification Databases Caching Books Engineering Micro Controllers OS Languages Paradigms IDEs Build Tools Frameworks Application Servers Open Source This Site Careers Other Pie Elite all forums
this forum made possible by our volunteer staff, including ...
Marshals:
  • Campbell Ritchie
  • Tim Cooke
  • paul wheaton
  • Jeanne Boyarsky
  • Ron McLeod
Sheriffs:
  • Paul Clapham
  • Liutauras Vilda
  • Devaka Cooray
Saloon Keepers:
  • Tim Holloway
  • Roland Mueller
Bartenders:

JSF Session-scope managed beans and Multiple browsers

 
Greenhorn
Posts: 6
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I am building a web app that allows users to create and edit records. The forms are somewhat complex with a lot of fields, and use heavy partial page rendering for adding and removing entries. The managed beans are session-scope.

Here is the perhaps familiar problem related to session-scoped beans: when a user opens more than one browser, bean data from one browser is unsafely altering the state of the other browser.

For example, if a user opens record A in browser #1, and then opens record B in browser #2, then record A will be over-written in the session. Browser #1 is now an invalid view of the current session data, and doing anything in this window will have unknown results.

This is an unfortunate side-effect of having session-scoped managed beans. And yet request beans just don't cut it for the amount of data and the amount of processing being done. For example, even before the record is ready to be submitted and saved, there is a ton of partial-page requests to add more fields, do custom validation, etc.

Ideally, I'd like only user information to be session-scoped (if a user logs in in one browser, and opens another browser, that one is also logged in. This bean works perfectly fine as a session bean). But individual records should have a feel of being request-scoped (a user should be able to edit two different records in two browsers; does not work so well as a session-bean). My attempt to rework this data into a request-scoped bean convinced me that it can't be done short of passing tons and tons of data back and forth with every action, and is therefore impractical, so there I am stuck.

I'm looking for solutions or alternative approaches. Any insight would be appreciated!

I'm using JSF 1.2 + Facelets + Trinidad.

Note: I've seen something called pageFlowScope mentioned in Trinidad's documentation. This is the closest thing I've found to a potential solution, but unfortunately it seems primitive and cumbersome. I've hit a dead-end looking into it - as complete as Trinidad's documentation is, much of it is briefly mentioned with no examples or resources to go with it. But if anyone has had success with this, please let me know.
 
Ranch Hand
Posts: 200
Eclipse IDE Java Ubuntu
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
If you're using the same bean across two browsers, why not make the user operations atomic? Essentially what we're talking about is a race condition.

Also, have you considered using AJAX as a way to push updated data into each browser so the changes are reflected in both without having to wait for a page refresh?
 
Vance Montague
Greenhorn
Posts: 6
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Sorry, maybe I didn't explain clearly enough. I actually don't even want two browsers to have access to the same bean (so race conditions are not applicable). I want each browser to have its own instance of the session bean.

I've been researching more and I think I found something that addresses the problem - a library called Orchestra:

http://myfaces.apache.org/orchestra/index.html

It leverages off of Spring to create a new bean scope called "conversation" scope, which I believe would create a new instance of the bean for every browser or tab that is opened. I'll post an update if I find it solves the problem.
 
Greenhorn
Posts: 12
Netbeans IDE MySQL Database Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I think JSF 'View Scope' can provide de 'Request' feel you are looking for. But it's only available in JSF 2.0.

The Conversation Scope provided by CDI Beans is indeed a valid option in your case and will most likely solve your problem. But it's a little more complex than using ViewScopes.
 
Vance Montague
Greenhorn
Posts: 6
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I heard of the view scope - unfortunately, the project I'm working on is using JSF 1.2. Maybe someone using JSF 2.0 can share their review of it?

Anyway, I gave Orchestra a shot and it seems to be working nicely. For anyone that may run into this problem in the future: in spite of requiring Spring and Orchestra libraries to be added, the solution still managed to work pretty seamlessly with an existing JSF project, without adding much complexity - managed beans will function the same, Orchestra just adds a new conversation scope.

Just need to throw spring.jar into your lib folder, and add the spring config file called "applicationContext.xml" to WEB-INF.

Then, orchestra jar files go into the lib folder as well, and the definitions for Orchestra's conversation-scoped beans are added to applicationContext.xml (it uses Spring's custom scope capability, hence the need for spring). Other than a few more lines needed in web.xml and faces-config.xml, that's all there is for setup.

The result is:
1) your existing JSF managed beans remain the same, and you can continue declaring request/session scope beans in faces-config.xml
2) now managed beans can also be declared in applicationContext.xml using the new conversation scope
3) beans from either of these two files are accessed the usual way from source: #{bean.whatever}

There is also a decent Orchestra API for the back-end stuff. If you're accustomed to using FacesContext to access beans from the session, Orchestra has something similar with ConversationManager, which gives you access to the beans stored in the conversation scope.

Thanks for the input, everyone.
 
We cannot change unless we survive, but we will not survive unless we change. Evolving tiny ad:
Smokeless wood heat with a rocket mass heater
https://woodheat.net
reply
    Bookmark Topic Watch Topic
  • New Topic