3

I have a home page xhtml where i am including 3 child xhtml based on conditions. The issue i am facing is , whatever be the scenario,Book.xhtml always gets invoked. I changed the rendered condition to false or move out to another condition, but the file always gets invoked Due to which its backing bean also is invoked causing unwanted overhead. Please provide me a solution

<ui:composition template="/xhtml/baseLayout.xhtml">
    <ui:define name="browserTitle">
        <h:outputText value="HOME PAGE" />
    </ui:define>
    <ui:define name="header">
        <ui:include src="/xhtml/header.xhtml" />
    </ui:define>
    <ui:define name="bodyContent">

        <h:panelGrid width="100%"
            rendered="#{pogcore:isRoleAuthorized(BUNDLE.SUPER)}"  >
            <ui:include src="/xhtml/SuperUser.xhtml"  />
        </h:panelGrid>
        <h:panelGrid width="100%"
            rendered="#{pogcore:isRoleAuthorized(BUNDLE.MAINTENANCE)}" >
            <ui:include src="/xhtml/Maintenance.xhtml" />
        </h:panelGrid>

        <h:panelGrid width="100%"
            rendered="#{pogcore:isRoleAuthorized(BUNDLE.PRINT)}">
            <ui:include src="/xhtml/Book.xhtml" />
        </h:panelGrid>

    </ui:define>
</ui:composition>
cubbuk
  • 7,800
  • 4
  • 35
  • 62
Neerocks
  • 43
  • 1
  • 1
  • 6

2 Answers2

13

This is happening due to lifecycle of jsf. JSF UIComponents are evaluated during view render time where as jstl tags are evaluated at build time.

So when you use rendered attribute of h:panelGrid it is too late to not invoke managed beans under the included page. To resolve this try having conditions using jstl tag, the following should work for you.

<c:if test="#{bean.yourCondition}">
    <h:panelGrid width="100%"> 
        <h:outputText value="#{bean.yourCondition}"/> <!--if this is not getting printed there is smtg wrong with your condition, ensure the syntax, the method signature is correct-->
        <ui:include src="/xhtml/Book.xhtml" /> 
    </h:panelGrid>
</c:if> 
<c:if test="#{!bean.yourCondition}"> 
    <h:outputText value="#{bean.yourCondition}"/> <!--This should print false-->
</c:if>

The document below describes the details of jstl and jsf lifecycle.

http://www.znetdevelopment.com/blogs/2008/10/18/jstl-with-jsffacelets/

Check the following document to see another way to solve this without using jstl tags.

http://pilhuhn.blogspot.com/2009/12/facelets-uiinclude-considered-powerful.html

cubbuk
  • 7,800
  • 4
  • 35
  • 62
  • @cubbuk.Thanks a lot.I will try out this option – Neerocks Jan 18 '13 at 09:25
  • @cubbuk..I read some where that the scope of the underlying backing bean should not be ViewScoped for JSTL tags to work properly.Should i be making that change as well? – Neerocks Jan 18 '13 at 09:31
  • I didn't work with viewScope, but I remember reading something like that too, you should try it, please let us know if indeed it is needed or not =) – cubbuk Jan 18 '13 at 09:34
  • @cubbuk.When i add the above condition, book.xhtml is not included(Working Perfectly).But when BUNDLE.Print is indeed true & the subsequentrendered is also true, Book.xhtml does not seem to get rendered.Only when i refresh the page 2nd time, the page gets rendered.Tried this for both View & SessionScope.Both seem to show the same behavior – Neerocks Jan 18 '13 at 09:50
  • Did you remove the rendered attribute of the ? – cubbuk Jan 18 '13 at 09:59
  • No.I didnt.This is how my code look lik now – Neerocks Jan 18 '13 at 10:02
  • try setting the rendered attribute to true for both c:iftest and h:panelGrid and see whether it loads the xhtml page. When I try myself it includes the page, this shouldn't happen – cubbuk Jan 18 '13 at 10:08
  • @cubbuk.Yes,when i am setting both the values to "true" explicitly,page is rendering. – Neerocks Jan 18 '13 at 10:20
  • can you ensure the condition is true by printing on your page #{pogcore:isRoleAuthorized(BUNDLE.PRINT)} – cubbuk Jan 18 '13 at 10:22
  • Yes.I printed it.The condition is indeed true. – Neerocks Jan 18 '13 at 10:33
  • can you try the following: – cubbuk Jan 18 '13 at 10:42
  • The solution is correct, the explanation is not entirely correct. JSTL also uses EL! See http://stackoverflow.com/a/13992285/157882. – BalusC Jan 18 '13 at 10:55
  • @cubbuk..i tried the above option.It is not working.The page renders fine only if i refresh the page. – Neerocks Jan 18 '13 at 10:57
  • @BalusC..Since ui:include & runs during the build phase, the condition works & the logic to not include this xhtml when other pages are loaded works.But, it seems that even if resolves to true, the included xhtml does nt get included until the page is refreshed.Am i doing something wrong?I am stuck on this for 2 days now.Any help would be deeply appreciated. – Neerocks Jan 18 '13 at 12:05
  • @BalusC updated my answer (changed EL evaluated at render time with JSF UI components evaluated at view render time, thanks for the hint). Neerocks xhtml under include:ui should work, don't know whats the problem there, can you just make sure that c:if is evaluated to true by printing the condition just before including ui:include. If this method does not work please try the suggestion mentioned in the answer (this one: http://pilhuhn.blogspot.com/2009/12/facelets-uiinclude-considered-powerful.html) – cubbuk Jan 18 '13 at 12:27
  • @cubbuk. I tried to print the condition just after the & just before the include but that was never printed in the page. – Neerocks Jan 18 '13 at 12:34
  • Neerocks I updated my answer, change it according to your condition and see what does it print etc. If this is not printing try the other solution suggested in the answer. – cubbuk Jan 18 '13 at 12:53
  • @cubbuk.I tried the answer given above.When the condition is true, the out text is printed as "true" but the included page – Neerocks Jan 18 '13 at 13:10
  • Have no idea why this is happening, sorry mate. – cubbuk Jan 18 '13 at 13:12
  • @cubbuk.. I am confused .Would my included xhtml be causing an issue? My included xhtml follows the structure >>... – Neerocks Jan 18 '13 at 13:20
  • I tried myself with a similar page and it worked again, just try with an Hello Page and see if anything changes but I don't think the problem is about the page. – cubbuk Jan 18 '13 at 13:28
  • @cubbuk..is there any web.xml context parameter that i need to add? – Neerocks Jan 21 '13 at 05:17
  • As far as I know you don't need any. – cubbuk Jan 21 '13 at 07:39
  • @cubbuk..Thanks a lot.I was able to resolve this issue.After debugging, found that the c:if was some how returning false for the (bean.condition) but h:output was returning true during the same flow.Handled it in the bean & it is working smoothly now.Thanks for all your patience :) – Neerocks Jan 21 '13 at 14:46
0

Do this:

  • Always include the sub pages
  • Put the panelGrid (with the rendered) inside the page that you always include

Why ? Because the inclusion is performed before the rendered is evaluated.

Christophe Roussy
  • 16,299
  • 4
  • 85
  • 85
  • @Christophe.This option does include the xhtml but it gets included for all the home page requests.EVen if the rendered condition is false for Book.xhtml, this would get included. – Neerocks Jan 18 '13 at 12:00
  • If your rendered condition evaluates to false no HTML will be generated. Are you sure the condition evaluates to false ? – Christophe Roussy Jan 18 '13 at 13:33
  • Yes.The condition evaluated to false & still the backing bean methods associated with the xhtml got invoked. – Neerocks Jan 18 '13 at 14:02