Java – EJB 3: Accessing a stateful session bean from an application client

application-clientejb-3.0javastateful-session-bean

I am having some trouble accessing a stateful session bean (SFSB) from an application client. I am using JBoss 5.0.1.GA. The application client and the EJBs are both packaged in an EAR which deploys and I have other application clients which work without problems. So far, I have only used stateless session beans (SLSBs), but as far as I unterstand it, the differences between SLSBs and SFSBs should not affect how they can be accessed from an application client.

The structure of the classes/interfaces:

@Local public interface A {...}

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

@Remote public interface B {...}

@Stateful public class BBean implements B {
    @EJB private A anInstanceOfA;

    @PostConstruct private void init() {
        this.anInstanceOfA.someMethod();
    }
}

The application client is run via the "appclient-launcher" as described in "How to use an application client in JBoss 5". Doing the lookup of "BBean" works fine until someMethod() on the (local) ABean is called during the execution of init(). During that call, the container throws an InvalidStateException("Local call: security context is null") (as the root cause). When I change the stateful bean to a stateless bean, everything works fine (except, of course, that the state is not preserved). Interestingly, I can use the exact same SFSB from a web application (in a JSF managed-bean) just fine.

Am I doing something wrong? How am I supposed to use a SFSB from an application client?

I have not found anything useful about this particular problem so far. The exception is mentioned in a similar context in [#JBAS-4317] Security Context over the invocation, but considering that it is marked as done and is fixed in JBoss 5.0.0.Beta3, it seems not to be the same problem.

Best Solution

Even though I'd still like to know why my original setup it works perfectly for stateless session beans but not for stateful session beans, here is the solution I found:

The web-application that is also packaged in the EAR does its authentication via JAAS. For this I have configured a security domain in the JBoss login-config.xml, which looks like this:

<application-policy name="My-SD">
    <authentication>
        <login-module code="org.jboss.security.auth.spi.DatabaseServerLoginModule" flag="required">
            <module-option name="unauthenticatedIdentity">guest</module-option>
            <module-option name="dsJndiName">java:/myDS</module-option>
            <module-option name="principalsQuery">SELECT PASSWORD FROM LOGIN WHERE LOGIN = ? AND STATUS > 0</module-option>
            <module-option name="rolesQuery">SELECT ROLE, 'Roles' FROM USER_ROLE WHERE LOGIN = ?</module-option>
        </login-module>
    </authentication>
</application-policy>

I have used this security domain in the web-application's jboss-web.xml as well as in the EJB-project's jboss.xml, even though I actually only use it in the web-app (the EJBs are accessible without authentication).

To solve the problem with accessing the SFSB, I just had to remove my security domain from the jboss.xml in the EJB-project. This then makes JBoss use the default security domain which seems to do the right thing and my application client finally can access and use the SFSB.