[ 
https://issues.apache.org/jira/browse/WICKET-1451?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=12659196#action_12659196
 ] 

Marat Radchenko commented on WICKET-1451:
-----------------------------------------

We also hit this bug with wicket-1.4-rc1.

> BaseWicketTester's simulated AJAX form submissions don't include Radio values
> -----------------------------------------------------------------------------
>
>                 Key: WICKET-1451
>                 URL: https://issues.apache.org/jira/browse/WICKET-1451
>             Project: Wicket
>          Issue Type: Bug
>            Reporter: David Shepherdson
>            Assignee: Frank Bille Jensen
>            Priority: Minor
>
> When submitting a form by AJAX, the BaseWicketTester goes through all the 
> form components to make sure their values are stored in the request. However, 
> because Radios are not instances of FormComponent, and because the code skips 
> RadioGroups, the values for radio buttons are not stored in the request. This 
> is particularly a problem if the form contains radio buttons marked as 
> required, because in that case validation will fail and the onSubmit() method 
> will not be called.
> The problem lies in BaseWicketTester.submitAjaxFormSubmitBehavior(). If the 
> visitor in this method were changed so that, instead of skipping RadioGroups, 
> it instead did something like the constructor of FormTester does (see 
> WICKET-1411) to extract the actual value for the group and set that in the 
> request, the problem would be prevented.
> For anyone else affected by this issue, we're working around it by overriding 
> the clickLink(String, boolean) method (since submitAjaxFormSubmitBehavior() 
> is private) in a subclass of WicketTester like this:
>       @Override
>       public void clickLink(String path, boolean isAjax) {
>               // Workaround for bug in BaseWicketTester: doexn't cope with 
> RadioGroups properly.
>               Component linkComponent = 
> getComponentFromLastRenderedPage(path);
>               if (linkComponent instanceof AjaxSubmitLink) {
>                       // Code borrowed from BaseWicketTester.
>                       AjaxSubmitLink link = (AjaxSubmitLink)linkComponent;
>                       // We cycle through the attached behaviors and select 
> the
>                       // LAST matching behavior as the one we handle.
>                       List behaviors = link.getBehaviors();
>                       AjaxFormSubmitBehavior behaviour = null;
>                       for (Iterator iter = behaviors.iterator(); 
> iter.hasNext();)
>                       {
>                               Object behavior = iter.next();
>                               if (behavior instanceof AjaxFormSubmitBehavior)
>                               {
>                                       AjaxFormSubmitBehavior submitBehavior = 
> (AjaxFormSubmitBehavior)behavior;
>                                       behaviour = submitBehavior;
>                               }
>                       }
>                       if (behaviour != null) {
>                               // More code borrowed from BaseWicketTester.
>                               Form form = null;
>                               try {
>                                       Field formField = 
> AjaxFormSubmitBehavior.class.getDeclaredField("form");
>                                       formField.setAccessible(true);
>                                       form = (Form)formField.get(behaviour);
>                               } catch (Exception e) {
>                                       s_log.error("Caught exception in 
> workaround for BaseWicketTester bug.", e);
>                               }
>                               if (form != null) {
>                                       form.visitFormComponents(new 
> FormComponent.AbstractVisitor()
>                                       {
>                                               public void 
> onFormComponent(FormComponent formComponent)
>                                               {
>                                                       if (formComponent 
> instanceof RadioGroup) {
>                                                               final String 
> name = formComponent.getInputName();
>                                                       final String value = 
> formComponent.getValue();
>                                                       Object choiceValue = 
> formComponent.visitChildren(Radio.class, new IVisitor()
>                                                       {
>                                                           public Object 
> component(Component component)
>                                                           {
>                                                               // O-P Preserve 
> old escaping value, then turn escaping off
>                                                               // so that 
> values aren't escaped unnecessarily.
>                                                               
> @SuppressWarnings("hiding")
>                                                               boolean 
> oldEscaping = component.getEscapeModelStrings();
>                                                               
> component.setEscapeModelStrings(false);
>                                                               Radio radio = 
> (Radio)component;
>                                                               String 
> radioValue = radio.getValue();
>                                                               // O-P Restore 
> the previous escaping setting.
>                                                               
> component.setEscapeModelStrings(oldEscaping);
>                                                               if 
> (radio.getModelObject().toString().equals(value))
>                                                               {
>                                                                   return 
> radioValue;
>                                                               }
>                                                               return 
> CONTINUE_TRAVERSAL;
>                                                           }
>                                                       });
>                                                       if (choiceValue != 
> null) {
>                                                               Map 
> requestParams = getParametersForNextRequest();
>                                                               if 
> (requestParams.get(name) == null) {
>                                                                       
> requestParams.put(name, (String) choiceValue);
>                                                               }
>                                                       }
>                                                       }
>                                               }
>                                       });
>                               }
>                       }
>               }
>               super.clickLink(path, isAjax);
>       }

-- 
This message is automatically generated by JIRA.
-
You can reply to this email to add a comment to the issue online.

Reply via email to