Leonardo Uribe created MYFACES-3660:
---------------------------------------

             Summary: Component resource added using @ResourceDependency 
annotation from a facelet component should have an id defined by facelets
                 Key: MYFACES-3660
                 URL: https://issues.apache.org/jira/browse/MYFACES-3660
             Project: MyFaces Core
          Issue Type: Bug
          Components: JSR-314
            Reporter: Leonardo Uribe
            Assignee: Leonardo Uribe


A problem related to @ResourceDependency has been mentioned on:

http://stackoverflow.com/questions/13526624/duplicate-id-error-with-partial-state-saving-and-myfaces-codi

CODI add a component called WindowContextIdHolderComponent in 
ResponseWriter.startDocument(), and later a UIViewRoot.createUniqueId() call is 
done when getClientId() is called from the code that checks for duplicate ids. 

The problem is the code that process @ResourceDependency annotations in 
ApplicationImpl object let UIViewRoot.addComponentResource() internals to call 
createUniqueId(). In the example proposed, there is a dynamic block that 
changes the resources added at an specific moment of time, and since by PSS 
saving algorithm, restore view phase calls buildView() before restore the 
initial state, the count of uniqueIdCounter in UIViewRoot is never restored, 
and there is a chance that the same id of the one assigned to 
WindowContextIdHolderComponent can be set to a component resource added by 
@ResourceDependency effect.

The problem of how generate ids is well known and has been studied for a long 
time. A general solution for facelets was committed in MYFACES-3329, and has 
worked well so far.

In few words, we need to generate predictable component ids to make PSS 
algorithm reliable, otherwise it will be problems related to state saving that 
are very difficult to track down and solve. In the other hand, PSS algorithm 
impose some restrictions over the view that conflicts with dynamic 
manipulations of the component tree.

I think the solution for this one is ensure all components created inside 
facelets vdl.buildView has unique ids, doing some changes over 
UIViewRoot.createUniqueId and changing @ResourceDependency processing in 
ApplicationImpl, so if facelets is processing the current view use 
FaceletCompositionContext.generateUniqueComponentId() to set an Id. Since 
@ResourceDependency depends on the component tree structure, the ids will now 
contains the information related to the tree structure itself (in the generated 
id), preventing duplicates.

In theory, if we can ensure that all components generated by facelets has a 
component id defined by facelets algorithm, createUniqueId will be let to 
components added programatically, so we can do some hack to restore the 
uniqueIdCounter for UIViewRoot on restore view phase before call vdl.buildView, 
and simulate the same behavior we had in JSF 1.2, without the side effects over 
the state and performance.

I think solutions using a HashMap using duplicates or random generators are out 
of discussion, because they will not ensure the predictability we need to get 
correct operation of PSS algorithm.

--
This message is automatically generated by JIRA.
If you think it was sent incorrectly, please contact your JIRA administrators
For more information on JIRA, see: http://www.atlassian.com/software/jira

Reply via email to