-
1. Re: Seam Injecting EJB3 in Websphere.
jbalunas.jbalunas.jboss.org Jun 10, 2008 2:27 PM (in response to rkpraveenp)Hello,
Take a look and compare with the jee5 example in the reference guide. WebSphere's EJB3 injection and scoping is a little strange. You need to do the
trick
in the web.xml so that Websphere will make the EJBs available to the application.If that does not work can you post your web.xml, and components.xml? Also post the errors you see.
Thanks,
Jay -
2. Re: Seam Injecting EJB3 in Websphere.
rkpraveenp Jun 11, 2008 11:25 AM (in response to rkpraveenp)Hello,
Thank you for the response. The following is what I am trying:
Through seam, trying to inject a stateless session bean into another stateless session bean using the \@In annotation.Both EJBs are in the same Jar file. I am invoking SessionBeanB.methodB through a standalone java client from the command line (using JDK1.5.0 update 14) by getting the SessionBeanB using JNDI name through iiop. I have also done the classloader settings in WAS as per documentation and followed other steps in http://in.relation.to/Bloggers/WebSphereRunningSeamsJEE5BookingExample
The code sample, web.xml, component xml and error are as follows.
Java Code
com.test.SessionBeanA.java @Name("sessionBeanA") @Scope(ScopeType.STATELESS) @Stateless public class SessionBeanA implements iARemote, iALocal{ public void methodA(){} }
Note: iARemote interface is annotated as \@Remote and iALocal interface is annotated as \@Local.
com.test.SessionBeanB.java @Name("sessionBeanB") @Scope(ScopeType.STATELESS) @Stateless //Note: iBRemote interface is annotated as @Remote and iBLocal interface is annotated as @Local public class SessionBeanB implements iBRemote, iBLocal{ @In(create = true) iALocal sessionBeanA; //I have also tried the following: //@In(create = true) //SessionBeanA sessionBeanA public void methodB(){ sessionBeanA.methodA(); } }
Component.xml
<core:init debug="true" jndi-pattern="java:comp/env/TestApp/#{ejbName}"/> <core:manager concurrent-request-timeout="500" conversation-timeout="120000" conversation-id-parameter="cid"/> <persistence:managed-persistence-context name="em" auto-create="true" entity-manager-factory="#{Test_EMFactory}"/> <persistence:entity-manager-factory name="Test_EMFactory" persistence-unit-name="TestUnit"/> <transaction:ejb-transaction />
Note: The entity manager is getting created and working fine.
Web.xml
<ejb-local-ref> <ejb-ref-name>TestApp/SessionBeanA</ejb-ref-name> <ejb-ref-type>Session</ejb-ref-type> <local-home></local-home> <local>com.test.iALocal</local> </ejb-local-ref>
Note: Web.xml is part of the standard web module which got created using seam-gen.
Error (in Websphere log)
ExceptionUtil E CNTR0020E: EJB threw an unexpected (non-declared) exception during invocation of method "methodB" on bean "BeanId(TestApp#TestApp.jar#SessaionBeanA, null)". Exception data: org.jboss.seam.InstantiationException: Could not instantiate Seam component: sessionBeanA at org.jboss.seam.Component.newInstance(Component.java:1970) at org.jboss.seam.Component.getInstance(Component.java:1873) at org.jboss.seam.Component.getInstance(Component.java:1840) at org.jboss.seam.Component.getInstanceInAllNamespaces(Component.java:2182) at org.jboss.seam.Component.getValueToInject(Component.java:2134) Caused by: javax.naming.NameNotFoundException: Name comp/env/TestApp not found in context "java:". at com.ibm.ws.naming.ipbase.NameSpace.getParentCtxInternal(NameSpace.java:1767) at com.ibm.ws.naming.ipbase.NameSpace.lookupInternal(NameSpace.java:1083) at com.ibm.ws.naming.ipbase.NameSpace.lookup(NameSpace.java:991) at com.ibm.ws.naming.urlbase.UrlContextImpl.lookup(UrlContextImpl.java:1263) at com.ibm.ws.naming.java.javaURLContextImpl.lookup(javaURLContextImpl.java:384) at com.ibm.ws.naming.java.javaURLContextRoot.lookup(javaURLContextRoot.java:204) at com.ibm.ws.naming.java.javaURLContextRoot.lookup(javaURLContextRoot.java:144) at javax.naming.InitialContext.lookup(InitialContext.java:363) at org.jboss.seam.Component.instantiateSessionBean(Component.java:1287) at org.jboss.seam.Component.instantiate(Component.java:1273) at org.jboss.seam.Component.newInstance(Component.java:1966) ...36 more
-
3. Re: Seam Injecting EJB3 in Websphere.
jbalunas.jbalunas.jboss.org Jun 11, 2008 3:20 PM (in response to rkpraveenp)The error that you are seeing is not that it can't find the bean. It is that it can't find your app
TestApp
. Although these can be related.Here are some questions/suggestions:
- Do you have any other entries in your web.xml?
- When you deploy do you see all of the beans from the web.xml listed on the Map EJB references to beans page?
- On the Map EJB references to beans do you select Allow EJB reference targets to resolve automatically?
The core problem here is that the WAR is not provided/linked to the EJB context in the EAR. That is why your command line client can get to the EJB but your WAR can't. The steps during deployment and in the web.xml are key to this.
This was one of the trickier issues to work out. Take a look at the reference guide because it contains more information about the the apps than the getting started guide.
-
4. Re: Seam Injecting EJB3 in Websphere.
rkpraveenp Jun 12, 2008 4:13 PM (in response to rkpraveenp)Hello,
With regards to your questions,
* Do you have any other entries in your web.xml?
No. Nothing outside of what seam-gen puts in and what is in the guides.* When you deploy do you see all of the beans from the web.xml listed on the Map EJB references to beans page?
Yes, they are listed as per the web.xml
* On the Map EJB references to beans do you select Allow EJB reference targets to resolve automatically?
Yes. I do select this option.One observation I have is that in the Websphere log, the beans get deployed under the following JNDI names:
Remote: ‘ejb/TestApp/TestApp.jar/SessionBeanA#com.test.iARemote’ or ‘com.test.iARemote’
Local: ‘ejblocal:TestApp/TestApp.jar/SessionBeanA#com.test.iALocal’ or ‘ejblocal:com.test.iALocal’
So, I am not clear on how they can be accessed using the jndi-pattern given in the component XML.
Am also going through all the settings and the guide again to make sure that I have not missed anything.
Thank you.
-
5. Re: Seam Injecting EJB3 in Websphere.
sanjeevsirigere Jun 27, 2008 2:45 AM (in response to rkpraveenp)Hi,
I was also working on getting Seam to work with EJB 3 components on Websphere 6.1.0.17 with EJB3 fp + webservice fp. I am using the Seam version jboss-seam-2.0.1.GA. Initially my approach was to get the Booking sample to work. After sometime, I realized that, instructions to configure were not complete and could not get it working.So I started with simple Seam-gen project and customized it for Websphere.. With that and my changes, I could able to get the seam injection working. Following are my observations.
Configuring Seam
If Seam component is a EJB3 component, then seam binds the component to a JNDI name. Seam resolves the JNDI name of the component by looking at the below configuration in the components.xml file.
components.xml
Example: <core:init debug="true" jndi-pattern="java:comp/env/Websphere_seam/#{ejbName}"/>
In the above example, seam is configured to bind the ejb component to a logical JNDI name. at runtime, seam will replace the string #{ejbName} with the actual component name.
Configuring the deployment descriptor
To bind the ejb component com.somepackage.ejbs.SeamEJB to jndi name, java:comp/env/Websphere_seam/SeamEJB, add the below configuration to the EJB component, which needs the SeamEJB seam component to be injected.
ejb-jar.xml
<?xml version="1.0" encoding="UTF-8"?> <ejb-jar xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/ejb-jar_3_0.xsd" version="3.0"> <enterprise-beans> <session> <ejb-name>EJB3</ejb-name> <ejb-local-ref> <ejb-ref-name>Websphere_seam/SeamEJB</ejb-ref-name> <local>com.somepackage.ejbs.SeamEJBInterface</local> </ejb-local-ref> </session> </enterprise-beans> <interceptors> <interceptor> <interceptor-class> org.jboss.seam.ejb.SeamInterceptor </interceptor-class> </interceptor> </interceptors> <assembly-descriptor> <interceptor-binding> <ejb-name>*</ejb-name> <interceptor-class> org.jboss.seam.ejb.SeamInterceptor </interceptor-class> </interceptor-binding> </assembly-descriptor> </ejb-jar>
Please use ejb-local-ref element instead of ejb-ref element in the above tag for configuring the EJB's local interface. Check out the section Configuring Seam if local EJB references are used below to configure the Seam.
Configuring Websphere
Websphere has a feature called AutoLink to generate the JNDI names for the EJB3 coponent. With this, we will not be able to provide the JNDI names as configured in the components.xml. To override this feature, we need to add the below IBM specific deployment description in META-INF directory of the ejb jar file.
META-INF/ibm-ejb-jar-bnd.xml <?xml version="1.0" encoding="UTF-8"?> <ejb-jar-bnd xmlns="http://websphere.ibm.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://websphere.ibm.com/xml/ns/javaee http://websphere.ibm.com/xml/ns/javaee/ibm-ejb-jar-bnd_1_0.xsd" version="1.0"> <session name="SeamEJB" simple-binding-name="ejb/Websphere_seam/xyz" /> <session name="EJB3"> <ejb-ref name="Websphere_seam/SeamEJB" binding-name="ejb/Websphere_seam/xyz" /> </session> </ejb-jar-bnd>
Configuring Seam if local EJB references are used
If a local EJB is configured, Seam will throw the following error
Caused by: javax.naming.ConfigurationException: NamingManager.getURLContext cannot find the factory for this scheme: ejblocal at com.ibm.ws.naming.jndicos.CNContextImpl.checkForUrlContext(CNContextImpl.java:3389) at com.ibm.ws.naming.jndicos.CNContextImpl.lookupExt(CNContextImpl.java:1555) at com.ibm.ws.naming.util.IndirectJndiLookupObjectFactory$1.run(IndirectJndiLookupObjectFactory.java:374)
Add the below configuration file to the root of the web context.
file name seam-jndi.properties com.ibm.websphere.naming.hostname.normalizer=com.ibm.ws.naming.util.DefaultHostnameNormalizer java.naming.factory.initial=com.ibm.websphere.naming.WsnInitialContextFactory com.ibm.websphere.naming.name.syntax=jndi com.ibm.websphere.naming.namespace.connection=lazy com.ibm.ws.naming.ldap.ldapinitctxfactory=com.sun.jndi.ldap.LdapCtxFactory com.ibm.websphere.naming.jndicache.cacheobject=populated com.ibm.websphere.naming.namespaceroot=defaultroot com.ibm.ws.naming.wsn.factory.initial=com.ibm.ws.naming.util.WsnInitCtxFactory com.ibm.websphere.naming.jndicache.maxcachelife=0 com.ibm.websphere.naming.jndicache.maxentrylife=0 com.ibm.websphere.naming.jndicache.cachename=providerURL java.naming.provider.url=corbaloc:rir:/NameServiceServerRoot java.naming.factory.url.pkgs=com.ibm.ws.runtime:com.ibm.ws.naming
Hope it helps. I am not sure, how I can upload my sample project.
-
6. Re: Seam Injecting EJB3 in Websphere.
kdubu Nov 18, 2008 10:54 PM (in response to rkpraveenp)Hi all,
is there any update with this issue, I'm having the exact same problem as Praveen. I'm using SEAM 2.0.1 deployed on WebSphere 6.1.0.19 plus ejb3 fp. I've retraced all my configuration steps and perform clean re-install of everything and the same problem occured. Did I miss something?
Java code:
@Local public interface IClassB { public boolean methodB(); }
@Stateless @Name("iclassb") public class ClassB implements IClassB { @Logger Log log; public boolean methodB() { // TODO Auto-generated method stub log.info("IN CLASS B"); return false; } }
@Stateless @Name("authenticator") public class AuthenticatorAction implements Authenticator { @Logger Log log; @In Identity identity; @In(create = true) IClassB iclassb; ....
Web.xml
<ejb-local-ref> <ejb-ref-name>myproject/ClassB</ejb-ref-name> <ejb-ref-type>Session</ejb-ref-type> <local-home></local-home> <local>com.mydomain.myproject.IClassB</local> </ejb-local-ref>
components.xml
<core:init jndi-pattern="java:comp/env/myproject/#{ejbName}" debug="true"/>
This is the exception
org.jboss.seam.InstantiationException: Could not instantiate Seam component: iclassb
....
Caused by: javax.naming.NameNotFoundException: Name comp/env/myproject not found in contextjava:
.
at com.ibm.ws.naming.ipbase.NameSpace.getParentCtxInternal(NameSpace.java:1767) -
7. Re: Seam Injecting EJB3 in Websphere.
jbalunas.jbalunas.jboss.org Nov 19, 2008 2:27 PM (in response to rkpraveenp)@Sanjeev Sirigere - thanks for your explanation, and details into websphere's EJB 3 support.
@ Ken Sanjeev Sirigere's post added a lot of information regarding the details of WebSphere and it's support. I would suggest reviewing his suggestions in addition to the reference guide chapter.
The Seam team has not updated of the WebSphere chapter in some time, but it is next on the list for review. When it is updated many of the suggestions provided by Sanjeev will be reviewed as well.
Please keep us informed of anything you find, and we will work it into the next update.
Regards,
Jay -
8. Re: Seam Injecting EJB3 in Websphere.
kdubu Nov 19, 2008 10:55 PM (in response to rkpraveenp)Hi Jay,
I'll follow Sanjeev's suggestion. Not really a WAS expert myself so will need to do some more reading/searching. I'll post an update on my progress back here. Looks like we'll have to manually bind the EJB - JNDI lookup and not use the automatic reference target option.
Ken
-
9. Re: Seam Injecting EJB3 in Websphere.
jeckhart Mar 27, 2009 9:33 PM (in response to rkpraveenp)Sanjeev
In regards to the following:
Add the below configuration file to the root of the web context.file name seam-jndi.properties com.ibm.websphere.naming.hostname.normalizer=com.ibm.ws.naming.util.DefaultHostnameNormalizer java.naming.factory.initial=com.ibm.websphere.naming.WsnInitialContextFactory com.ibm.websphere.naming.name.syntax=jndi com.ibm.websphere.naming.namespace.connection=lazy com.ibm.ws.naming.ldap.ldapinitctxfactory=com.sun.jndi.ldap.LdapCtxFactory com.ibm.websphere.naming.jndicache.cacheobject=populated com.ibm.websphere.naming.namespaceroot=defaultroot com.ibm.ws.naming.wsn.factory.initial=com.ibm.ws.naming.util.WsnInitCtxFactory com.ibm.websphere.naming.jndicache.maxcachelife=0 com.ibm.websphere.naming.jndicache.maxentrylife=0 com.ibm.websphere.naming.jndicache.cachename=providerURL java.naming.provider.url=corbaloc:rir:/NameServiceServerRoot java.naming.factory.url.pkgs=com.ibm.ws.runtime:com.ibm.ws.naming
I believe that these values are the defaults in WebSphere (http://publib.boulder.ibm.com/infocenter/wasinfo/v7r0/index.jsp?topic=/com.ibm.websphere.javadoc.doc/public_html/api/com/ibm/websphere/naming/PROPS.html), so pushing them to the initial context environment (which is what jndi.properties and seam-jndi.properties does) would seem to be redundant. Is this incorrect?
-
10. Re: Seam Injecting EJB3 in Websphere.
sanjeevsirigere Jul 1, 2010 9:22 AM (in response to rkpraveenp)yes. you are right. It has been a long time I worked on this issue. As far as I remember, InitialContext was initial with some wrong values. Due to which the above behavior. Other alternative I tried that time after posting this response was just add an empty seam-jndi.properties. That would enable the InitialContext to have the right value.
Hope this helps