Calling a CDI session scoped producer method from an EJB stateless session bean

北战南征 提交于 2020-01-12 18:19:17

问题


I want to inject the current user using @Inject @Current User across all layers (i.e. web layer, EJB layer). In order to do this, I have the following CDI Producer method:

@Named
@SessionScoped
public class UserController {
   @Resource SessionContext sessionContext;
   @EJB UserDao userDao;

   @Produces @Current
   public User getCurrentUser() {
     String username = sessionContext.getCallerPrincipal().getName();
     User user = userDao.findByUsername(username);
   }
}

@Qualifier
@Target({TYPE, METHOD, PARAMETER, FIELD})
@Retention(RUNTIME)
public @interface Current{}

Now, I want to inject the current user into an EJB stateless session bean as follows:

@Stateless
public class SomeBackendService {
   @Inject @Current
   private User user;
}

My question: Is the current user object always re-injected after the session changes, because the dependencies of a stateless session bean are normally injected once at creation time and the bean may be pooled and used across different sessions?


回答1:


Although I haven't tried this exact situation, in CDI beans are normally not re-injected. Instead, a proxy is injected that is aware of its context.

Via this mechanism, it's possible to inject say a session scoped bean in an application scoped bean. Every user of the application scoped bean goes to the same bean and the same proxy, but the proxy will then dynamically resolve calls on it to a different bean for each user.

So even though the scope of @Stateless is basically 'application', it would be possible that the proxy that represents User in your `SomeBackendService' still delegates to the correct session scoped version.

p.s.

If with layers you actually mean modules as in web and EJB modules that are part of an EAR, it's going to be a little bit more complicated, as CDI doesn't always works as expected between modules (especially in JBoss AS). This is partly due to the ambiguity of what an 'application' and thus the application scope is within an EAR.




回答2:


Yes, to each business method called the container will be re-injected all dependencies of your SLSB. Here is text that guarantees this in EJB 3.1 specification:

"If a session bean makes use of dependency injection, the container injects these references after the bean instance is created, and before any business methods are invoked on the bean instance." - Section 4.3.2

I had this doubt too and I posted a question explaining this situation here




回答3:


By design, your stateless session bean should not have a state "User", it's stateless by all means.

If you want your EJB to have states, then use @Stateful instead.



来源:https://stackoverflow.com/questions/6973028/calling-a-cdi-session-scoped-producer-method-from-an-ejb-stateless-session-bean

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!