9 Replies Latest reply on Apr 30, 2002 2:35 PM by phunsberger

    Local Interfaces ClassCastException

      I'm get a java.lang.ClassCastException when I try to retrieve a local interface.

      I get an object back from JNDI, then I try to cast it to the LocalHome interface. No such luck.

      Note: It's my understanding I don't need to 'narrow' for local interfaces.

      Code Snippet:

      // Get the Context;
      Context ctx = new InitialContext();
      // Return a Interface Object for Remote Home.
      Object obj = ctx.lookup("AlarmSession");
      // Causes ClassCastException
      AlarmSessionLocalHome alHome = (AlarmSessionLocalHome)obj;

      I'm stumped, I've tried
      "java:comp/env/ejb/AlarmSession"
      "java:comp/env/local/AlarmSession"
      "java:comp/env/AlarmSession"
      All of these aren't bound.

      Any help would be great!!

        • 1. Re: Local Interfaces ClassCastException
          duder

          Look at
          http://jboss.org/forums/thread.jsp?forum=50&thread=9594
          http://jboss.org/forums/thread.jsp?forum=47&thread=10977
          If your code runs under jboss-tomcat bundle somewhere in web module, then the problem can be catalina's class loading delegation model (by default it lookup classes in web-app classpath, then in parent classloader), I don't know if it's fixed already in some bundle.
          Try to remove client jar file with your local interfaces from your war file (as I understand it violates some j2ee related specs, but probably it will work - let me know in this case).

          • 2. Re: Local Interfaces ClassCastException
            jeffdelong

            I also had this problem, and then I noticed in the JNDIView that my EJB's JNDI names were not the jndi-name from the jboss.xml, rather I saw them under the Global JNDI Namespace under local -> EJBName. So I changed the string in ctx.lookup(local/EJBName) and that seemed to do the trick. Hope this helps.

            • 3. Re: Local Interfaces ClassCastException
              duder

              Guys, from the last reply (from jeffdelong) I realized that you did not use java:comp/env. Why don't you just try something like this in your ejb-jar or webapp deployment descriptor :

              <ejb-local-ref>
              <ejb-ref-name>ejb/local/AlarmSession</ejb-ref-name>
              <ejb-ref-type>Session</ejb-ref-type>
              <local-home>com.some_package.AllarmSessionLocalHome</local-home>
              AllarmSessionLocalHome
              <ejb-link>com.some_package.AllarmSessionEJB</ejb-link>
              </ejb-local-ref>

              and in your code it would be:

              Context ctx = new InitialContext()
              Object obj = ctx.lookup("java:comp/env/ejb/local/AlarmSession");
              // Causes ClassCastException
              AlarmSessionLocalHome alHome = (AlarmSessionLocalHome)obj;

              As I understand this is recommended technique. Using global jndi names for this is not good approach usually. There was luck of some features (such as specifying ejb-local-ref) in some old versions of jboss, but for 3.0. and 2.4.5 it's fixed as I know.

              Best regards

              • 4. Re: Local Interfaces ClassCastException
                duder

                I've checked, with ejb-local-ref/ejb-link class casting works if web module doesn't contain ejb local interface classes, otherwise it throws ClassCastException.

                • 5. Re: Local Interfaces ClassCastException
                  jeffdelong

                  In my case the local client was a java class running in the JBoss JVM; so it did not have access to java:comp/env. Your comments caused me to look again at the CMP example that comes with the paid docs, where I noticed that there is a local-jndi-name in the jboss.xml. So I added one to my jboss.xml one and use it on the lookup successfully.

                  • 6. Re: Local Interfaces ClassCastException
                    phunsberger

                    I'm missing something here (not too surprising, I'm new to JBoss). I thought that if we used the default names we didn't need a jboss.xml? Is this essentially a work around for the problem or should I be able to make this work without jboss.xml?

                    Can anyone spell out for me exactly what needs to be done? Changes to ejb-xml ? Create a jboss.xml? Changes to other files? We generate our ejb-xml automatically by running a class that does introspection over the EJB's (requires well defined EJB names) so if I can avoid having to create a jboss.xml I'd prefer that.

                    FWIW, I'm currently trying to get 2.4.5 to download but it's failed once after 45 minutes of downloading and is currently projected to take almost four hours to complete (over a T3 no less)!!!

                    • 7. Re: Local Interfaces ClassCastException
                      duder

                      What's to be done mostly depends on what kind of problem do you have and what do you want to get :)
                      For local and remote home interfaces, as I understand, JBoss will create some default binding to jndi, something like binding remote home interfaces by $ejb-name; and local home interfaces by local/$ejb-name;. If for some reason you lookup your home interfaces from global jndi context and/or have two applications having ejbs with the same ejb-name, then you probably will have some problems with deployment or porting on different app server. You can resolve it by providing jndi-name and/or local-jndi-name, also it gives you possibility to organize this part of jndi mapping according to your naming conventions.
                      As alternative, you can lookup your ejb interfaces not from global jndi context, but from java:comp/env, and your can configure it (at least in case of single j2ee application, possibly with several modules) via <ejb-ref> and/or <local-ejb-ref> plus <ejb-link>, in this case you don't need jboss.xml (but it also doesn't resolve problem, if it does exist and you have it, with multiple components with the same name in different applications) and your solution is portable between servers. For me it works fine, except that I have some troubles not related to class casting.

                      http://jboss.org/forums/thread.jsp?forum=46&thread=14157

                      As slightly different approach it's possible to use xslt to transform your ejb-jar.xml to jboss.xml and/or jbosscmp-jdbc.xml, where your can apply rules of binding to jndi context according to i.e. your package hierarchy, or any naming transformations, it works perfect for me as a part build process.

                      • 8. Re: Local Interfaces ClassCastException
                        duder

                        They say issue has been resolved
                        http://sourceforge.net/tracker/index.php?func=detail&aid=547160&group_id=22866&atid=376685

                        (you have to cut and paste link, for some reason it's parsed or formatted incorrectly)

                        • 9. Re: Local Interfaces ClassCastException
                          phunsberger

                          This turned out to be an error on our side: the particular EJB in question was in fact being invoked correctly. However, it was a base class far lower down on the hierarchy than the caller and was depending on the datasource JNDI name being passed to it in a data class. Going from Websphere 3 to JBoss I had to change some of the JNDI calls but missed this one since it an abnormal pattern for our code. As a result the JNDI name was not set, no datasource was returned and things blew up in the bean.

                          Why this resulted in a classCastException being reported isn't clear, I would have expected a nullPointerException, but all is working now.