You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@wicket.apache.org by Yoann Rodière <yo...@openwide.fr> on 2015/11/30 17:03:47 UTC

Detecting which (nested) form was submitted through AjaxFormSubmitBehavior

Hi all,

My team is in the process of converting one of our projects to Wicket 7 
(7.1.0, exactly). Unfortunately, we think we're having a blocking issue, 
due to the fact that Form.wantSubmitOnNestedFormSubmit() turned 
protected. It seems that with this method gone from the public API, 
there is now no way of knowing which form was submitted in a given 
(ajax) request.

Here follows the detailed explanation of the problem, and below several 
potential fixes. Any comment would be greatly appreciated.

First, our use case : we've got a listener on our Ajax calls that adds 
some CSS on components whenever a FormComponent inside them has been 
submitted and was deemed invalid. For several reasons, when doing this, 
we need to refresh the Form that was effectively submitted.

That's were we've got a problem... It seems that AjaxFormSubmitBehavior, 
when submitting a *nested* form, will not mark the nested form as 
submitted, but the *root* form :

     @Override
     protected void onEvent(final AjaxRequestTarget target)
     {
         getForm()*.getRootForm()*.onFormSubmitted(new 
AjaxFormSubmitter(this, target));
     }

Please note the use of Form.getRootForm(), which puts us in trouble. It 
means that some metadata will be set on the root form and any nested 
form, resulting in Form.isSubmitted() returning true for any form. 
Hence, unless I missed something, no public API in Wicket allows us to 
know which form was submitted anymore.

I say "anymore", because we previously used the same workaround as in 
Form.findFormToProcess :

     private Form<?> findFormToProcess(IFormSubmitter submitter)
     {
                 // [... some code, irrelevant in our case ...]

                 final Form<?> targetedForm = submitter.getForm();

                 // [... some code, irrelevant in our case ...]

                 Form<?> formThatWantsToBeSubmitted = targetedForm;
                 Form<?> current = targetedForm.findParent(Form.class);
                 while (current != null)
                 {
                     if (current.*wantSubmitOnNestedFormSubmit()*)
                     {
                         formThatWantsToBeSubmitted = current;
                     }
                     current = current.findParent(Form.class);
                 }
                 return formThatWantsToBeSubmitted;
     }

Since it is a private method, we had to copy/paste the code. But we 
can't even do that anymore, because Form.wantSubmitOnNestedFormSubmit() 
is now protected.

It seems to me that, in order to fix this issue, we've got several options :

 1. Make Form.wantSubmitOnNestedFormSubmit() public again, so we can at
    least reproduce the findFormToProcess() method in an application.
 2. Make Form.findFormToProcess() public, so that we can use it directly
    in an application.
 3. Make AjaxFormSubmitBehavior.onEvent() call Form.onFormSubmitted on
    the form that was actually submitted, and not the root form, so that
    we can simply use Form.isSubmitted() in an application.


Regards,

-- 
Yoann Rodière<yo...@openwide.fr>
Pôle Développement Spécifique Java
Open Wide - Systèmes d'Information
Tél. : +33 6 21 36 48 35


Re: Detecting which (nested) form was submitted through AjaxFormSubmitBehavior

Posted by andrea del bene <an...@gmail.com>.
you're welcome!

Andrea.

On 30/11/2015 17:57, Yoann Rodière wrote:
> Sorry for the lack of research before posting to the mailing list! 


Re: Detecting which (nested) form was submitted through AjaxFormSubmitBehavior

Posted by Yoann Rodière <yo...@openwide.fr>.
Sven, Andrea,

Thanks for your answers. I added my input to WICKET-6041.

I will do as suggested by Sven for the time being, it should work just 
fine (plus or minus some tweaks to reset the FormValidator after a request).

Sorry for the lack of research before posting to the mailing list!

Regards,
Yoann

Le 30/11/2015 17:32, Sven Meier a écrit :
> Hi,
>
> > It seems that AjaxFormSubmitBehavior, when submitting a
> > *nested* form, will not mark the nested form as submitted,
> > but the *root* form
>
> because the whole form *is* submitted (currently). But only the nested 
> form is processed.
>
> Just an idea:
>
> You can add an IFormValidator to all your forms (through an 
> IComponentInstantiationListener).
> If its #validate() method is invoked, you know that its owning form 
> was processed.
>
> Regards
> Sven
>
> On 30.11.2015 17:11, andrea del bene wrote:
>> Hi Yoann,
>>
>> there is actually an ongoing discussion about this problem:
>> https://issues.apache.org/jira/browse/WICKET-6041 Feel free to dive into
>> it and express your opinion.
>>
>> Andrea.
>>> Hi all,
>>>
>>> My team is in the process of converting one of our projects to Wicket
>>> 7 (7.1.0, exactly). Unfortunately, we think we're having a blocking
>>> issue, due to the fact that Form.wantSubmitOnNestedFormSubmit() turned
>>> protected. It seems that with this method gone from the public API,
>>> there is now no way of knowing which form was submitted in a given
>>> (ajax) request.
>>>
>>> Here follows the detailed explanation of the problem, and below
>>> several potential fixes. Any comment would be greatly appreciated.
>>>
>>> First, our use case : we've got a listener on our Ajax calls that adds
>>> some CSS on components whenever a FormComponent inside them has been
>>> submitted and was deemed invalid. For several reasons, when doing
>>> this, we need to refresh the Form that was effectively submitted.
>>>
>>> That's were we've got a problem... It seems that
>>> AjaxFormSubmitBehavior, when submitting a *nested* form, will not mark
>>> the nested form as submitted, but the *root* form :
>>>
>>>     @Override
>>>     protected void onEvent(final AjaxRequestTarget target)
>>>     {
>>>         getForm()*.getRootForm()*.onFormSubmitted(new
>>> AjaxFormSubmitter(this, target));
>>>     }
>>>
>>> Please note the use of Form.getRootForm(), which puts us in trouble.
>>> It means that some metadata will be set on the root form and any
>>> nested form, resulting in Form.isSubmitted() returning true for any
>>> form. Hence, unless I missed something, no public API in Wicket allows
>>> us to know which form was submitted anymore.
>>>
>>> I say "anymore", because we previously used the same workaround as in
>>> Form.findFormToProcess :
>>>
>>>     private Form<?> findFormToProcess(IFormSubmitter submitter)
>>>     {
>>>                 // [... some code, irrelevant in our case ...]
>>>
>>>                 final Form<?> targetedForm = submitter.getForm();
>>>
>>>                 // [... some code, irrelevant in our case ...]
>>>
>>>                 Form<?> formThatWantsToBeSubmitted = targetedForm;
>>>                 Form<?> current = targetedForm.findParent(Form.class);
>>>                 while (current != null)
>>>                 {
>>>                     if (current.*wantSubmitOnNestedFormSubmit()*)
>>>                     {
>>>                         formThatWantsToBeSubmitted = current;
>>>                     }
>>>                     current = current.findParent(Form.class);
>>>                 }
>>>                 return formThatWantsToBeSubmitted;
>>>     }
>>>
>>> Since it is a private method, we had to copy/paste the code. But we
>>> can't even do that anymore, because
>>> Form.wantSubmitOnNestedFormSubmit() is now protected.
>>>
>>> It seems to me that, in order to fix this issue, we've got several
>>> options :
>>>
>>> 1. Make Form.wantSubmitOnNestedFormSubmit() public again, so we can at
>>>    least reproduce the findFormToProcess() method in an application.
>>> 2. Make Form.findFormToProcess() public, so that we can use it directly
>>>    in an application.
>>> 3. Make AjaxFormSubmitBehavior.onEvent() call Form.onFormSubmitted on
>>>    the form that was actually submitted, and not the root form, so that
>>>    we can simply use Form.isSubmitted() in an application.
>>>
>>>
>>> Regards,
>>>


Re: Detecting which (nested) form was submitted through AjaxFormSubmitBehavior

Posted by Sven Meier <sv...@meiers.net>.
Hi,

 > It seems that AjaxFormSubmitBehavior, when submitting a
 > *nested* form, will not mark the nested form as submitted,
 > but the *root* form

because the whole form *is* submitted (currently). But only the nested 
form is processed.

Just an idea:

You can add an IFormValidator to all your forms (through an 
IComponentInstantiationListener).
If its #validate() method is invoked, you know that its owning form was 
processed.

Regards
Sven

On 30.11.2015 17:11, andrea del bene wrote:
> Hi Yoann,
>
> there is actually an ongoing discussion about this problem:
> https://issues.apache.org/jira/browse/WICKET-6041 Feel free to dive into
> it and express your opinion.
>
> Andrea.
>> Hi all,
>>
>> My team is in the process of converting one of our projects to Wicket
>> 7 (7.1.0, exactly). Unfortunately, we think we're having a blocking
>> issue, due to the fact that Form.wantSubmitOnNestedFormSubmit() turned
>> protected. It seems that with this method gone from the public API,
>> there is now no way of knowing which form was submitted in a given
>> (ajax) request.
>>
>> Here follows the detailed explanation of the problem, and below
>> several potential fixes. Any comment would be greatly appreciated.
>>
>> First, our use case : we've got a listener on our Ajax calls that adds
>> some CSS on components whenever a FormComponent inside them has been
>> submitted and was deemed invalid. For several reasons, when doing
>> this, we need to refresh the Form that was effectively submitted.
>>
>> That's were we've got a problem... It seems that
>> AjaxFormSubmitBehavior, when submitting a *nested* form, will not mark
>> the nested form as submitted, but the *root* form :
>>
>>     @Override
>>     protected void onEvent(final AjaxRequestTarget target)
>>     {
>>         getForm()*.getRootForm()*.onFormSubmitted(new
>> AjaxFormSubmitter(this, target));
>>     }
>>
>> Please note the use of Form.getRootForm(), which puts us in trouble.
>> It means that some metadata will be set on the root form and any
>> nested form, resulting in Form.isSubmitted() returning true for any
>> form. Hence, unless I missed something, no public API in Wicket allows
>> us to know which form was submitted anymore.
>>
>> I say "anymore", because we previously used the same workaround as in
>> Form.findFormToProcess :
>>
>>     private Form<?> findFormToProcess(IFormSubmitter submitter)
>>     {
>>                 // [... some code, irrelevant in our case ...]
>>
>>                 final Form<?> targetedForm = submitter.getForm();
>>
>>                 // [... some code, irrelevant in our case ...]
>>
>>                 Form<?> formThatWantsToBeSubmitted = targetedForm;
>>                 Form<?> current = targetedForm.findParent(Form.class);
>>                 while (current != null)
>>                 {
>>                     if (current.*wantSubmitOnNestedFormSubmit()*)
>>                     {
>>                         formThatWantsToBeSubmitted = current;
>>                     }
>>                     current = current.findParent(Form.class);
>>                 }
>>                 return formThatWantsToBeSubmitted;
>>     }
>>
>> Since it is a private method, we had to copy/paste the code. But we
>> can't even do that anymore, because
>> Form.wantSubmitOnNestedFormSubmit() is now protected.
>>
>> It seems to me that, in order to fix this issue, we've got several
>> options :
>>
>> 1. Make Form.wantSubmitOnNestedFormSubmit() public again, so we can at
>>    least reproduce the findFormToProcess() method in an application.
>> 2. Make Form.findFormToProcess() public, so that we can use it directly
>>    in an application.
>> 3. Make AjaxFormSubmitBehavior.onEvent() call Form.onFormSubmitted on
>>    the form that was actually submitted, and not the root form, so that
>>    we can simply use Form.isSubmitted() in an application.
>>
>>
>> Regards,
>>
>

Re: Detecting which (nested) form was submitted through AjaxFormSubmitBehavior

Posted by andrea del bene <an...@gmail.com>.
Hi Yoann,

there is actually an ongoing discussion about this problem: 
https://issues.apache.org/jira/browse/WICKET-6041 Feel free to dive into 
it and express your opinion.

Andrea.
> Hi all,
>
> My team is in the process of converting one of our projects to Wicket 
> 7 (7.1.0, exactly). Unfortunately, we think we're having a blocking 
> issue, due to the fact that Form.wantSubmitOnNestedFormSubmit() turned 
> protected. It seems that with this method gone from the public API, 
> there is now no way of knowing which form was submitted in a given 
> (ajax) request.
>
> Here follows the detailed explanation of the problem, and below 
> several potential fixes. Any comment would be greatly appreciated.
>
> First, our use case : we've got a listener on our Ajax calls that adds 
> some CSS on components whenever a FormComponent inside them has been 
> submitted and was deemed invalid. For several reasons, when doing 
> this, we need to refresh the Form that was effectively submitted.
>
> That's were we've got a problem... It seems that 
> AjaxFormSubmitBehavior, when submitting a *nested* form, will not mark 
> the nested form as submitted, but the *root* form :
>
>     @Override
>     protected void onEvent(final AjaxRequestTarget target)
>     {
>         getForm()*.getRootForm()*.onFormSubmitted(new 
> AjaxFormSubmitter(this, target));
>     }
>
> Please note the use of Form.getRootForm(), which puts us in trouble. 
> It means that some metadata will be set on the root form and any 
> nested form, resulting in Form.isSubmitted() returning true for any 
> form. Hence, unless I missed something, no public API in Wicket allows 
> us to know which form was submitted anymore.
>
> I say "anymore", because we previously used the same workaround as in 
> Form.findFormToProcess :
>
>     private Form<?> findFormToProcess(IFormSubmitter submitter)
>     {
>                 // [... some code, irrelevant in our case ...]
>
>                 final Form<?> targetedForm = submitter.getForm();
>
>                 // [... some code, irrelevant in our case ...]
>
>                 Form<?> formThatWantsToBeSubmitted = targetedForm;
>                 Form<?> current = targetedForm.findParent(Form.class);
>                 while (current != null)
>                 {
>                     if (current.*wantSubmitOnNestedFormSubmit()*)
>                     {
>                         formThatWantsToBeSubmitted = current;
>                     }
>                     current = current.findParent(Form.class);
>                 }
>                 return formThatWantsToBeSubmitted;
>     }
>
> Since it is a private method, we had to copy/paste the code. But we 
> can't even do that anymore, because 
> Form.wantSubmitOnNestedFormSubmit() is now protected.
>
> It seems to me that, in order to fix this issue, we've got several 
> options :
>
> 1. Make Form.wantSubmitOnNestedFormSubmit() public again, so we can at
>    least reproduce the findFormToProcess() method in an application.
> 2. Make Form.findFormToProcess() public, so that we can use it directly
>    in an application.
> 3. Make AjaxFormSubmitBehavior.onEvent() call Form.onFormSubmitted on
>    the form that was actually submitted, and not the root form, so that
>    we can simply use Form.isSubmitted() in an application.
>
>
> Regards,
>