stateless EJB3 bean invoked from request-scoped JA

2019-07-31 15:49发布

问题:

I have the following situation: Request-scoped JAX-RS service invokes stateless EJB3 bean and the EJB3 bean retains state between successive invocation of the web service from a client.

Code as follows:

web service

@javax.enterprise.context.RequestScoped
@Path("/actions")
public class CounterFrontEnd {

    @EJB
    private ICounterService.ILocal counterService;

    @GET @Produces("application/text;") @Path("/counter")
    public String counter() {
        return String.format("%d ", counterService.incCounter());
    }

stateless EJB3 bean

@Stateless
@Local (ICounterService.ILocal.class)
@Remote(ICounterService.IRemote.class)
public class CounterService implements ICounterService.ILocal, ICounterService.IRemote {

    public int counter = 0;
    @Override
    public int incCounter() {
        return counter++;
    }

I then invoke the service with the following python script:

for i in range(100):
  os.system( 'curl  http://somewhere:8080/counter-ws/rest/actions/counter' ) 

Surprisingly, the output is:

1 2 3 4 5 ...

回答1:

This is because the container (happens) to give you the same bean-instance every time, not something you should rely on.

Stateless session-beans should not rely on instance-variables like in your example.

From java ee tutorial: http://docs.oracle.com/javaee/6/tutorial/doc/javaeetutorial6.pdf

Stateless Session Beans

A stateless session bean does not maintain a conversational state with the client. When a client invokes the methods of a stateless bean, the bean’s instance variables may contain a state speciic to that client but only for the duration of the invocation. When the method is inished, the client-speciic state should not be retained. Clients may, however, change the state of instance variables in pooled stateless beans, and this state is held over to the next invocation of the pooled stateless bean. Except during method invocation, all instances of a stateless bean are equivalent, allowing the EJB container to assign an instance to any client. That is, the state of a stateless session bean should apply across all clients.