<f:ajax> execute="@this" and render="@this" does not behave as expected when nested in composite component
Given:
<cc:interface ...>
...
<cc:clientBehavior name="change" default="true" targets="hour minute" event="change" />
</cc:interface>
<cc:implementation>
...
<h:selectOneMenu id="hour" />
<h:selectOneMenu id="minute" />
...
</cc:implementation>
When:
<my:inputLocalTime>
<f:ajax execute="@this" />
</my:inputLocalTime>
Then the expectation is that the "entire" <my:inputLocalTime> is executed (at least the components covered in targets attribute of the associated <cc:clientBehavior>). The current unintuitive behavior is that it's only executing the individual <h:selectOneMenu> component on which the event is triggered.
The same problem applies to render attribute.
When:
<my:inputLocalTime>
<f:ajax render="@this" />
</my:inputLocalTime>
Then the expectation is that the entire <my:inputLocalTime> is rendered. The current unintuitive behavior is that it's only rendering the invididual <h:selectOneMenu> component on which the event is triggered.
@tandraschko: is this updated spec for you also sufficient to fix this issue in MyFaces side? https://github.com/eclipse-ee4j/mojarra/commit/bc2d918345dde59aa7406df84a9f46191328d2d4
@BalusC which reported MF issue do you mean?
The current one.
yep, i think @this should reference to the parent CC in this case.
But im not sure how its currently implemented in both Mojarra and MyFaces?
The unexpected behavior is described in issue description. In Mojarra, it's because the f:ajax is basically re-attached to the individual components. So the @this is simply evaluated in their context.
i think its the same for MyFaces Not sure how easy it is to change this behavior; do you already work on a PR for Mojarra?
NVM: pressed f5 ;D i willl check it for MyFaces
F5 again, initial impl did not exactly work as intended ;)
PR created. All local tests passed (although it's missing a good bunch of f:ajax tests since migration ..)
I've backported impl improvements to Mojarra 2.3 nonetheless. All f:ajax tests over there now pass.
Merged in 3.0 as well.
@BalusC
i currently check this in MF and it seems that AjaxBehavior#setExecute is already called with the remapped clientId (button) insteadof @this
so we have to manipulate the execute string/list in the AjaxBehavior
is there any reason you didnt try to make this "remapping" earlier, so AjaxBehavior#setExecute is already called with the CC clientId?
Also i wonder if we can implement this a bit different, so that even p:ajax might work automatically?
No idea. Logic was already like this and I didn't want to break backwards compatibility. If I were to guess I think it's to ensure that any EL in execute/render attribute is evaluated at right moment.
@BalusC I'm throwing this out there as I'm seeing some behavior changes in mojarra going form 2.3.14 to 2.3.17 which seem to be related to this change. What I'm seeing is in the below where <oc:wizardSection> is a compositeComponent with no <cc:clientBehavior defined. It really is just a layout container.
What happens is when the h:selectOneMenu is changed and the f:ajax triggers it is executing all of the input fields in the <oc:wizardSection rather than just the <h:selectOneMenu This obviously can cause an issue when other fields which may be required=true are not yet set.
<oc:wizardSection section="#{emergencyAddressUpdateView.inputSection}" label="Address Input">
<o:decorateInput label="Calling Name">
<h:inputText id="name" required="true" value="#{emergencyAddressUpdateView.callingName}" p:autocomplete="new-name" maxlength="32" />
<p class="form-text">Name sent to Emergency Services. Could be an individual or business name. This is seperate from Caller-Id</p>
</o:decorateInput>
<o:decorateInput label="Suggestions">
<h:selectOneMenu id="suggestions" value="#{emergencyAddressUpdateView.selectedServiceAddress}" styleClass="form-control" converter="ServiceAddressConverter">
<f:selectItem itemLabel="Choose" />
<f:selectItems value="#{emergencyAddressUpdateView.serviceAddresses}" />
<f:ajax execute="@this" render="@form" listener="#{emergencyAddressUpdateView.applyServiceAddress()}" />
</h:selectOneMenu>
</o:decorateInput>
</oc:wizardSection>
oc:wizardSection is a composite component o:decorateInput is a custom component (not composite)
This did not occur in 2.3.14, but I'm not sure yet if this is the intent. My reading of this issue and the spec would lead me to believe the @this should only apply if it is a direct child of the composite like
<my:inputLocalTime>
<f:ajax execute="@this" />
</my:inputLocalTime>
But probably shouldn't execute all inputs if it was like
<my:inputLocalTime>
<h:inputText>
<f:ajax execute="@this" />
</<h:inputText>
</my:inputLocalTime>
If any <f:ajax execute="@this" /> contained within a composite (including it's inserted children as is the case here causes all inputs contained within the composite to be executed then composites can't really be used as layout containers.
But probably shouldn't execute all inputs if it was like
You're right. I'll have to take a second look at this.
Reproduced. The spec was correct, it's actually a bug in Mojarra impl and happens only when a composite is doubly-nested.
Unsure why this has 4.1 tag/milestone. It's added in 4.0. See updated execute and render attributes of f:ajax: https://jakarta.ee/specifications/faces/4.0/vdldoc/f/ajax.html
I should probably not have reopened this.