YevgenyL
YevgenyL

Reputation: 331

Using @Inject Instance to get EJB and CDI beans that implements specific interface

In our application we have CDI (@ApplicationScoped annotation) and EJB (@Stateless annotaion) beans that structured like this:

MyInterface
    MyAbstractClass
       MyBean (CDI or EJB)

I'm using below to get all the beans (CDI and EJB) in my application that implements MyInterface:

@Inject
Instance<MyIterface> beans;

Here I see two weird things:

How can I get all the beans, CDI and EJB, with the inject above?

Upvotes: 0

Views: 764

Answers (1)

Illya Kysil
Illya Kysil

Reputation: 1756

Quote from section 4.9.2.1 of EJB 3.2 specification:

@Stateless
public class A implements Foo { ... }

@Stateless
public class B extends A implements Bar { ... }

Assuming Foo and Bar are local business interfaces and there is no associated deployment descriptor, session bean A exposes local business interface Foo and session bean B exposes local business interface Bar, but not Foo.

Session bean B would need to explicitly include Foo in its set of exposed views for that interface to apply. For example:

@Stateless
public class A implements Foo { ... }

@Stateless
public class B extends A implements Foo, Bar { ... }

In your example, MyBean defined as EJB does not expose MyInterface, and, as a result, is not injected at Instance<MyInterface>.

There are two ways to handle it:

  • declare EJBs as implementing MyInterface;
  • annotate EJBs with @Local(MyInterface.class)

Warning for the approach with @Local - this EJB will satisfy only those injection points which use one of the interfaces provided as a parameter to the annotation. You won't be able to inject it at

@Inject
MyBean bean;

Also, you won't be able to cast the injected proxy to any other type.

Upvotes: 4

Related Questions