views:

365

answers:

1

Scenario:

I have @Singleton UserFactory (@Stateless could be) , its method createSession() generating @Stateful UserSession bean by manual lookup.

If I am injecting by DI @EJB - i will get same instance during calling fromFactory() method(as it should be)

What I want - is to get new instance of UserSession without preforming lookup.

Q1: how could I call new instance of @Stateful session bean?

Code:

@Singleton
@Startup
@LocalBean
public class UserFactory {

    @EJB
    private UserSession session;

    public UserFactory() {
    }


    @Schedule(second =  "*/1", minute = "*", hour = "*")
    public void creatingInstances(){
        try {
            InitialContext ctx = new InitialContext();
            UserSession session2 = (UserSession) ctx.lookup("java:global/inferno/lic/UserSession");
            System.out.println("in singleton UUID " +session2.getSessionUUID());    
        } catch (NamingException e) {
            e.printStackTrace();
        }

    }

    @Schedule(second =  "*/1", minute = "*", hour = "*")
    public void fromFactory(){
        System.out.println("in singleton UUID " +session.getSessionUUID());
    }


    public UserSession creatSession(){
        UserSession session2 = null;
        try {
            InitialContext ctx = new InitialContext();
            session2 = (UserSession) ctx.lookup("java:global/inferno/lic/UserSession");
            System.out.println("in singleton UUID " +session2.getSessionUUID());
        } catch (NamingException e) {
            e.printStackTrace();
        }
        return session2;

    }



}

As I understand, calling of

session.getClass().newInstance();

is not a best idea

Q2 : is it true?


#

Update

Goals

In reality the goal is to create some SessionsFactory that that would managed user`s sessions (this is web services users)

The Session @Statefull bean :

@Stateful
//Destroying outomaticly after 30 minuts inactive
@StatefulTimeout(180000)
@LocalBean
public class UserSession {
    //represent creation time, used by scheduler for destroying session
    private GregorianCalendar creationDate;
    private UUID sessionUUID;
    private String userId;
    private String state;

    //TODO change to xml
    private String histrory;

    public UserSession() {
    }
    @PostConstruct
    private void initSession(){
        //getting construction date
        creationDate = (GregorianCalendar) Calendar.getInstance();
        //generationg session id
        sessionUUID = UUID.randomUUID();
    }

    @PreDestroy
    private void releaseResource(){
        creationDate =null;
        sessionUUID = null;
        userId =null;
    }

    @Remove
    public void destroySession(){

    }

    public UUID getSessionUUID() {
        return sessionUUID;
    }

    public GregorianCalendar getCreationDate() {
        return creationDate;
    }

    public String getUserId() {
        return userId;
    }

    public void setUserId(String userId) {
        this.userId = userId;
    }

    public String getState() {
        return state;
    }

    public void setState(String state) {
        this.state = state;
    }

    public String getHistrory() {
        return histrory;
    }

    public void addHistroryEntry(String entry) {
        //TODO add history entry

    }
}

In factory methods I want just create new instance of @Statefull UserSession and to manage number of created sessions for each user, and call destroySession() after some period (30 minutes)

I need to track the history of user`s sessions requests , and persists there history later..

So I think @Statefull bean should suet my needs. But it looks like the lookup by JNDI name is the only chance to be shore that new ejb will be created. I am searching for possibility
to inject new instance of ejb without lookups, and maybe possibility to get collection of currently created instances of my @Statefull UserSession instead of keeping thrm in some map/collection.

Q3: so.. only JNDI will help me to create new instance of ejb ?

Q4: Is it possible to get collection of some ejb`s instances from container?


I am using glassfish v3, ejb 3.1.

A: 

Q1: how could I call new instance of @Stateful session bean?

You must not inject a Stateful Session Bean into a stateless object such as Stateless Session Bean or Servlet that may be shared by multiple concurrent clients, you should use JNDI instead. Period.

To be honest, I'm not sure to understand what you are doing and I don't see important steps such as removal of your Stateful Session Beans. You are likely going to run out of memory or cause a lot of disk IO as the container that will try to passivate/activate instances to save memory.

Q2 : is it true?

You can call new but don't expect to get something else than a simple Java class i.e. don't expect to get a managed object i.e. don't expect to get an EJB. I don't think that this is what you want.


Sorry if this doesn't help much but as I said, I don't really understand what you're trying to achieve. You should maybe start to explain your goal first, I don't have the feeling that you are on the right path.

Pascal Thivent
the singleton was just an example of testing injection/lookups. Sorry for confusing. I try to explain my goals. please, take a look at updates.
kislo_metal