11 Replies Latest reply on Jun 23, 2008 11:08 AM by felipealbertao

    ApplicationContext confusion

      Hi,


      I'm exposing an action method which sends out email through a WebService from a Seam application (using annotations - great stuff!).
      Everything is working properly, if the application has been accessed from a web browser before the SOAP request takes place.
      But if a SOAP request occurs right after a server restart, I'm facing a No application context active IllegalStateException despite a call to Contexts.isApplicationContextActive() in my action method returns true.


      The following is the snippet of my action method:


      log.debug("Application context #0", Contexts.isApplicationContextActive()?"is active":"ISN'T ACTIVE"); //indicates an active application context in the log
      renderer.render(viewId); //instance of type org.jboss.seam.faces.Renderer
      



      when renderer.render(viewId) is hit, the following exception is thrown:




      java.lang.IllegalStateException: No application context active
           at org.jboss.seam.Component.forName(Component.java:1812)
           at org.jboss.seam.Component.getInstance(Component.java:1862)
           at org.jboss.seam.Component.getInstance(Component.java:1845)
           at org.jboss.seam.Component.getInstance(Component.java:1824)
           at org.jboss.seam.Component.getInstance(Component.java:1819)
           at org.jboss.seam.mail.MailSession.instance(MailSession.java:279)
           at org.jboss.seam.mail.ui.UIMessage.getMailSession(UIMessage.java:62)
           at org.jboss.seam.mail.ui.UIMessage.getMimeMessage(UIMessage.java:77)
           at org.jboss.seam.mail.ui.MailComponent.findMimeMessage(MailComponent.java:94)
           at org.jboss.seam.mail.ui.UIFrom.encodeBegin(UIFrom.java:23)
           at org.jboss.seam.ui.util.JSF.renderChild(JSF.java:172)
           at org.jboss.seam.ui.util.JSF.renderChildren(JSF.java:163)
           at org.jboss.seam.mail.ui.UIMessage.encodeChildren(UIMessage.java:165)
           at org.jboss.seam.ui.util.JSF.renderChild(JSF.java:175)
           at org.jboss.seam.ui.util.JSF.renderChildren(JSF.java:163)
           at org.jboss.seam.ui.facelet.FaceletsRenderer.renderFacelet(FaceletsRenderer.java:206)



      I debugged the application and a call to Contexts.isApplicationContextActive() from org.jboss.seam.mail.MailSession.instance() returns indeed false.


      Could anyone explain why a previously active application context is not active in the MailSession?
      Is there a way to initialize the application context from the code (not by hitting the application from a browser)?


      Any help greatly appreciated!


      Best regards, Kurt

        • 1. Re: ApplicationContext confusion
          pmuir

          I don't really know the WS stuff in Seam at all, but could you show us how you call the Renderer - it looks like it's not being run inside a Seam request to me.

          • 2. Re: ApplicationContext confusion

            Thank you Pete for your reply.
            The Renderer is called from within a method annotated with @Observer and it is actually called after the WS Request, which tells me, that the Seam stuff is working, right? Please correct me, if I'm getting something wrong here.


            Here's the code actually invoking the renderer:


            @Observer(PasswordManager.PASSWORD_RESET_EVENT)
            public void sendPasswordReset() {
                 sendLocalizedEmail("/mail/passwordResetSuccess.xhtml", localeSelector.getLocaleString());
            }
            
            private void sendLocalizedEmail(String viewId, String localeString) {
                    log.debug("Will send localized mail '#0' with locale '#1'", viewId,localeString);
                    log.debug("Personal: " + personal);
                    if (!viewId.endsWith(TEMPLATE_EXTENSION))throw new IllegalArgumentException("Can only localize email templates with the extension .xhtml");
                    if (localeString == null)throw new IllegalArgumentException("Cannot localize an email with an localeString of 'null'");
                 try {
                 int extIdx = viewId.lastIndexOf(TEMPLATE_EXTENSION);
                 String vId = viewId.substring(0, extIdx) + "_"+localeString.toUpperCase() + TEMPLATE_EXTENSION;
                      try {
                           renderer.render(vId);
                      } catch (IllegalArgumentException e) {
                           if (e.getMessage().contains("resource doesn't exist:")) {
                           log.warn("Couldn't find the localized mail template '#0' - will try to send the generic one.",vId);
                           log.debug("Application context #0", Contexts.isApplicationContextActive()?"is active":"ISN'T ACTIVE"); //this one logs that the AppCtx IS ACTIVE
                           renderer.render(viewId);
                           } else {
                                log.warn("Couldn't render msg - Cause: " + e.getCause());
                                log.warn("Couldn't render msg - Msg:" + e.getMessage());
                           }
                      }
                      facesMessages.addFromResourceBundleOrDefault(RESET_PW_SUCCESS_MSG_KEY,RESET_PW_SUCCESS_MSG_DEFAULT);
                      } catch (Exception e) {
                           log.error("Couldn't send email!", e);
                           facesMessages.addFromResourceBundleOrDefault(
                                     FacesMessage.SEVERITY_WARN,
                                     RESET_PW_SUCCESS_BAD_EMAIL_MSG_KEY,
                                     RESET_PW_SUCCESS_BAD_EMAIL_MSG_DEFAULT);
                      }
            }
            
            



            The renderer is injected as the following snippet shows:


            @In(create = true)
            Renderer renderer;



            Since the renderer is actually called (hence is not null), this is another indication, that I'm being inside a Seam request, right?


            Any other pointers? I'm greatly appreciating your help!


            Best regards, Kurt

            • 3. Re: ApplicationContext confusion
              pmuir

              Can you debug in SOAPRequestHandler:handleOutbound() and see why, when it calls Lifecycle.beginRequest() the application context isn't being set up?

              • 4. Re: ApplicationContext confusion

                Thank you very much for your quick reply!


                I've set a breakpoint in SOAPRequestHandler.handleOutbound(), but the Exception occurs before the breakpoint is hit.
                The Exception is thrown, when MailSession.instance() want's to retrieve the MailSession component.


                I still wonder, under what circumstances a application context can get disabled.


                Best regards, Kurt

                • 5. Re: ApplicationContext confusion
                  pmuir

                  What component is the @Observer in? Can you try putting it in a different one to the component which handles the WS request?

                  • 6. Re: ApplicationContext confusion

                    Hi, thank you again for you interest!


                    The observer is already in a non-ws component. I've set it up as it is recommended in the reference manual.



                    • PasswordService/PasswordServiceRemote: Classe/Interface setting up the WebService (@WebService/@WebMethod Annotations)

                    • ResetPassword (JavaBean, Seam-Component @Name - doing the actual work - using another seam component to trigger the event)

                    • EmailRenderer (JavaBean with @Observer annotation)



                    The latter is the one I've posted earlier, which is actually calling Renderer.render() and does have an active application context.


                    Best regards, Kurt

                    • 7. Re: ApplicationContext confusion
                      pmuir

                      Ok, this is quite odd.


                      Can you create a JIRA issue, and attach a simple example to reproduce?

                      • 8. Re: ApplicationContext confusion

                        Hi!


                        Sorry for my late response, but I haven't been in the office lately.
                        I didn't had the chance to create a simple example, but I figured out, that the Exception only occurs after the seam application has been RE-deployed.
                        Everything is working fine as long as the application is deployed at server startup.


                        Best regards, Kurt

                        • 9. Re: ApplicationContext confusion
                          pmuir

                          Ok. Please still create a JIRA issue with as much info to reproduce as possible.

                          • 10. Re: ApplicationContext confusion

                            Hi Pete,


                            thank you again for your help so far. I've submitted a JIRA issue: http://jira.jboss.com/jira/browse/JBSEAM-2861


                            Best regards, Kurt

                            • 11. Re: ApplicationContext confusion
                              felipealbertao

                              Hello everyone,


                              I was experiencing this very same issue. I was able to create a workaround by calling the Seam component asynchronously. In other words, the web service schedules an async call for the next second, and then the scheduler indirectly calls the Seam component, which then renders the email. It's ugly, but it worked for me!


                              I posted more info here: My Link