Background: I am inheriting an ancient application that utilizes EJBs. In the facet of the project it lists as a 3.0 EJB. The EJB was written while running WebSphere 6.1 where we had two jvms, one for UI/Presentation Layer and a second JVM that hosted the EJB / "data layer" which is also using JPA. We are moving to WebSphere Liberty 8.5.5.8 and when I start my application and access it, I get the following exception:
....
Caused by:
com.ibm.wsspi.injectionengine.InjectionException: CWNEN0030E: The server was unable to obtain an object instance for the java:comp/env/ejb/CHServiceBean reference. The exception message was: CWNEN1003E: The server was unable to find the com.xxx.xxx.service.CHServiceRemote binding with the com.xxx.xxx.service.CHService type for the java:comp/env/ejb/CHServiceBean reference.
at com.ibm.wsspi.injectionengine.InjectionBinding.getInjectionObject(InjectionBinding.java:1458)
at com.ibm.ws.ejb.injection.processor.EJBInjectionBinding.getInjectionObject(EJBInjectionBinding.java:1047)
at com.ibm.wsspi.injectionengine.InjectionBinding.getInjectionObject(InjectionBinding.java:1389)
at com.ibm.ws.injectionengine.osgi.internal.naming.InjectionJavaColonHelper.getObjectInstance(InjectionJavaColonHelper.java:116)
... 44 more
Caused by:
com.ibm.wsspi.injectionengine.InjectionException: CWNEN1003E: The server was unable to find the com.xxx.xxxx.service.CHServiceRemote binding with the com.xxx.xxxxx.service.CHService type for the java:comp/env/ejb/CHServiceBean reference.
at com.ibm.ws.injectionengine.osgi.internal.IndirectJndiLookupObjectFactory.getObjectInstance(IndirectJndiLookupObjectFactory.java:202)
Here is the code that is accessing the context object: The supplied String jndiName that is failing is: "java:comp/env/ejb/CHServiceBean"
public Object getResource(String jndiName) throws Exception {
Object obj = null;
if (obj == null) {
try {
obj = new InitialContext().lookup(jndiName);
return obj;
} catch (Exception e) {
XXXXXX.error("ServiceLocator.getResource(...) ERROR, "");
throw e;
}
}
return obj;
}
We have two packaged EAR files, Ear file A called (CHNew.ear) which contains a .war called CHNew.war that contains most of the front end logic and in the deployment assembly references the CHService.jar file. Ear file B called (CHService.ear) houses the EJB code in a war project called CHService.war. They both reside on the same application server and thus the same jvm but are obviously not packaged in the same ear file.
Ear A has the following web.xml snippet:
<ejb-ref id="EjbRef_1430884948507">
<description>
</description>
<ejb-ref-name>ejb/CHServiceBean</ejb-ref-name>
<ejb-ref-type>Session</ejb-ref-type>
<home>com.xxx.xxx.service.CHService</home>
<remote>com.xxx.xxx.service.CHServiceRemote</remote>
</ejb-ref>
<ejb-ref id="EjbRef_1430885115133">
<ejb-ref-name>ejb/CHServiceBeanRO</ejb-ref-name>
<ejb-ref-type>Session</ejb-ref-type>
<home>com.xxx.xxxx.service.CHServiceRO</home>
<remote>com.xxx.xxx.service.CHServiceRemoteRO</remote>
</ejb-ref>
EDIT: Here is the contents of the ibm-web-bnx.xml file:
<?xml version="1.0" encoding="UTF-8"?>
<webappbnd:WebAppBinding xmi:version="2.0" xmlns:xmi="http://www.omg.org/XMI" xmlns:webappbnd="webappbnd.xmi" xmi:id="WebAppBinding_1430419801447" virtualHostName="default_host">
<webapp href="WEB-INF/web.xml#WebApp_ID"/>
<resRefBindings xmi:id="ResourceRefBinding_1430749102271" jndiName="services/cache/CHContacts">
<bindingResourceRef href="WEB-INF/web.xml#ResourceRef_1430749102271"/>
</resRefBindings>
<resRefBindings xmi:id="ResourceRefBinding_1436377001246" jndiName="jdbc/nextgen">
<bindingResourceRef href="WEB-INF/web.xml#ResourceRef_1436377001246"/>
</resRefBindings>
<resRefBindings xmi:id="ResourceRefBinding_1436377001247" jndiName="jdbc/nextgen_RO">
<bindingResourceRef href="WEB-INF/web.xml#ResourceRef_1436377001247"/>
</resRefBindings>
<resRefBindings xmi:id="ResourceRefBinding_1456409466488" jndiName="services/cache/CHGeneric">
<bindingResourceRef href="WEB-INF/web.xml#ResourceRef_1456409466488"/>
</resRefBindings>
<ejbRefBindings xmi:id="EjbRefBinding_1430884948507" jndiName="com.xxx.xxx.service.CHServiceRemote">
<bindingEjbRef href="WEB-INF/web.xml#EjbRef_1430884948507"/>
</ejbRefBindings>
<ejbRefBindings xmi:id="EjbRefBinding_1430885115133" jndiName="com.xxx.xxx.service.CHServiceRemoteRO">
<bindingEjbRef href="WEB-INF/web.xml#EjbRef_1430885115133"/>
</ejbRefBindings>
</webappbnd:WebAppBinding>
*There are binding .xmi (note not .xml) files from the past which I believe are ignored?
In the Ear App B there is an ibm-ejb-jar-bnd.xml file that contains the following stanza:
<session name="CHServiceBean">
<resource-ref name="jdbc/db" binding-name="jdbc/db"></resource-ref>
<resource-ref name="services/cache/CacheA" binding-name="services/cache/CHBluepages"></resource-ref>
<resource-ref name="services/cache/CacheB" binding-name="services/cache/CHGeneric" ></resource-ref>
</session>
<session name="CHServiceBeanRO">
<resource-ref name="jdbc/db_RO"
binding-name="jdbc/db_RO">
</resource-ref>
<resource-ref name="jdbc/db" binding-name="jdbc/db"></resource-ref>
<resource-ref name="services/cache/CHGeneric" binding-name="services/cache/CHGeneric"></resource-ref>
<resource-ref name="services/cache/CacheA" binding-name="services/cache/CacheB"></resource-ref>
</session>
Here is my Liberty server.xml file:
<!-- Enable features -->
<featureManager>
<feature>javaee-7.0</feature>
<feature>localConnector-1.0</feature>
<feature>distributedMap-1.0</feature>
<feature>adminCenter-1.0</feature>
<feature>ssl-1.0</feature>
<feature>usr:webCacheMonitor-1.0</feature>
<feature>webCache-1.0</feature>
<feature>ldapRegistry-3.0</feature>
</featureManager>
<!-- Admin Center Config Start -->
<!-- To access this server from a remote client add a host attribute to the following element, e.g. host="*" -->
<httpEndpoint host="*" httpPort="9080" httpsPort="9443" id="defaultHttpEndpoint"/>
<keyStore id="defaultKeyStore" password="xxxxxx"/>
<basicRegistry id="basic">
<user name="wpsadmin" password="xxxxxx"/>
</basicRegistry>
<administrator-role>
<user>wpsadmin</user>
</administrator-role>
<remoteFileAccess>
<writeDir>${server.config.dir}</writeDir>
</remoteFileAccess>
<!-- Automatically expand WAR files and EAR files -->
<applicationManager autoExpand="true"/>
<applicationMonitor updateTrigger="mbean"/>
<enterpriseApplication id="CHNewCHRDMEAR" location="CHNewCHRDMEAR.ear" name="CHNewCHRDMEAR">
<application-bnd>
<security-role name="AllAuthenticated">
<special-subject type="ALL_AUTHENTICATED_USERS"/>
</security-role>
</application-bnd>
</enterpriseApplication>
<enterpriseApplication id="CHServiceEAR" location="CHServiceEAR.ear" name="CHServiceEAR"/>
<!-- JAAS Authentication Alias (Global) Config -->
<authData id="r4dba" password="{xor}MzhmJT06ajI=" user="r4dba"/>
<!-- JDBC Driver and Datasource Config -->
<library id="DB2JCC4Lib">
<fileset dir="C:\DB2\Jars" includes="db2jcc4.jar db2jcc_license_cisuz.jar"/>
</library>
</server>
Questions:
You've shown the ibm-ejb-jar-bnd.xml, but you need to show the ibm-web-bnd.xml from CHNew.war. The error message suggests you have a binding configured like:
<ejb-ref name="ejb/CHServiceBean" binding-name="com.xxx.xxx.service.CHServiceRemote">
...or something like this if you're using ibm-web-bnd.xmi:
<ejbRefBindings xmi:id="EjbRefBinding_1430884948507" jndiName="com.xxx.xxx.service.CHServiceRemote">
<bindingEjbRef href="WEB-INF/web.xml#EjbRef_1430884948507"/>
</ejbRefBindings>
The Liberty profile only binds EJBs to the java:
namespace and never to the default namespace (which includes names like com.xxx.xxx.service.CHServiceRemote
), so this lookup will always fail. See the "Naming" section of the Using enterprise JavaBeans with remote interfaces on Liberty topic in the Knowledge Center. You need to update the binding-name to something like java:global/CHService/CHService/CHServiceBean
. See the CNTR0167I message in messages.log for the exact string to use.