8
votes

Using Wildfly 8.1 I have several beans which I try to inject several EJB into each other. Lets say I have 3 beans:

@Stateless 
public class A{
  @Inject
  private B b;
}

@Stateless 
public class B{
  @Inject
  private C c;
}

@Stateless 
public class C{
  @Inject
  private A a;
}

Obviously, I have circular dependency. According to specification:

The container is required to support circularities in the bean dependency graph where at least one bean participating in every circular chain of dependencies has a normal scope

Running above code in container result in an error of the form:

org.jboss.weld.exceptions.DeploymentException: WELD-001443: Pseudo scoped bean has circular dependencies. Dependency path:

-Session bean [class A with qualifiers [@Default @Any]; local interfaces are [A] BackedAnnotatedField] @Inject private B,

[..]

My question here is: what is the scope of @Stateless beans? Is it by default @Dependent? And most of all how can I enable circular dependencies between stateless session beans?

Sorry if the question is too trivial. I will appreciate any good further reading sources which will explain presented behavior. Thanks in advance.

UPDATED Ok. I found the workaround. I've used @EJB annotation instead of @Inject but this does not explain the weird behavior of @Inject. The question remains open but as Mika suggested it may be unresolved issue in both CDI specification and Weld RI.

3
I don't have an answer, but it's not a trivial question. There was a discussion about this between the CDI EG members. Look at the CDI spec jira, there should be an issue about this very topic.Mike Braun
@MikeBraun could you perhaps provide a link to the jira issue? I've searched but I'm not sure I'm looking at the right one.iku
Thanks. As it's written in description current workaround is same as I've put in update. So for now I'll make it an answer.iku
CDI-414 deals with self injection, not circular injection.John Ament

3 Answers

9
votes

It's a bug in wildfly/jboss CDI implementation. Current workaround (as suggested by @MikeBraun), provided in issue description https://issues.jboss.org/browse/CDI-414, is to use @EJB annotation instead of @Inject.

3
votes

@Stateless has no scope and has no correlation to any scope. Your beans are ending up as @Dependent since you have not annotated any other scope on your beans.

You need to give them a normal scope - @RequestScoped or @ApplicationScoped, however I'm not sure either makes sense in your case.

3
votes

This doesn't answer the entire question, but it was the first hit on google when I searched circular dependency exceptions. Hoping this will help other programmers finding a quicker answer here is my solution.

The code that cause circular dependency exception:

class A{
    @Inject B b;
    public void foo(){
        b.bar();
    }
    public void quux(){
        //some code
    }
}
class B{
    @Inject A a;
    public void bar(){
        //some code
    }
    public void baz(){
        a.quux();
    }
}

A solution to solve the issue is by using javax.enterprise.inject.Instance

class A{
    @Inject B b;
    public void foo(){
        b.bar();
    }
    public void quux(){
        //some code
    }
}
class B{
    @Inject Instance<A> a;
    public void bar(){
        //some code
    }
    public void baz(){
        a.get().quux();
    }
}