2
votes

I'm stuck with the infamous WELD-001408 that everyone programming with CDI has come across in one way or other. Using Oracle JDK 1.8.0_25, Wildfly 8.2.0.Final. My code is as follows:

module availability-service (war) depends on module hospital-user (jar). Former has a beans.xml in WEB-INF and later in META-INF, even though CDI 1.1 doesn't require a beans.xml.

In hospital-user:

@ApplicationScoped
public class Users {
    @Produces
    @Doctors
    public List<Doctor> getDoctors() {
        return getUsers("/doctors.json", Doctor.class);
    }

    @Produces
    @Patients
    public List<Patient> getPatients() {
        return getUsers("/patients.json", Patient.class);
    }
}

Doctors annotation (Patients is similar except for the name):

@Qualifier
@Retention(RUNTIME)
@Target({ FIELD, METHOD })
public @interface Doctors {
}

In availability-service:

@ApplicationScoped
public class AvailabilityService {
    @Inject
    @Doctors
    private List<Doctor> doctors;
}

Error:

Caused by: org.jboss.weld.exceptions.DeploymentException: WELD-001408: Unsatisfied dependencies for type List<Doctor> with qualifiers @Doctors
  at injection point [BackedAnnotatedField] @Inject @Doctors private name.abhijitsarkar.microservices.availability.AvailabilityService.doctors
  at name.abhijitsarkar.microservices.availability.AvailabilityService.doctors(AvailabilityService.java:0)

    at org.jboss.weld.bootstrap.Validator.validateInjectionPointForDeploymentProblems(Validator.java:372)

If I inject the Users instead of the List, it works. Here is a sample Maven project that demonstrates the problem with 4 classes. Just run mvn clean test.

1

1 Answers

0
votes

In the sample Maven project that you provided, dependency injection in the test class isn't available as you specified your Arquillian deployment as @Deployment(testable = true).

When set to true, which is the default, the test passes.

Besides, adding the following injection point in the test method:

@Inject
@Employees
List<Employee> employees;

works fine which demonstrates that your bean deployment is valid.

It continues to work when the Arquillian deployment matches exactly the application WAR structure that you've depicted, i.e.:

@Deployment
public static WebArchive createDeployment() {
return create(WebArchive.class, "availability-service.war")
    .addAsLibraries(create(JavaArchive.class, "hospital-user.jar")
        .addPackages(true, Filters.exclude(".*Test.*"), Producer.class.getPackage())
        .addAsManifestResource(EmptyAsset.INSTANCE, "beans.xml"))
    .addAsWebInfResource(EmptyAsset.INSTANCE, "beans.xml");
}