dev@javaserverfaces.java.net

Re: Re: bug seems to reoccures in 2.2.5 - page performance degrades significantly as page size increases

From: Edward Burns <edward.burns_at_oracle.com>
Date: Tue, 10 Jun 2014 08:46:42 -0700

>>>>> On Tue, 10 Jun 2014 14:28:45 +0000 (UTC), <erik.bamberg_at_oio.de> said:

EB> Hi,
EB> The tests uses server site state saving.

EB> No further configuration settings for Partial state saving have been
EB> done,
EB> so we are running the default behaviour. Means using Partial State
EB> saving.

Hello Erik,

I hope things are going well at OIO and in Mannheim. Give my regards to
Fr. Fassott. I hope I can come back and teach another class there some
day.

Now, on to the performance issue. I did some work on this recently under

https://java.net/jira/browse/JAVASERVERFACES-3193

here is the gist of these changes.

Consider this page
<https://svn.java.net/svn/mojarra~svn/branches/MOJARRA_2_2X_ROLLING/test/agnostic/facelets/findChild/src/main/webapp/AjaxTest.xhtml>.

Here is a sketch of the page.

<html>
  <h:head/>
  <h:body>
    <h:form>
      a small number of component and template text children
    </h:form>
    <h:form>
      a small number of component and template text children

      over 4,000 inputText and outputText children

      <h:panelGroup>

        over 4,000 inputText and outputText children

        <h:panelGroup>

           over 4,000 inputText and outputText children

        </h:panelGroup>

      </h:panelGroup>

    <h:form>
  </h:body>
</html>

I made the following optimizations, many of them suggested by Blake
Sullivan.

1. Make ComponentSupport.findChildByTagId (henceforth known as fcbti) a
no-op if called on a non-postback.

2. Make fcbti a no-op if called during RestoreView.

3. Make fcbti a no-op if called from UIInstructionHandler if
PartialStateSaving is false.

4. In fcbti, I use a for loop instead of using
UIComponent.getFacetsAndChildren(). Furthermore, I use an optimization
suggested by Andy Schwartz to return immediately if the named facet can
be found (JAVASERVERFACES-3308).

I instrumented fcbti with debug printlns that print out the value of i
and size of the components array in the following cases.

  A match is found.

  A match is found in the funny UIPanel subcase.

  A match is found when calling the method recursively.

For example:

INFO: debug: edburns: found c. i: 0 len: 4437

On the above page, I observe the component is always found at index 0.
This is due to the remove/re-add/cleanup-orphaned-children design of
Facelets. I observe this to be true with both full and partial state
saving. This observation leads me to conclude that the complexity
introduced by the "save the index" suggestion is unwarranted. Now,
let's get to some performance numbers.

In all cases stateSavingMethod=server, projectStage=Development.

Here are some numbers with Mojarra 2.2.5 on the above page:

PartialStateSaving=true

Initial render: 10.94 seconds
Non-Ajax postback: 8.7 seconds
Ajax postback: 9.3 seconds

PartialStateSaving=false

Initial render: 10.42 seconds
Non-Ajax postback: 0.92 seconds
Ajax postback: 0.92 seconds

Here are some numbers with the Mojarra 2.2.7-SNAPSHOT with the above
optimizations on the above page:

PartialStateSaving=true

Initial render: 2.72 seconds
Non-Ajax postback: 2.28 seconds
Ajax postback: 2.17 seconds

PartialStateSaving=false

Initial render: 2.15 seconds
Non-Ajax postback: 0.73 seconds
Ajax postback: 0.31 seconds

Conclusion: the O(n^2) behavior exhibited by fcbti can be avoided by
only calling the method when it can sensibly have a result.

SECTION: Modified Files
----------------------------
M jsf-ri/src/main/java/com/sun/faces/facelets/tag/jsf/ComponentSupport.java

- Add FacesContext to fcbti as first parameter. This is necessary to
  call isPostback() and to discover the current lifecycle phase.

- In fcbti, take no action if we are not on a postback, or we are in the
  RestoreView phase.

- In fcbti, don't use parent.getFacetsAndChildren(). Instead, only get
  the facets if there are facets. Otherwise, just use getChildren().


M jsf-ri/src/main/java/com/sun/faces/facelets/tag/jsf/ComponentTagHandlerDelegateImpl.java

- Pass FacesContext to fcbti.

M test/agnostic/facelets/findChild/nbactions.xml

- debug test update.
Sending jsf-ri/src/main/java/com/sun/faces/facelets/tag/jsf/ComponentSupport.java
Sending jsf-ri/src/main/java/com/sun/faces/facelets/tag/jsf/ComponentTagHandlerDelegateImpl.java
Transmitting file data ..
Committed revision 13285.

Erik, please try the latest 2.2.7-SNAPSHOT release, available at the
usual place. Here is the most recent SNAPSHOT release:

https://maven.java.net/content/repositories/snapshots/org/glassfish/javax.faces/2.2.7-SNAPSHOT/javax.faces-2.2.7-20140610.143345-51.jar

Please let us know what you find.

Ed

-- 
| edward.burns_at_oracle.com | office: +1 407 458 0017
| 14 business days til Santa Clara trip