MyFaces Core
  1. MyFaces Core
  2. MYFACES-3117

Current server state saving implementation prevents multi-window usage

    Details

    • Type: Bug Bug
    • Status: Closed
    • Priority: Critical Critical
    • Resolution: Fixed
    • Affects Version/s: 2.0.6-SNAPSHOT
    • Fix Version/s: 2.0.6, 2.1.0
    • Component/s: General
    • Labels:
      None
    • Environment:
      myfaces core trunk

      Description

      Problem:

      open two tabs (or windows) in browser with view:

      <h:body>
      <h:form id="formId">
      <h:commandButton value="Click me 20x!" />
      </h:form>
      </h:body>

      then click the button on the first tab 20x or more -> then click the button on the second tab -> you will get the most beloved ViewExpiredException.

      Reason:
      oam.SerializedViewCollection drops the saved state for 2. tab from map.

      Suggestion:
      remove the successfully restored view state from map. This can be done, because each SerializedViewKey is unique over all requests for one HttpSession - see DefaultFaceletsStateManagementHelper.nextViewSequence(FacesContext). Because each request has unique sequence number, we can the "just restored" one remove from the map, because it can never come from client again.

      Open question: the previous statement is true except the double submit problem: JAVASERVERFACES_SPEC_PUBLIC-559. In this case, server can process same request (with the same sequence number) twice.

      1. MYFACES-3117-1.patch
        121 kB
        Leonardo Uribe
      2. MYFACES-3117.patch
        2 kB
        Martin Kočí

        Issue Links

        There are no Sub-Tasks for this issue.

          Activity

          Leonardo Uribe made changes -
          Link This issue is duplicated by MYFACES-1847 [ MYFACES-1847 ]
          Leonardo Uribe made changes -
          Status Resolved [ 5 ] Closed [ 6 ]
          Leonardo Uribe made changes -
          Link This issue is related to MYFACES-1753 [ MYFACES-1753 ]
          Leonardo Uribe made changes -
          Link This issue is duplicated by MYFACES-1791 [ MYFACES-1791 ]
          Leonardo Uribe made changes -
          Status In Progress [ 3 ] Resolved [ 5 ]
          Fix Version/s 2.0.6 [ 12316397 ]
          Fix Version/s 2.1.0 [ 12315190 ]
          Resolution Fixed [ 1 ]
          Show
          Leonardo Uribe added a comment - See the discussion here: http://markmail.org/message/7yrh7267lr5jauua?q=[core]+Enhancements+to+State+Saving+Caching+Algorithm
          Leonardo Uribe made changes -
          Attachment MYFACES-3117-1.patch [ 12479200 ]
          Leonardo Uribe made changes -
          Status Open [ 1 ] In Progress [ 3 ]
          Leonardo Uribe made changes -
          Assignee Martin Kočí [ markoc50 ] Leonardo Uribe [ lu4242 ]
          Martin Kočí made changes -
          Assignee Martin Kočí [ markoc50 ]
          Hide
          Martin Kočí added a comment -

          > double submit: when server processes two or more requests from same client (one DOM instance) to same URL (same view in case of JSF):
          <h:form>
          <h:commandButton actionListener="#

          {invokeLongRunningThread}

          " />
          <h:form>
          <h:commandButton actionListener="#

          {invokeSomething}

          " />
          </h:form>

          in this case, second button creates another request/response to the same view, which is currently processing LongRunningThread

          Robert, do you have all requests AJAXied? If so you can ignore double submit problem, because ajax has own queue.

          Anyway this problem is critical for me too (blocks a product delivery) - I'll look at it asap.

          Show
          Martin Kočí added a comment - > double submit: when server processes two or more requests from same client (one DOM instance) to same URL (same view in case of JSF): <h:form> <h:commandButton actionListener="# {invokeLongRunningThread} " /> <h:form> <h:commandButton actionListener="# {invokeSomething} " /> </h:form> in this case, second button creates another request/response to the same view, which is currently processing LongRunningThread Robert, do you have all requests AJAXied? If so you can ignore double submit problem, because ajax has own queue. Anyway this problem is critical for me too (blocks a product delivery) - I'll look at it asap.
          Hide
          Robert M. Gary added a comment -

          Sorry for a dumb question; but what is the "double submit" problem. Does it refer to a connection retry in which the server actually receives both requests? I'm seeing the defect mentioned here. I use RichFaces for Ajax and use a4j:poll. The polling window quickly uses up the default 20 saved views on the server and then any other open windows immediately get View Expired. Unfortunately some of my view data is large so I"m avoiding using client side.

          Show
          Robert M. Gary added a comment - Sorry for a dumb question; but what is the "double submit" problem. Does it refer to a connection retry in which the server actually receives both requests? I'm seeing the defect mentioned here. I use RichFaces for Ajax and use a4j:poll. The polling window quickly uses up the default 20 saved views on the server and then any other open windows immediately get View Expired. Unfortunately some of my view data is large so I"m avoiding using client side.
          Hide
          Martin Kočí added a comment -

          Too bad that sychronizer token for JSF is not specified yet (JAVASERVERFACES_SPEC_PUBLIC-559 has my vote). I think that viewSequence used in myfaces codebase is de-facto token and with we can use it for detection if request with same token is processed or not.

          Timeout for saved view: I think that does not solve the problem: user can wait between requests seconds or hours, timeout makes behaviour of app undeterministic.

          A new param org.apache.myfaces.REMOVE_RESTORED_VIEW_STATE with default false can solve this problem for now. Applications where double submit problem is solved (for example with Seam UIToken or with AJAX-only requests - ajax has own queue) can set this param to true without side effects.

          Show
          Martin Kočí added a comment - Too bad that sychronizer token for JSF is not specified yet (JAVASERVERFACES_SPEC_PUBLIC-559 has my vote). I think that viewSequence used in myfaces codebase is de-facto token and with we can use it for detection if request with same token is processed or not. Timeout for saved view: I think that does not solve the problem: user can wait between requests seconds or hours, timeout makes behaviour of app undeterministic. A new param org.apache.myfaces.REMOVE_RESTORED_VIEW_STATE with default false can solve this problem for now. Applications where double submit problem is solved (for example with Seam UIToken or with AJAX-only requests - ajax has own queue) can set this param to true without side effects.
          Hide
          Jakob Korherr added a comment -

          Another idea: we could provide a way to not limit the serialized view states in the session per quantity (currently 20), but per timeout (e.g. 10 minutes). This would most certainly also solve the problem, right?

          Show
          Jakob Korherr added a comment - Another idea: we could provide a way to not limit the serialized view states in the session per quantity (currently 20), but per timeout (e.g. 10 minutes). This would most certainly also solve the problem, right?
          Hide
          Jakob Korherr added a comment -

          You're right, that's a very big problem. However, only if you use server-side state-saving.

          The first idea which popped into my mind was using a window-id (which we also requested for JSF 2.2, see [1]).

          Your proposal seems even better to me, but we can't commit it directly in the way you are proposing since we should support the double submit scenarios too. Maybe we could remove it after the next but one view has been restored, meaning that you have three view states 1, 2, 3 and you remove 1 after you restored 3. Just an idea...

          However, if we commit something that may cause any side effects from the current (== old) behavior (e.g. no double submit possible), we have to make it configurable. Otherwise the chance is high that we break a lot of existing applications...

          [1] http://java.net/jira/browse/JAVASERVERFACES_SPEC_PUBLIC-949

          Show
          Jakob Korherr added a comment - You're right, that's a very big problem. However, only if you use server-side state-saving. The first idea which popped into my mind was using a window-id (which we also requested for JSF 2.2, see [1] ). Your proposal seems even better to me, but we can't commit it directly in the way you are proposing since we should support the double submit scenarios too. Maybe we could remove it after the next but one view has been restored, meaning that you have three view states 1, 2, 3 and you remove 1 after you restored 3. Just an idea... However, if we commit something that may cause any side effects from the current (== old) behavior (e.g. no double submit possible), we have to make it configurable. Otherwise the chance is high that we break a lot of existing applications... [1] http://java.net/jira/browse/JAVASERVERFACES_SPEC_PUBLIC-949
          Martin Kočí made changes -
          Attachment MYFACES-3117.patch [ 12477432 ]
          Hide
          Martin Kočí added a comment -

          suggested solution attached; not a final patch, because current codebase contains two same classes SerializedViewCollection:
          one in JspStateManagerImpl and one in DefaultFaceletsStateManagementHelper - refactor first?

          But anyway: review this problem ASAP please, because this is a real blocker for enterprise apps with more than one widnow!

          Show
          Martin Kočí added a comment - suggested solution attached; not a final patch, because current codebase contains two same classes SerializedViewCollection: one in JspStateManagerImpl and one in DefaultFaceletsStateManagementHelper - refactor first? But anyway: review this problem ASAP please, because this is a real blocker for enterprise apps with more than one widnow!
          Martin Kočí made changes -
          Field Original Value New Value
          Link This issue incorporates MYFACES-3100 [ MYFACES-3100 ]
          Martin Kočí created issue -

            People

            • Assignee:
              Leonardo Uribe
              Reporter:
              Martin Kočí
            • Votes:
              1 Vote for this issue
              Watchers:
              1 Start watching this issue

              Dates

              • Created:
                Updated:
                Resolved:

                Development