How to configure beans.xml in CDI applications

The beans.xml file is the bean archive descriptor for CDI applications. It can be used for any CDI compliant container, such as Weld which is included in WildFly application server.

First off, it’s worth understanding that the bean descriptor in CDI (META-INF/beans.xml or WEB-INF/beans.xml) is not there to define beans in XML. Rather, you can use this file to enable some CDI services for your application.

wildfly beans.xml wildfly beans.xml wildfly beans.xml

For example, in CDI, you can use beans.xml to enable interceptors (disabled by default) and define interceptor priority. So the bean descriptor complements the metadata that is available in other annotations or XML configuration files.

Beans.xml schema

The schema for the beans.xml file varies according to the Enterprise specification of your project:

Jakarta EE 10

If you are deploying Jakarta EE 10 application, this is a sample beans.xml file:

<beans xmlns="https://jakarta.ee/xml/ns/jakartaee"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="https://jakarta.ee/xml/ns/jakartaee https://jakarta.ee/xml/ns/jakartaee/beans_4_0.xsd"
       version="4.0" bean-discovery-mode="annotated">

</beans>

Please notice that the default value for bean-discover-mode is “annotated“. This means that only Classes with Bean defining annotations will be registered as CDI Bean. If you want to register also Beans which don’t use Bean defining annotations you have to set bean-discovery-mode=”all”.

Jakarta EE 9

If you are deploying Jakarta EE 9 applications, you can use the following schema for your beans.xml

<beans xmlns="https://jakarta.ee/xml/ns/jakartaee"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="https://jakarta.ee/xml/ns/jakartaee https://jakarta.ee/xml/ns/jakartaee/beans_3_0.xsd"
        version="3.0" bean-discovery-mode="all">
</beans>

When using CDI 3.0 (available in Jakarta EE 9) the default value for bean-discover-mode is “all

Java Enterprise Edition 8

For applications running in Java Enterprise 8 (or equivalent Jakarta EE 8), you can use the following beans.xml schema:

<beans xmlns="http://xmlns.jcp.org/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/beans_2_0.xsd" bean-discovery-mode="all" version="2.0"> 
</beans>

Is the beans.xml file required?

The answer to your questions depends on the version of CDI.

For version 1.0 of CDI, beans.xml is mandatory to enable CDI bean discovery. Without beans.xml, CDI is simply not active in the corresponding archive.

Starting from CDI 1.1, beans.xml is no longer mandatory. And the scanning is as follow :

  • Omitting beans.xml, or setting bean-discovery-mode=”annotated” (default in Jakarta EE 10), makes the archive an implicit archive. In this case, the container will scan for Bean defining annotations. Here is an example of Bean which uses Bean defining annotations:
@ApplicationScoped
public class MyProducer {
    @PersistenceContext
    private EntityManager em;

    public Object query() {
    Query q = em.createNativeQuery("SELECT CURRENT_TIMESTAMP");

    return q.getSingleResult();

     }
}
  • On the other hand, by setting bean-discovery-mode=”all”, all classes will be scanned.
<beans xmlns="https://jakarta.ee/xml/ns/jakartaee"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="https://jakarta.ee/xml/ns/jakartaee https://jakarta.ee/xml/ns/jakartaee/beans_4_0.xsd"
       version="4.0" bean-discovery-mode="all">

</beans>

Beans.xml structure

The beans element can have one or more of each of the following children:

  • Interceptors
  • Decorators
  • Alternatives

Interceptors:

By default, a bean archive has no enabled interceptors bound via interceptor bindings. An interceptor must be explicitly enabled by listing the fully qualified class name in a child <class> element of <interceptors>.

There may be zero or more interceptor class elements. The order of the class declarations determines the interceptor ordering. Interceptors which occur earlier in the list are called first. The same class may not be listed twice. And of course, the class must exist and it must be an interceptor class.

<interceptors>
   <class>com.acme.intercept.SecurityInterceptor</class>
   <class>com.acme.intercept.TransactionInterceptor</class>
</interceptors>

Decorators:

By default, a bean archive has no enabled decorators. A decorator must be explicitly enabled by listing the fully qualified class name in a child <class> element of <decorators>.

There may be zero or more decorator class elements. The order of the class declarations determines the decorator ordering. Decorators which occur earlier in the list are called first. The same class may not be listed twice. And of course, the class must exist and it must be an decorator class.

<decorators>
   <class>com.acme.decorate.BigAccountDecorator</class>
   <class>com.acme.decorate.SpecialGiftDecorator</class>
</decorators>

Alternatives:

An alternative is a bean that must be explicitly declared in the beans.xml file if it should be available for lookup, injection or EL resolution. By default, a bean archive has no active alternatives. An alternative must be explicitly declared using the fully qualified bean class name or stereotype class name in either a child <class> or <stereotype> element of <alternatives>, respectively.
An alternative is selected for the bean archive if either: the alternative is a managed bean or session bean and the bean class of the bean is listed, or the alternative is a producer method, field or resource, and the bean class that declares the method or field is listed, or any @Alternative stereotype of the alternative is listed.
There may be zero or more alternative bean class elements. The same class may not be listed twice. And of course, the class must exist and it must be an alternative bean class.
There may also be zero or more @Alternative stereotype elements. The same stereotype may not be listed twice. And of course, the stereotype class must exist and it must be an stereotype annotation.

<stereotypes>
   <class>com.acme.business.MockPaymentProcessor</class>
   <stereotype>com.acme.stereotype.Mock</stereotype>
</stereotypes>
Found the article helpful? if so please follow us on Socials