9 Replies Latest reply on Sep 7, 2007 7:35 PM by gbc1

    Missing exceptions within asynchronious methods

    gbc1

      Hi!

      I did an asynchronious event today, being raised inside a conversation. The observer method throwed a custom RuntimeException and a Seam Excption that a injected component could not be found. At least it should have, because it was misspelled for sure and the RuntimeException was mine.

      But instead of showing up, both exceptions simple vanish. First I needed to start in Debug Mode to see the RuntimeException being thrown (Did not debug further). No output in the Server, although Seam is configured to use debug mode either. After putting a try/catch around the method code I was able to get my RuntimeException. Later after changing the class, injected another component, the method output (log.debug(...)) simply did not show up. After reading the source closely I finaly found the misspelled @In field.

      Where have the excptions gone? Is this a common behavoir for asynchronious methods, did I forget to configure something or is this a bug?

      Thanks for answering!

      Many Greetz, GHad

      Setup: WinXPSP2, JDK5.Update12, JBoss4.2GA, Seam2.0.0Beta1, Ant1.65, MyEclipse5.6

        • 1. Re: Missing exceptions within asynchronious methods
          pmuir

          Post the code for your async method.

          • 2. Re: Missing exceptions within asynchronious methods
            gbc1

            Sorry, my cody is at my business, no access at home, giving examples:

            @Stateful
            @Name("someComponent")
            public class someComponent implements SomeComponentLocalInterface {
            
            @Logger private Log log
            
            @Observer("myEvent")
            public void checkSomething(Some some) {
             throw new RuntimeException("Exception"); // no effect on jboss/seam
            /*
             try {
             throw new RuntimeException("Exception"); // works
             } catch (RuntimeException e) {
             log.degub("Error", e);
             }
            */
            }
            
            public void someMethod() {
             Events.instance().raiseAsynchroniousEvent("myEvent", new Some());
            }
            }
            


            Code for the missing Seam Component Exception like:

            
            @Stateful
            @Name("someComponent")
            public class SomeComponent implements SomeComponentLocalInterface {
            
            @Logger private Log log
            @In(create = true) private MyComponentLocalInterface myComponent
            
            @Observer("myEvent")
            public void checkSomething(Some some) {
             log.debug(myComponent.toString); // never executes
            }
            
            public void someMethod() {
             Events.instance().raiseAsynchroniousEvent("myEvent", new Some());
            }
            }
            
            @Stateful
            @Name("myCmponent") // Spell Error
            public class MyComponent implements MyComponentLocalInterface {
            }
            
            


            Ok, @Destroy method is missing, but my components at business do have them.

            So, first code does not show the thrown RuntimeException, second code sould have shown an Seam Exception that component could not be found...

            Hope this helps, thanks in advance

            • 3. Re: Missing exceptions within asynchronious methods
              gbc1

              Well, still want to know if it's a bug... Then I'll open a Jira issue

              Exception should at least show up, because I can imagine there is no user try/catch to get, but one could listen to the (not)handledError (not sure which one would be raised) Event and create a special Excption for Asynchronious cases

              Thanks, Greets GHad

              • 4. Re: Missing exceptions within asynchronious methods
                pmuir

                If you post real code (that would actually compile) then we can take a look at this.

                • 5. Re: Missing exceptions within asynchronious methods
                  gbc1

                  Ok, full working example code, tested just now.

                  First post regarding the missing RuntimeException (Second post follows later after coding example...):

                  Interface:

                  package org.esit.server.sessionbeans;
                  
                  import javax.ejb.Local;
                  
                  @Local
                  public interface Blob {
                  
                   public boolean isAvailable();
                  
                   public void raiseBlob();
                  
                   public void observeBlob();
                  
                   public void destroy();
                  
                  }
                  


                  SessionBean:
                  package org.esit.server.sessionbeans;
                  
                  import javax.ejb.Remove;
                  import javax.ejb.Stateful;
                  
                  import org.jboss.seam.annotations.Begin;
                  import org.jboss.seam.annotations.End;
                  import org.jboss.seam.annotations.In;
                  import org.jboss.seam.annotations.Name;
                  import org.jboss.seam.annotations.Observer;
                  import org.jboss.seam.core.Events;
                  import org.jboss.seam.faces.FacesMessages;
                  
                  @Stateful
                  @Name("blob")
                  public class BlobAction implements Blob {
                  
                   @In FacesMessages facesMessages;
                  
                   @In Events events;
                  
                   public boolean isAvailable() {
                   boolean out = true;
                   facesMessages.add("isAvailable(): #0", out);
                   return out;
                   }
                  
                   @Begin
                   @End
                   public void raiseBlob() {
                   facesMessages.add("raiseEvent() called");
                   events.raiseAsynchronousEvent("blob");
                   }
                  
                   @Observer("blob")
                   public void observeBlob() {
                   System.out.println("blob");
                   throw new RuntimeException("blob");
                   }
                  
                   @Remove
                   public void destroy() { }
                  }
                  
                  


                  Called by blob.xhtml (seam generated and edited)
                  <!DOCTYPE composition PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
                   "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
                  <ui:composition xmlns="http://www.w3.org/1999/xhtml"
                   xmlns:s="http://jboss.com/products/seam/taglib"
                   xmlns:ui="http://java.sun.com/jsf/facelets"
                   xmlns:f="http://java.sun.com/jsf/core"
                   xmlns:h="http://java.sun.com/jsf/html"
                   xmlns:rich="http://richfaces.ajax4jsf.org/rich"
                   xmlns:a="https://ajax4jsf.dev.java.net/ajax"
                   template="layout/template.xhtml">
                  
                  <ui:define name="body">
                  
                   <h:messages globalOnly="true" styleClass="message"/>
                  
                   <rich:panel>
                   <f:facet name="header">blob</f:facet>
                  
                   <h:form id="blobActionForm">
                  
                   <h:commandButton id="isAvailable" value="isAvailable!"
                   action="#{blob.isAvailable}"/>
                  
                   <h:commandButton id="raiseBlob" value="raiseBlob!"
                   action="#{blob.raiseBlob}"/>
                  
                   </h:form>
                  
                   </rich:panel>
                  
                  </ui:define>
                  
                  </ui:composition>
                  


                  Fresh seam-gen project, no further configuration gives only following Server output on JBoss 4.2 (using Java 1.5 Beta 12 and Seam 2.0 Beta1):
                  ...
                  23:31:40,437 INFO [STDOUT] blob
                  ...
                  


                  But no sign of the RuntimeException. I tried to throw the RuntimeException in method raiseBlob() directly and voilá, there it is as expected.

                  Missing RuntimeException, where are you?

                  Note: Just tested without
                   @Begin
                   @End
                  

                  with same effect

                  Greetz, GHad

                  • 6. Re: Missing exceptions within asynchronious methods
                    gbc1

                    Second Post regarding the missing Seam Exception:

                    Here I have two SessionBeans:

                    Interface One:

                    package org.esit.server.sessionbeans;
                    
                    import javax.ejb.Local;
                    
                    @Local
                    public interface Blob {
                    
                     public boolean isAvailable();
                    
                     public void raiseBlob();
                    
                     public void destroy();
                    
                    }
                    


                    SessionBean One:
                    package org.esit.server.sessionbeans;
                    
                    import javax.ejb.Remove;
                    import javax.ejb.Stateful;
                    
                    import org.jboss.seam.annotations.In;
                    import org.jboss.seam.annotations.Logger;
                    import org.jboss.seam.annotations.Name;
                    import org.jboss.seam.core.Events;
                    import org.jboss.seam.faces.FacesMessages;
                    import org.jboss.seam.log.Log;
                    
                    @Stateful
                    @Name("blob")
                    public class BlobAction implements Blob {
                    
                     @In FacesMessages facesMessages;
                    
                     @In Events events;
                    
                     @Logger Log log;
                    
                     public boolean isAvailable() {
                     boolean out = true;
                     facesMessages.add("isAvailable(): #0", out);
                     return out;
                     }
                    
                     public void raiseBlob() {
                     facesMessages.add("raiseEvent() called");
                     events.raiseAsynchronousEvent("blob");
                     }
                    
                     @Remove
                     public void destroy() { }
                    }
                    


                    Interface Two:
                    package org.esit.server.sessionbeans;
                    
                    import javax.ejb.Local;
                    
                    @Local
                    public interface Foo {
                    
                     public void observeBlob();
                    
                     public void destroy();
                    
                    }
                    


                    SessionBean Two:
                    package org.esit.server.sessionbeans;
                    
                    import javax.ejb.Remove;
                    import javax.ejb.Stateful;
                    
                    import org.jboss.seam.annotations.In;
                    import org.jboss.seam.annotations.Name;
                    import org.jboss.seam.annotations.Observer;
                    
                    @Stateful
                    @Name("fooAction")
                    public class FooAction implements Foo{
                    
                     @In(create=true) Blob blb;
                    
                     @Observer("blob")
                     public void observeBlob() {
                     System.out.println("blob");
                     throw new RuntimeException("blob");
                     }
                    
                     @Remove
                     public void destroy() {
                     }
                    
                    }
                    


                    Same Page with invoking button gives no server output at all. The injected Blob variable name is misspelled so that the component cannot be found.

                    Correcting the variable name to blob, the server shows only
                    [code|
                    23:56:35,359 INFO [STDOUT] blob
                    [/code|
                    like in the example above and no RuntimeException again.

                    So long, Greetz GHad

                    • 7. Re: Missing exceptions within asynchronious methods
                      gbc1

                      No one able to see an issue or a bug in my code?

                      I can image that there is no context alive when the exception is being thrown. But shouldn't JBoss or at least Seam print out the exception?

                      Greetz, GHad

                      • 8. Re: Missing exceptions within asynchronious methods
                        pmuir

                        Control at this point has been passed to the relevant dispatcher (java.util.concurrent.ScheduledThreadPoolExecutor by default) and its up to that to deal with any exceptions thrown. I'm not sure why they aren't printed to the JBoss AS console.

                        • 9. Re: Missing exceptions within asynchronious methods
                          gbc1

                          Thank you for your reply!

                          I guessed something like this... Isn't Seam then using a try/catch around invocation of ScheduledThreadPoolExecutor? If true, Seam may pass output along.

                          Greetz GHad