Wednesday, January 12, 2011

JBoss, JNDI and java:comp/env

On startup JBoss will process any xyz-service.xml files it finds in the deploy folder before it processes any war or ear files, etc.  One thing this could be useful for is to preload configuration values into JNDI, thus making them available to web applications when they start up.  It may sound simple but it consists of a non-obvious four step process:

1.  Create a JNDIBindingServiceMgr mbean in the xzy-service.xml file.

2.  In the WEB-INF/jboss-web.xml file map a resource-env-ref entry over to a JNDI value bound in step 1.

3.  In the WEB-INF/web.xml file create a resource-env-ref entry for each JNDI bound value.

4.  Access the JNDI value from somewhere, such as a servlet filter, using 'java:comp/env'

First, the xyz-service.xml file:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE server PUBLIC "-//JBoss//DTD MBean Service 4.0//EN"
    "http://www.jboss.org/j2ee/dtd/jboss-service_4_0.dtd">
<server>

    <mbean code="org.jboss.naming.JNDIBindingServiceMgr"
           name="netcds.cas.client:service=JNDIBindingServiceMgr">

        <attribute name="BindingsConfig" serialDataType="jbxb">

            <jndi:bindings
                xmlns:xs="http://www.w3.org/2001/XMLSchema-instance"
                xmlns:jndi="urn:jboss:jndi-binding-service:1.0"
                xs:schemaLocation="urn:jboss:jndi-binding-service:1.0 resource:jndi-binding-service_1_0.xsd">

                <jndi:binding name="my/jndi/property">
                    <jndi:value type="java.lang.Boolean">false</jndi:value>
                </jndi:binding>

            </jndi:bindings>
        </attribute>
        <depends>jboss:service=Naming</depends>
    </mbean>

</server>

Next, the resource-env-ref entry in the jboss-web.xml file:

    <resource-env-ref>
        <resource-env-ref-name>my/jndi/property</resource-env-ref-name>
        <jndi-name>my/jndi/property</jndi-name>
    </resource-env-ref>

And the associated web.xml entry:

    <resource-env-ref>
        <resource-env-ref-name>my/jndi/property</resource-env-ref-name>
        <resource-env-ref-type>java.lang.Boolean</resource-env-ref-type>
    </resource-env-ref>

Finally, accessing the JNDI value from a servlet filter:
      
    boolean result = false;
    try {
        InitialContext context = new InitialContext();
        result = (Boolean)context.lookup("java:comp/env/my/jndi/property");
    } catch (final NamingException e) {
        // log and/or sys out
    }

1 comment:

iamsyam said...

Hi,

Do you have an example for jndi bindings for JBoss 7.1.1 with a similar approach that you have taken in this example? i.e., service.xml..