1 Reply Latest reply on Feb 26, 2008 10:11 AM by Eric H

    Redirecting before rendering the page, if some condition

    Eric H Novice

      Here's my simple example: I have a page which displays invoices.  Call it /protected/show-invoice.xhtml.  It gets the Invoice object which it needs from the conversation context.


      If there is no Invoice in the conversation, like if the user types in http://example.com/protected/show-invoice.seam, the page really shouldn't display at all because it will be completely broken.  In fact, it should simply bounce the user straight to a search for an invoice page or something like that.


      I tried to do this with pages.xml:


          <page view-id="/protected/show-invoice.xhtml">
              
              <navigation>
                  <rule if="#{true}">
                      <redirect view-id="/protected/invoice-search.xhtml"/>
                  </rule>
              </navigation>
          </page>
          


      Note that I put in if="#{true}" which you would obviously not use in a real application.  I put that in there to force it to always trigger, so with that rule in place, it should never display but should always bounce straight to the invoice-search page.


      But that doesn't work.  The navigation rule isn't triggering when it is from a GET request (ie, the user types that in to his browser URL field).


      Is there a way to do this?  I'm aware of the <restrict> thing, but that's really for security checks, not for navigation.  I know that I can specify actions, which are method bindings which get called before the page is rendered.  But method bindings don't have a way to do a redirect; they are not Servlets.


      How do I do this the Seam way?


      Thanks

        • 1. Re: Redirecting before rendering the page, if some condition
          Eric H Novice

          I searched around some more after asking, and found this page with a handy trick:


          Redirect before rendering


          In essence, you create a dummy action, which can in fact be a true noop:


          @Name("helpfulPojo") public class HelpfulPojo {
            public void noop() { }
          }



          And then in pages.xml you do a trick like this:


              <page action="#{helpfulPojo.noop}" view-id="/protected/show-invoice.xhtml">
                  
                  <navigation from-action="#{helpfulPojo.noop}">
                      <rule if="#{true}">
                          <redirect view-id="/protected/invoice-search.xhtml"/>
                      </rule>
                  </navigation>
                  
              </page>



          And obviously, you would use some EL expression that's more meaningful than if="#{true}".


          It works!  The action attribute's method binding gets called before rendering, and that then hits the navigation rule because of the from-action attribute on it.


          Note the use of <redirect>, not a navigate-to or something like that.