Search code examples
jsfjava-ee-6cdiejb-3.1

Singleton to hold collections of rows


In a Web App, need to display a view of 6 objects (rows of table DB) via JSF per page. To advance to the next view another different random 6 objects are to be displayed and so on...

So I was thinking in having a @Singleton that queries all the rows of the table with a @Schedule job in a given interval, let's say every 1 hour. It will have a getCollection() method.

Then every visitor will have a @SessionScoped CDI bean, that will query the Collection of the @Singleton, then shuffle it to make a random view to the specific user.

As with many visits, many CDI beans will be created that will access the getCollection() method concurrently.

Is this thought correctly? Any specific annotations are needed for this case? Any other way of doing this?

-----UPDATE---

After speaking with friends, specially Luiggi Mendoza, they tell me that best thing here is to use a EHCACHE or similar, instead of a Singleon. I think that's the way.


Solution

  • Will you have a cluster of webservers? In that case you need a distributed cache or you need to update state through the database.

    Else I would just go for a simple map in a bean that is @ApplicationScoped.

    I use JPA in a solution where a big bunch of data is almost always the same. There's more then one tomcat involved so a pure cache in a bean that is @ApplicationScoped won't work. To fix it I have no second level cache and instead cache the result of the database queries. That means each tomcat has it's own cache.

    For every login a timestamp is read, if the data in the cache is not stale it is used. Otherwise the cache is updated. The timestamp is updated when changes occur with the help of database triggers.

    @PrePersist
    @PreUpdate
    @PreRemove
    public void newTimeStamp() {
    // save a new timestamp
    }
    

    @Singleton is not part of the CDI specification so I would refrain from using it.

    Also I would keep my client bean @RequestScoped and reload the 6 objects with @PostConstruct. That way you will get a fresh 6 for every request.

    Or if that is to short lived maybe @ViewScoped (requires myfaces codi), @ConversationScoped or @ViewAccessScoped (requires myfaces codi).