6 Replies Latest reply on Oct 12, 2006 8:37 AM by jaikiran

    ClassCastException after redeploy

    ahachmann

      Hi there,
      I am quiet frustrated with having a strange behavior I do not understand.

      I have an EAR Application containing an EJB and a WAR.
      In the EJB I have a small HelloWorld Class being remote and local.

      I Call this class from the Servlet in the War. Which works perfectly fine.

      Now when I change the Code in the HelloWorld Class (simply changing the returned text) and redeploy this EAR, I get a ClassCastException when calling this Object.

      When I hav the WAR deployed itself in a different ctxPath, that servlet keeps working fine.

      My Bean:

      @Stateless
      @Local(MyDAO.class)
      @LocalBinding(jndiBinding="EpgData/LocalDao")
      @Remote(MyDAO.class)
      @RemoteBinding(jndiBinding="EpgData/RemoteDao")
      public class MyDAOImpl implements MyDAO {
      
       public String getObject() {
       // TODO Auto-generated method stub
       return "Hi There?! Someone";
       }
      
      }
      


      my servlet:
       public void doGet(HttpServletRequest arg0, HttpServletResponse arg1) throws ServletException, IOException {
       arg1.setContentType("text/html");
       PrintWriter out = arg1.getWriter();
       Context ctx;
       try {
       ctx = new InitialContext();
       out.println("2----------------------------------------------------------------<br>");
       Object o;
       try {
       o = ctx.lookup("EpgData/LocalDao");
       MyDAO hello = (MyDAO)o;
       out.println(hello.getObject());
       } catch (NamingException e) {
       // TODO Auto-generated catch block
       out.println("Second: "+e);
       }catch (ClassCastException e){
       e.printStackTrace(out);
       out.println(reflect(ctx.lookup("LOVE")));
       }
      
       } catch (NamingException e) {
       // TODO Auto-generated catch block
       out.println("Outer: "+e);
       }
       }
      
      


        • 1. Re: ClassCastException after redeploy
          ahachmann

          I would be very happy if anyone could help me.
          Any Ideas?

          Thx,
          Alexander

          • 2. Re: ClassCastException after redeploy
            jaikiran

            Where are placing the remote and home interfaces of your beans. Is it in two separate locations(once in war and once in a jar)? If yes, then maintain it at only one place and remove those interfaces from the war.

            Have a look at:

            http://wiki.jboss.org/wiki/Wiki.jsp?page=ClassLoadingOverview

            Here's an extract from the same:

            I get ClassCastException

            Assuming it is the same class name, this problem relates to classes getting loaded from different classloaders. At compile time your class has only one identity, its name. If you "deploy" a class many times in different jars, it has multiple identities. They are not the same. See below for more information on the solutions to this problem.

            This can also be caused by you only redeploying part of your application. e.g. a webapp uses an EJB and you only redeploy the EJB. The webapp will still have the old versions of the classes.


            Also, look at:

            http://wiki.jboss.org/wiki/Wiki.jsp?page=ClassCastExceptions
            Specifically, the jmx-console method mentioned over there




            • 3. Re: ClassCastException after redeploy
              ahachmann

              Yes, that helped. Thank you.

              Does this mean, that I have to build different packages if I wish to deploy one of those Packages on a diferent Server?

              I hoped, that I could simply put this Package on a different Server and
              remap the JNDI Name to the remote object. But for this Situation there are
              the Interfaces missing.

              So this was not where its going with EJB3?

              Regards,
              Alexander

              • 4. Re: ClassCastException after redeploy
                jaikiran

                If you packaging your war inside the ear(which also includes the ejb jars), then the remote/home interfaces need not be in the war file, since the war is *part of the ear application* which contains the necessary interfaces. However if you want the war to be a separate archive(outside the ear), then you will have to ship the remote/home interfaces of these ejbs since your war is no longer a part of the ear application - the war and the ear will act as two separate independent applications

                • 5. Re: ClassCastException after redeploy
                  ahachmann

                  Yes, this what i expected to happen,
                  But now I have the situation, that when I have taken the war out of the ear, I still need to leave out the Interfaces from the war.
                  When i deploy the archives at the same time, everything works fine. But when I now change the interfaces implementations and redeploy the ear, i get a class cast exception. I know, that this sounds like the opposite of what i wrote in the first post. And I am confused about that.

                  What I did now, is that i put the Interfaces in a single jar-file which i deploy itsself. Now i can modify the implementation without any problems.

                  Is it that way, that the Deployer perhaps does not recognise, that the Interfaces in the new EAR file are the same as the ones in the war file? Then the Classlaoder would load the interfaces again. But the ones in the ear are then different ones to the ones in the war.

                  Anyone a short comment whether this asumption could be right?

                  thx,
                  Alexander

                  • 6. Re: ClassCastException after redeploy
                    jaikiran

                    So you want to have a separate war containing the remote/home interfaces and also an ear containing these remote/home interfaces. You want these 2 to behave as two separate applications independent of each other. You will have to do classloader isolation as mentioned in
                    Section "Isolation" at:

                    http://wiki.jboss.org/wiki/Wiki.jsp?page=ClassLoadingConfiguration

                    Briefly, you will have to add the following entry to your jboss-web.xml(present in your war file) :

                    <jboss-web>
                     <class-loading java2ClassLoadingCompliance="false">
                     <loader-repository>
                     someName.someOtherName:loader=someUniqueName
                     <loader-repository-config>java2ParentDelegation=false</loader-repository-config>
                     </loader-repository>
                     </class-loading>
                    .....
                    </jboss-web>


                    And add the following to jboss-app.xml(present in ear file):

                    <jboss-app>
                     <loader-repository>
                     someName2.someOtherName2:loader=someOtherUniqueName
                     <loader-repository-config>
                     java2ParentDelegation=false
                     </loader-repository-config>
                     </loader-repository>
                    </jboss-app>


                    This will actually create 2 separate classloaders, one for the ear application and the other for the war application. You can then use the war separately from the ear file.