You are viewing a plain text version of this content. The canonical link for it is here.
Posted to user@struts.apache.org by Burton Rhodes <bu...@gmail.com> on 2017/09/25 03:04:25 UTC

Extending StrutsTypeConverter :: How to detect specific type of "Class toClass"?

When extending the StrutsTypeConverter, is there anyway to figure out if
the "toClass" is a List<Integer> or a List<String>?  I have found that when
converting data from a submitted webpage that has a value of a List in a
single variable, the standard struts conversion fails.  For example:
<s:hidden name="integerList" value="%{integerList}" /> display as <s:hidden
name="integerList" value="[1,2,3,4,5]" />.  When the form submits, this
value will not convert properly back into the List.  In addition, the
conversion fails if you have a list of checkboxes and the user only checks
one -  hence only a single variable being converted to a List.

I have solved this issue by creating a MyListConverter, but I have to
declare the converter on each action in a [-conversion.properties] file
which is now becoming a bit cumbersome since this is such a common
occurrence. I have also declared some on my model/entity beans, but
still.... I would love to have a more global "List" converter, such as:

[xwork-conversion.properties]
java.util.List=com.afs.web.converter.MyListConverter

Thus any List that is encountered, I could attempt "my conversion" and send
up the chain of command if the resulting List is not of List<Integer> or
List<String>.

[Psuedo_Code]
public class MyListConverter extends StrutsTypeConverter {
    public Object convertFromString(Map context, String[] values, Class
toClass) {
        // Is toClass List<Integer>, then try "my" conversion

        // Else is toClass List<String?, then try "my" conversion

        // Else return performFallbackConversion(context, o, toClass);
    }
}

Any ideas?  Or am I going about this incorrectly?

Thanks in advance.

Re: Extending StrutsTypeConverter :: How to detect specific type of "Class toClass"?

Posted by Yasser Zamani <ya...@live.com>.
Hello Burton,

I could post back lists without any custom converter as below:

```jsp
<s:form action="strutsTypeConverterAction" >
     <s:iterator value="integerList" status="stat" var="i">
         <s:hidden value="%{#i}" name="integerList[%{#stat.count}]"/>
     </s:iterator>
     <s:iterator value="stringList" status="stat" var="s">
         <s:hidden value="%{#s}" name="stringList[%{#stat.count}]"/>
     </s:iterator>
     <s:submit/>
</s:form>
```

But about your question:
Java uses something called "type erasure", which means at runtime both 
List<String> and List<Integer> are equivalent. The compiler knows the 
lists contain integers or strings, and as such can maintain a type safe 
environment. This information is lost (on an object instance basis) at 
runtime, and the list only contain 'Objects'.

If the list has a non-zero number of elements, you could investigate the 
type of the first element ( using it's getClass method, for instance ). 
That won't tell you the generic type of the list, but it would be 
reasonable to assume that the generic type was some superclass of the 
types in the list.

I wouldn't advocate the approach, but in a bind it might be useful.

```java
List<Object> listCheck = (List<Object>)(Object) stringList;
     if (!listCheck.isEmpty()) {
        if (listCheck.get(0) instanceof String) {
            System.out.println("List type is String");
        }
        if (listCheck.get(0) instanceof Integer) {
            System.out.println("List type is Integer");
        }
     }
}
```

References:
[1] 
https://stackoverflow.com/questions/1942644/get-generic-type-of-java-util-list

On 9/25/2017 6:34 AM, Burton Rhodes wrote:
> When extending the StrutsTypeConverter, is there anyway to figure out if
> the "toClass" is a List<Integer> or a List<String>?  I have found that when
> converting data from a submitted webpage that has a value of a List in a
> single variable, the standard struts conversion fails.  For example:
> <s:hidden name="integerList" value="%{integerList}" /> display as <s:hidden
> name="integerList" value="[1,2,3,4,5]" />.  When the form submits, this
> value will not convert properly back into the List.  In addition, the
> conversion fails if you have a list of checkboxes and the user only checks
> one -  hence only a single variable being converted to a List.
> 
> I have solved this issue by creating a MyListConverter, but I have to
> declare the converter on each action in a [-conversion.properties] file
> which is now becoming a bit cumbersome since this is such a common
> occurrence. I have also declared some on my model/entity beans, but
> still.... I would love to have a more global "List" converter, such as:
> 
> [xwork-conversion.properties]
> java.util.List=com.afs.web.converter.MyListConverter
> 
> Thus any List that is encountered, I could attempt "my conversion" and send
> up the chain of command if the resulting List is not of List<Integer> or
> List<String>.
> 
> [Psuedo_Code]
> public class MyListConverter extends StrutsTypeConverter {
>      public Object convertFromString(Map context, String[] values, Class
> toClass) {
>          // Is toClass List<Integer>, then try "my" conversion
> 
>          // Else is toClass List<String?, then try "my" conversion
> 
>          // Else return performFallbackConversion(context, o, toClass);
>      }
> }
> 
> Any ideas?  Or am I going about this incorrectly?
> 
> Thanks in advance.
> 

---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
For additional commands, e-mail: user-help@struts.apache.org

Re: Extending StrutsTypeConverter :: How to detect specific type of "Class toClass"?

Posted by Yasser Zamani <ya...@live.com>.
Good time Burton,

Thank you for your code but I think adding a new parameter maybe is not 
a real necessary in this case. If we add it then it crowds check box tag 
out more, confuses users with more options, needs support for a long 
time and needs documentation. Maybe these are not necessary in this case 
IMHO because...

>>> Got it.  I'll use that for now.  Don't you think that is a bit of a hack?
>>> Do you think this be fixed or reported as a "bug"?

What do you think about refactoring List<Integer> to List<Boolean> (i.e. 
to see if choice#k {0<=k<n} is selected or not, just check if 
list.get(k) is true or false)? I'm almost sure if you do, your example 
starts to be working.

Regards,
Yasser.

On 10/1/2017 11:32 PM, Burton Rhodes wrote:
> As a followup to my last email, it appears the Struts default design
> pattern for checkboxes (submitting false values with hidden value) is the
> cause.  An easy fix for this would be to allow the developer to override
> this design pattern by a s:checkbox parameter (e.g. requiredValue).  The
> default would be "true" - which keeps backwards compatibility, but by
> setting to "false", the hidden checkbox value would not be created in the
> document.  It seems like this would be an easy and beneficial addition to
> the Struts community.  I don't think the "submit false checkboxes" design
> pattern is necessary or appropriate at all times.
> 
> Below is the changed code from the overridden checkbox.ftl.  In this
> example, I simply added an <#if> clause around the <input hidden
> __checkbox> element and checked for a new parameter called "requiredValue"
> (dynamicParameter in this example).  Of course the permanent solution would
> be for "requiredValue" to be an actual parameter of the <s:checkbox> tag.
> 
> [checkbox.ftl]
> <!-- Code Snippet -->
> <#if (parameters.dynamicAttributes['requiredValue']!"true")?boolean>
>      <input type="hidden" id="__checkbox_${parameters.id?html}"
> name="__checkbox_${parameters.name?html}"
> value="${parameters.fieldValue?html}"<#rt/>
>      <#if parameters.disabled!false>
>               disabled="disabled"<#rt/>
>      </#if>
>      />
> </#if>
> 
> Thoughts?  Any reason this would cause issues elsewhere?
> 
> On Sun, Oct 1, 2017 at 1:37 PM, Burton Rhodes <bu...@gmail.com>
> wrote:
> 
>> Got it.  I'll use that for now.  Don't you think that is a bit of a hack?
>> Do you think this be fixed or reported as a "bug"?
>>
>> On Sun, Oct 1, 2017 at 7:54 AM, Yasser Zamani <ya...@live.com>
>> wrote:
>>
>>> Hello Burton,
>>>
>>> Thank you; I examined your example and found out this behavior is
>>> because of something in Struts named "automatic checkbox detection",
>>> CheckboxInterceptor.
>>>
>>> When your `choices` count is bigger than 1, you'll see your desired
>>> behavior because CheckboxInterceptor does nothing with following message
>>> where value.isMultiple() is true:
>>>
>>> ```java
>>> if(value.isMultiple()) {
>>>       LOG.debug("Bypassing automatic checkbox detection due to multiple
>>> checkboxes of the same name: {}", name);
>>> } else if(!parameters.contains(checkboxName)) {
>>>       extraParams.put(checkboxName, new Request(checkboxName,
>>> this.uncheckedValue));
>>> }
>>> ```
>>>
>>> But what happens when your `choices` count is one and you don't click on
>>> that one (your current example): Actually W3C says unchecked checkbox
>>> wont be posted, so, the above else will be executed (because
>>> !parameters.contains(checkboxName) is true) and CheckboxInterceptor sets
>>> a new parameter, "itemsFail->false". Then OGNL cannot convert `false` to
>>> an array of Integer into your action, so, the result will be changed to
>>> `input`.
>>>
>>> I searched how to also post unchecked check boxes and found out that
>>> following makes your example working:
>>> ```jsp
>>> <s:iterator var="choice" value="%{choices}">
>>>       <s:hidden value='0' name='itemsFail'/><!-- I added this; a default
>>> -->
>>>       <s:checkbox name="itemsFail" fieldValue="%{choice}"
>>> value="%{isItemsFailSelected(#choice)}"/> <s:property
>>> value="%{#choice}"/>
>>> </s:iterator>
>>> ```
>>>
>>> Hope these help!
>>> Yasser.
>>>
>>> On 10/1/2017 6:57 AM, Burton Rhodes wrote:
>>>> Well shoot - after further testing it seems the issue is still
>>> present.  I
>>>> isolated the issue in a simple mvn webapp (see link below).  Essentially
>>>> Struts conversion fails when: 1) setting form input element to a
>>>> List<Integer>, 2) there is only one checkbox in the list, 3) the
>>> checkbox
>>>> is not checked when the form is submitted.  The situation arises for me
>>>> when I need to display a list of checkboxes, but I can't use
>>>> <s:checkboxlist/> tag because the page requires a more advanced html
>>>> layout.  Thus I am forced to display the checkbox list using an
>>>> <s:iterator/> and the <s:checkbox/> tag.  If the displayed list so
>>> happens
>>>> to have only one element, and the user doesn't check it, the conversion
>>>> fails.
>>>>
>>>> I am using now Struts Version 2.5.13.
>>>>
>>>> *Test Struts Webb App*
>>>> *Download*: https://www.dropbox.com/s/x27o9a8qky9nwta/listTest.zip?dl=0
>>>> *Action*: mvn jetty:run
>>>> *Url*: http://localhost:8080/ListConverterTest.action
>>>>
>>>> On Fri, Sep 29, 2017 at 10:56 AM, Burton Rhodes <burtonrhodes@gmail.com
>>>>
>>>> wrote:
>>>>
>>>>> Sorry for the delay.  I have upgraded to the newest version and
>>> everything
>>>>> seems to be working.  Thanks!
>>>>>
>>>>> On Mon, Sep 25, 2017 at 2:34 AM, Lukasz Lenart <
>>> lukaszlenart@apache.org>
>>>>> wrote:
>>>>>
>>>>>> 2017-09-25 5:04 GMT+02:00 Burton Rhodes <bu...@gmail.com>:
>>>>>>> When extending the StrutsTypeConverter, is there anyway to figure
>>> out if
>>>>>>> the "toClass" is a List<Integer> or a List<String>?  I have found
>>> that
>>>>>> when
>>>>>>> converting data from a submitted webpage that has a value of a List
>>> in a
>>>>>>> single variable, the standard struts conversion fails.  For example:
>>>>>>> <s:hidden name="integerList" value="%{integerList}" /> display as
>>>>>> <s:hidden
>>>>>>> name="integerList" value="[1,2,3,4,5]" />.  When the form submits,
>>> this
>>>>>>> value will not convert properly back into the List.  In addition, the
>>>>>>> conversion fails if you have a list of checkboxes and the user only
>>>>>> checks
>>>>>>> one -  hence only a single variable being converted to a List.
>>>>>>>
>>>>>>> I have solved this issue by creating a MyListConverter, but I have to
>>>>>>> declare the converter on each action in a [-conversion.properties]
>>> file
>>>>>>> which is now becoming a bit cumbersome since this is such a common
>>>>>>> occurrence. I have also declared some on my model/entity beans, but
>>>>>>> still.... I would love to have a more global "List" converter, such
>>> as:
>>>>>>>
>>>>>>> [xwork-conversion.properties]
>>>>>>> java.util.List=com.afs.web.converter.MyListConverter
>>>>>>>
>>>>>>> Thus any List that is encountered, I could attempt "my conversion"
>>> and
>>>>>> send
>>>>>>> up the chain of command if the resulting List is not of
>>> List<Integer> or
>>>>>>> List<String>.
>>>>>>>
>>>>>>> [Psuedo_Code]
>>>>>>> public class MyListConverter extends StrutsTypeConverter {
>>>>>>>       public Object convertFromString(Map context, String[] values,
>>> Class
>>>>>>> toClass) {
>>>>>>>           // Is toClass List<Integer>, then try "my" conversion
>>>>>>>
>>>>>>>           // Else is toClass List<String?, then try "my" conversion
>>>>>>>
>>>>>>>           // Else return performFallbackConversion(context, o,
>>> toClass);
>>>>>>>       }
>>>>>>> }
>>>>>>>
>>>>>>> Any ideas?  Or am I going about this incorrectly?
>>>>>>
>>>>>> What version of Struts do you use? I think this was resolved in 2.5.13
>>>>>> or 2.5.12 - I meant conversion of list of built-in types (ints,
>>>>>> doubles, etc), to convert your own type just register it (as for the
>>>>>> List above).
>>>>>>
>>>>>>
>>>>>> Regards
>>>>>> --
>>>>>> Łukasz
>>>>>> + 48 606 323 122 <+48%20606%20323%20122> http://www.lenart.org.pl/
>>>>>>
>>>>>> ---------------------------------------------------------------------
>>>>>> To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
>>>>>> For additional commands, e-mail: user-help@struts.apache.org
>>>>>>
>>>>>>
>>>>>
>>>>
>>>
>>
>>
> 

Re: Extending StrutsTypeConverter :: How to detect specific type of "Class toClass"?

Posted by Lukasz Lenart <lu...@apache.org>.
2017-10-02 17:45 GMT+02:00 Burton Rhodes <bu...@gmail.com>:
> Lukasz -
> I've created a fix in my fork of the struts project on GitHub.  Should I
> still create the JIRA or just submit a pull request?  Not sure about
> protocol here.

Yes, please create the JIRA ticket and then reference it from the PR.
This help us manage a release process :)


Kind regards
-- 
Łukasz
+ 48 606 323 122 http://www.lenart.org.pl/

---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
For additional commands, e-mail: user-help@struts.apache.org


Re: Extending StrutsTypeConverter :: How to detect specific type of "Class toClass"?

Posted by Burton Rhodes <bu...@gmail.com>.
Lukasz -
I've created a fix in my fork of the struts project on GitHub.  Should I
still create the JIRA or just submit a pull request?  Not sure about
protocol here.
Thanks,
Burton

On Mon, Oct 2, 2017 at 5:11 AM, Burton Rhodes <bu...@gmail.com>
wrote:

> Lukasz - yes.  The checkbox.ftl was overridden using the technique you
> linked to.  For my case, I just performed the "simple" theme modification.
> However, after looking at the other checkbox.ftl files - it appears they
> just include the /simple/checkbox.ftl file - so the code change is only
> required in one place.  I will file a JIRA.
>
> Thanks to you both for your help.
>
> On Mon, Oct 2, 2017 at 3:20 AM, Yasser Zamani <ya...@live.com>
> wrote:
>
>>
>>
>> On 10/2/2017 11:00 AM, Lukasz Lenart wrote:
>> > was off for few days to take few
>> > off-road rides on my dirty bike;-)
>>
>> :) cool! I hope you did not reach any issue with your bike's Struts :)
>>
>> Just joking! welcome back Łukasz! Actually such days traverses hardly
>> for me as I do not hear about you and Struts and cannot do any more with
>> it ;) Of course, any one like you, need it; I hope you will have a lot
>> of fun in your off days :)
>>
>> Thanks for your community,
>> Yasser.
>>
>> ---------------------------------------------------------------------
>> To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
>> For additional commands, e-mail: user-help@struts.apache.org
>>
>
>

Re: Extending StrutsTypeConverter :: How to detect specific type of "Class toClass"?

Posted by Burton Rhodes <bu...@gmail.com>.
Lukasz - yes.  The checkbox.ftl was overridden using the technique you
linked to.  For my case, I just performed the "simple" theme modification.
However, after looking at the other checkbox.ftl files - it appears they
just include the /simple/checkbox.ftl file - so the code change is only
required in one place.  I will file a JIRA.

Thanks to you both for your help.

On Mon, Oct 2, 2017 at 3:20 AM, Yasser Zamani <ya...@live.com>
wrote:

>
>
> On 10/2/2017 11:00 AM, Lukasz Lenart wrote:
> > was off for few days to take few
> > off-road rides on my dirty bike;-)
>
> :) cool! I hope you did not reach any issue with your bike's Struts :)
>
> Just joking! welcome back Łukasz! Actually such days traverses hardly
> for me as I do not hear about you and Struts and cannot do any more with
> it ;) Of course, any one like you, need it; I hope you will have a lot
> of fun in your off days :)
>
> Thanks for your community,
> Yasser.
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
> For additional commands, e-mail: user-help@struts.apache.org
>

Re: Extending StrutsTypeConverter :: How to detect specific type of "Class toClass"?

Posted by Lukasz Lenart <lu...@apache.org>.
2017-10-02 10:20 GMT+02:00 Yasser Zamani <ya...@live.com>:
> On 10/2/2017 11:00 AM, Lukasz Lenart wrote:
>> was off for few days to take few
>> off-road rides on my dirty bike;-)
>
> :) cool! I hope you did not reach any issue with your bike's Struts :)
>
> Just joking! welcome back Łukasz! Actually such days traverses hardly
> for me as I do not hear about you and Struts and cannot do any more with
> it ;) Of course, any one like you, need it; I hope you will have a lot
> of fun in your off days :)

Hehe ... nope, everything went smoothly :)


Regards
-- 
Łukasz
+ 48 606 323 122 http://www.lenart.org.pl/

---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
For additional commands, e-mail: user-help@struts.apache.org


Re: Extending StrutsTypeConverter :: How to detect specific type of "Class toClass"?

Posted by Yasser Zamani <ya...@live.com>.

On 10/2/2017 11:00 AM, Lukasz Lenart wrote:
> was off for few days to take few
> off-road rides on my dirty bike;-)  

:) cool! I hope you did not reach any issue with your bike's Struts :)

Just joking! welcome back Łukasz! Actually such days traverses hardly 
for me as I do not hear about you and Struts and cannot do any more with 
it ;) Of course, any one like you, need it; I hope you will have a lot 
of fun in your off days :)

Thanks for your community,
Yasser.

---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
For additional commands, e-mail: user-help@struts.apache.org

Re: Extending StrutsTypeConverter :: How to detect specific type of "Class toClass"?

Posted by Lukasz Lenart <lu...@apache.org>.
2017-10-01 22:02 GMT+02:00 Burton Rhodes <bu...@gmail.com>:
> As a followup to my last email, it appears the Struts default design
> pattern for checkboxes (submitting false values with hidden value) is the
> cause.  An easy fix for this would be to allow the developer to override
> this design pattern by a s:checkbox parameter (e.g. requiredValue).  The
> default would be "true" - which keeps backwards compatibility, but by
> setting to "false", the hidden checkbox value would not be created in the
> document.  It seems like this would be an easy and beneficial addition to
> the Struts community.  I don't think the "submit false checkboxes" design
> pattern is necessary or appropriate at all times.
>
> Below is the changed code from the overridden checkbox.ftl.  In this
> example, I simply added an <#if> clause around the <input hidden
> __checkbox> element and checked for a new parameter called "requiredValue"
> (dynamicParameter in this example).  Of course the permanent solution would
> be for "requiredValue" to be an actual parameter of the <s:checkbox> tag.
>
> [checkbox.ftl]
> <!-- Code Snippet -->
> <#if (parameters.dynamicAttributes['requiredValue']!"true")?boolean>
>     <input type="hidden" id="__checkbox_${parameters.id?html}"
> name="__checkbox_${parameters.name?html}"
> value="${parameters.fieldValue?html}"<#rt/>
>     <#if parameters.disabled!false>
>              disabled="disabled"<#rt/>
>     </#if>
>     />
> </#if>
>
> Thoughts?  Any reason this would cause issues elsewhere?

I didn't follow the whole discussion (was off for few days to take few
off-road rides on my dirty bike ;-) but I like your idea, feel free to
fill a ticket in JIRA and put your comments with your sample code
there.

One more question, you have overridden the checkbox.ftl by using this
[1] technic, right?

[1] https://struts.apache.org/docs/template-loading.html#TemplateLoading-OverridingTemplates


Regards
-- 
Łukasz
+ 48 606 323 122 http://www.lenart.org.pl/

---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
For additional commands, e-mail: user-help@struts.apache.org


Re: Extending StrutsTypeConverter :: How to detect specific type of "Class toClass"?

Posted by Burton Rhodes <bu...@gmail.com>.
As a followup to my last email, it appears the Struts default design
pattern for checkboxes (submitting false values with hidden value) is the
cause.  An easy fix for this would be to allow the developer to override
this design pattern by a s:checkbox parameter (e.g. requiredValue).  The
default would be "true" - which keeps backwards compatibility, but by
setting to "false", the hidden checkbox value would not be created in the
document.  It seems like this would be an easy and beneficial addition to
the Struts community.  I don't think the "submit false checkboxes" design
pattern is necessary or appropriate at all times.

Below is the changed code from the overridden checkbox.ftl.  In this
example, I simply added an <#if> clause around the <input hidden
__checkbox> element and checked for a new parameter called "requiredValue"
(dynamicParameter in this example).  Of course the permanent solution would
be for "requiredValue" to be an actual parameter of the <s:checkbox> tag.

[checkbox.ftl]
<!-- Code Snippet -->
<#if (parameters.dynamicAttributes['requiredValue']!"true")?boolean>
    <input type="hidden" id="__checkbox_${parameters.id?html}"
name="__checkbox_${parameters.name?html}"
value="${parameters.fieldValue?html}"<#rt/>
    <#if parameters.disabled!false>
             disabled="disabled"<#rt/>
    </#if>
    />
</#if>

Thoughts?  Any reason this would cause issues elsewhere?

On Sun, Oct 1, 2017 at 1:37 PM, Burton Rhodes <bu...@gmail.com>
wrote:

> Got it.  I'll use that for now.  Don't you think that is a bit of a hack?
> Do you think this be fixed or reported as a "bug"?
>
> On Sun, Oct 1, 2017 at 7:54 AM, Yasser Zamani <ya...@live.com>
> wrote:
>
>> Hello Burton,
>>
>> Thank you; I examined your example and found out this behavior is
>> because of something in Struts named "automatic checkbox detection",
>> CheckboxInterceptor.
>>
>> When your `choices` count is bigger than 1, you'll see your desired
>> behavior because CheckboxInterceptor does nothing with following message
>> where value.isMultiple() is true:
>>
>> ```java
>> if(value.isMultiple()) {
>>      LOG.debug("Bypassing automatic checkbox detection due to multiple
>> checkboxes of the same name: {}", name);
>> } else if(!parameters.contains(checkboxName)) {
>>      extraParams.put(checkboxName, new Request(checkboxName,
>> this.uncheckedValue));
>> }
>> ```
>>
>> But what happens when your `choices` count is one and you don't click on
>> that one (your current example): Actually W3C says unchecked checkbox
>> wont be posted, so, the above else will be executed (because
>> !parameters.contains(checkboxName) is true) and CheckboxInterceptor sets
>> a new parameter, "itemsFail->false". Then OGNL cannot convert `false` to
>> an array of Integer into your action, so, the result will be changed to
>> `input`.
>>
>> I searched how to also post unchecked check boxes and found out that
>> following makes your example working:
>> ```jsp
>> <s:iterator var="choice" value="%{choices}">
>>      <s:hidden value='0' name='itemsFail'/><!-- I added this; a default
>> -->
>>      <s:checkbox name="itemsFail" fieldValue="%{choice}"
>> value="%{isItemsFailSelected(#choice)}"/> <s:property
>> value="%{#choice}"/>
>> </s:iterator>
>> ```
>>
>> Hope these help!
>> Yasser.
>>
>> On 10/1/2017 6:57 AM, Burton Rhodes wrote:
>> > Well shoot - after further testing it seems the issue is still
>> present.  I
>> > isolated the issue in a simple mvn webapp (see link below).  Essentially
>> > Struts conversion fails when: 1) setting form input element to a
>> > List<Integer>, 2) there is only one checkbox in the list, 3) the
>> checkbox
>> > is not checked when the form is submitted.  The situation arises for me
>> > when I need to display a list of checkboxes, but I can't use
>> > <s:checkboxlist/> tag because the page requires a more advanced html
>> > layout.  Thus I am forced to display the checkbox list using an
>> > <s:iterator/> and the <s:checkbox/> tag.  If the displayed list so
>> happens
>> > to have only one element, and the user doesn't check it, the conversion
>> > fails.
>> >
>> > I am using now Struts Version 2.5.13.
>> >
>> > *Test Struts Webb App*
>> > *Download*: https://www.dropbox.com/s/x27o9a8qky9nwta/listTest.zip?dl=0
>> > *Action*: mvn jetty:run
>> > *Url*: http://localhost:8080/ListConverterTest.action
>> >
>> > On Fri, Sep 29, 2017 at 10:56 AM, Burton Rhodes <burtonrhodes@gmail.com
>> >
>> > wrote:
>> >
>> >> Sorry for the delay.  I have upgraded to the newest version and
>> everything
>> >> seems to be working.  Thanks!
>> >>
>> >> On Mon, Sep 25, 2017 at 2:34 AM, Lukasz Lenart <
>> lukaszlenart@apache.org>
>> >> wrote:
>> >>
>> >>> 2017-09-25 5:04 GMT+02:00 Burton Rhodes <bu...@gmail.com>:
>> >>>> When extending the StrutsTypeConverter, is there anyway to figure
>> out if
>> >>>> the "toClass" is a List<Integer> or a List<String>?  I have found
>> that
>> >>> when
>> >>>> converting data from a submitted webpage that has a value of a List
>> in a
>> >>>> single variable, the standard struts conversion fails.  For example:
>> >>>> <s:hidden name="integerList" value="%{integerList}" /> display as
>> >>> <s:hidden
>> >>>> name="integerList" value="[1,2,3,4,5]" />.  When the form submits,
>> this
>> >>>> value will not convert properly back into the List.  In addition, the
>> >>>> conversion fails if you have a list of checkboxes and the user only
>> >>> checks
>> >>>> one -  hence only a single variable being converted to a List.
>> >>>>
>> >>>> I have solved this issue by creating a MyListConverter, but I have to
>> >>>> declare the converter on each action in a [-conversion.properties]
>> file
>> >>>> which is now becoming a bit cumbersome since this is such a common
>> >>>> occurrence. I have also declared some on my model/entity beans, but
>> >>>> still.... I would love to have a more global "List" converter, such
>> as:
>> >>>>
>> >>>> [xwork-conversion.properties]
>> >>>> java.util.List=com.afs.web.converter.MyListConverter
>> >>>>
>> >>>> Thus any List that is encountered, I could attempt "my conversion"
>> and
>> >>> send
>> >>>> up the chain of command if the resulting List is not of
>> List<Integer> or
>> >>>> List<String>.
>> >>>>
>> >>>> [Psuedo_Code]
>> >>>> public class MyListConverter extends StrutsTypeConverter {
>> >>>>      public Object convertFromString(Map context, String[] values,
>> Class
>> >>>> toClass) {
>> >>>>          // Is toClass List<Integer>, then try "my" conversion
>> >>>>
>> >>>>          // Else is toClass List<String?, then try "my" conversion
>> >>>>
>> >>>>          // Else return performFallbackConversion(context, o,
>> toClass);
>> >>>>      }
>> >>>> }
>> >>>>
>> >>>> Any ideas?  Or am I going about this incorrectly?
>> >>>
>> >>> What version of Struts do you use? I think this was resolved in 2.5.13
>> >>> or 2.5.12 - I meant conversion of list of built-in types (ints,
>> >>> doubles, etc), to convert your own type just register it (as for the
>> >>> List above).
>> >>>
>> >>>
>> >>> Regards
>> >>> --
>> >>> Łukasz
>> >>> + 48 606 323 122 <+48%20606%20323%20122> http://www.lenart.org.pl/
>> >>>
>> >>> ---------------------------------------------------------------------
>> >>> To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
>> >>> For additional commands, e-mail: user-help@struts.apache.org
>> >>>
>> >>>
>> >>
>> >
>>
>
>

Re: Extending StrutsTypeConverter :: How to detect specific type of "Class toClass"?

Posted by Burton Rhodes <bu...@gmail.com>.
Got it.  I'll use that for now.  Don't you think that is a bit of a hack?
Do you think this be fixed or reported as a "bug"?

On Sun, Oct 1, 2017 at 7:54 AM, Yasser Zamani <ya...@live.com>
wrote:

> Hello Burton,
>
> Thank you; I examined your example and found out this behavior is
> because of something in Struts named "automatic checkbox detection",
> CheckboxInterceptor.
>
> When your `choices` count is bigger than 1, you'll see your desired
> behavior because CheckboxInterceptor does nothing with following message
> where value.isMultiple() is true:
>
> ```java
> if(value.isMultiple()) {
>      LOG.debug("Bypassing automatic checkbox detection due to multiple
> checkboxes of the same name: {}", name);
> } else if(!parameters.contains(checkboxName)) {
>      extraParams.put(checkboxName, new Request(checkboxName,
> this.uncheckedValue));
> }
> ```
>
> But what happens when your `choices` count is one and you don't click on
> that one (your current example): Actually W3C says unchecked checkbox
> wont be posted, so, the above else will be executed (because
> !parameters.contains(checkboxName) is true) and CheckboxInterceptor sets
> a new parameter, "itemsFail->false". Then OGNL cannot convert `false` to
> an array of Integer into your action, so, the result will be changed to
> `input`.
>
> I searched how to also post unchecked check boxes and found out that
> following makes your example working:
> ```jsp
> <s:iterator var="choice" value="%{choices}">
>      <s:hidden value='0' name='itemsFail'/><!-- I added this; a default -->
>      <s:checkbox name="itemsFail" fieldValue="%{choice}"
> value="%{isItemsFailSelected(#choice)}"/> <s:property value="%{#choice}"/>
> </s:iterator>
> ```
>
> Hope these help!
> Yasser.
>
> On 10/1/2017 6:57 AM, Burton Rhodes wrote:
> > Well shoot - after further testing it seems the issue is still present.
> I
> > isolated the issue in a simple mvn webapp (see link below).  Essentially
> > Struts conversion fails when: 1) setting form input element to a
> > List<Integer>, 2) there is only one checkbox in the list, 3) the checkbox
> > is not checked when the form is submitted.  The situation arises for me
> > when I need to display a list of checkboxes, but I can't use
> > <s:checkboxlist/> tag because the page requires a more advanced html
> > layout.  Thus I am forced to display the checkbox list using an
> > <s:iterator/> and the <s:checkbox/> tag.  If the displayed list so
> happens
> > to have only one element, and the user doesn't check it, the conversion
> > fails.
> >
> > I am using now Struts Version 2.5.13.
> >
> > *Test Struts Webb App*
> > *Download*: https://www.dropbox.com/s/x27o9a8qky9nwta/listTest.zip?dl=0
> > *Action*: mvn jetty:run
> > *Url*: http://localhost:8080/ListConverterTest.action
> >
> > On Fri, Sep 29, 2017 at 10:56 AM, Burton Rhodes <bu...@gmail.com>
> > wrote:
> >
> >> Sorry for the delay.  I have upgraded to the newest version and
> everything
> >> seems to be working.  Thanks!
> >>
> >> On Mon, Sep 25, 2017 at 2:34 AM, Lukasz Lenart <lukaszlenart@apache.org
> >
> >> wrote:
> >>
> >>> 2017-09-25 5:04 GMT+02:00 Burton Rhodes <bu...@gmail.com>:
> >>>> When extending the StrutsTypeConverter, is there anyway to figure out
> if
> >>>> the "toClass" is a List<Integer> or a List<String>?  I have found that
> >>> when
> >>>> converting data from a submitted webpage that has a value of a List
> in a
> >>>> single variable, the standard struts conversion fails.  For example:
> >>>> <s:hidden name="integerList" value="%{integerList}" /> display as
> >>> <s:hidden
> >>>> name="integerList" value="[1,2,3,4,5]" />.  When the form submits,
> this
> >>>> value will not convert properly back into the List.  In addition, the
> >>>> conversion fails if you have a list of checkboxes and the user only
> >>> checks
> >>>> one -  hence only a single variable being converted to a List.
> >>>>
> >>>> I have solved this issue by creating a MyListConverter, but I have to
> >>>> declare the converter on each action in a [-conversion.properties]
> file
> >>>> which is now becoming a bit cumbersome since this is such a common
> >>>> occurrence. I have also declared some on my model/entity beans, but
> >>>> still.... I would love to have a more global "List" converter, such
> as:
> >>>>
> >>>> [xwork-conversion.properties]
> >>>> java.util.List=com.afs.web.converter.MyListConverter
> >>>>
> >>>> Thus any List that is encountered, I could attempt "my conversion" and
> >>> send
> >>>> up the chain of command if the resulting List is not of List<Integer>
> or
> >>>> List<String>.
> >>>>
> >>>> [Psuedo_Code]
> >>>> public class MyListConverter extends StrutsTypeConverter {
> >>>>      public Object convertFromString(Map context, String[] values,
> Class
> >>>> toClass) {
> >>>>          // Is toClass List<Integer>, then try "my" conversion
> >>>>
> >>>>          // Else is toClass List<String?, then try "my" conversion
> >>>>
> >>>>          // Else return performFallbackConversion(context, o,
> toClass);
> >>>>      }
> >>>> }
> >>>>
> >>>> Any ideas?  Or am I going about this incorrectly?
> >>>
> >>> What version of Struts do you use? I think this was resolved in 2.5.13
> >>> or 2.5.12 - I meant conversion of list of built-in types (ints,
> >>> doubles, etc), to convert your own type just register it (as for the
> >>> List above).
> >>>
> >>>
> >>> Regards
> >>> --
> >>> Łukasz
> >>> + 48 606 323 122 http://www.lenart.org.pl/
> >>>
> >>> ---------------------------------------------------------------------
> >>> To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
> >>> For additional commands, e-mail: user-help@struts.apache.org
> >>>
> >>>
> >>
> >
>

Re: Extending StrutsTypeConverter :: How to detect specific type of "Class toClass"?

Posted by Yasser Zamani <ya...@live.com>.
Hello Burton,

Thank you; I examined your example and found out this behavior is 
because of something in Struts named "automatic checkbox detection", 
CheckboxInterceptor.

When your `choices` count is bigger than 1, you'll see your desired 
behavior because CheckboxInterceptor does nothing with following message 
where value.isMultiple() is true:

```java
if(value.isMultiple()) {
     LOG.debug("Bypassing automatic checkbox detection due to multiple 
checkboxes of the same name: {}", name);
} else if(!parameters.contains(checkboxName)) {
     extraParams.put(checkboxName, new Request(checkboxName, 
this.uncheckedValue));
}
```

But what happens when your `choices` count is one and you don't click on 
that one (your current example): Actually W3C says unchecked checkbox 
wont be posted, so, the above else will be executed (because 
!parameters.contains(checkboxName) is true) and CheckboxInterceptor sets 
a new parameter, "itemsFail->false". Then OGNL cannot convert `false` to 
an array of Integer into your action, so, the result will be changed to 
`input`.

I searched how to also post unchecked check boxes and found out that 
following makes your example working:
```jsp
<s:iterator var="choice" value="%{choices}">
     <s:hidden value='0' name='itemsFail'/><!-- I added this; a default -->
     <s:checkbox name="itemsFail" fieldValue="%{choice}" 
value="%{isItemsFailSelected(#choice)}"/> <s:property value="%{#choice}"/>
</s:iterator>
```

Hope these help!
Yasser.

On 10/1/2017 6:57 AM, Burton Rhodes wrote:
> Well shoot - after further testing it seems the issue is still present.  I
> isolated the issue in a simple mvn webapp (see link below).  Essentially
> Struts conversion fails when: 1) setting form input element to a
> List<Integer>, 2) there is only one checkbox in the list, 3) the checkbox
> is not checked when the form is submitted.  The situation arises for me
> when I need to display a list of checkboxes, but I can't use
> <s:checkboxlist/> tag because the page requires a more advanced html
> layout.  Thus I am forced to display the checkbox list using an
> <s:iterator/> and the <s:checkbox/> tag.  If the displayed list so happens
> to have only one element, and the user doesn't check it, the conversion
> fails.
> 
> I am using now Struts Version 2.5.13.
> 
> *Test Struts Webb App*
> *Download*: https://www.dropbox.com/s/x27o9a8qky9nwta/listTest.zip?dl=0
> *Action*: mvn jetty:run
> *Url*: http://localhost:8080/ListConverterTest.action
> 
> On Fri, Sep 29, 2017 at 10:56 AM, Burton Rhodes <bu...@gmail.com>
> wrote:
> 
>> Sorry for the delay.  I have upgraded to the newest version and everything
>> seems to be working.  Thanks!
>>
>> On Mon, Sep 25, 2017 at 2:34 AM, Lukasz Lenart <lu...@apache.org>
>> wrote:
>>
>>> 2017-09-25 5:04 GMT+02:00 Burton Rhodes <bu...@gmail.com>:
>>>> When extending the StrutsTypeConverter, is there anyway to figure out if
>>>> the "toClass" is a List<Integer> or a List<String>?  I have found that
>>> when
>>>> converting data from a submitted webpage that has a value of a List in a
>>>> single variable, the standard struts conversion fails.  For example:
>>>> <s:hidden name="integerList" value="%{integerList}" /> display as
>>> <s:hidden
>>>> name="integerList" value="[1,2,3,4,5]" />.  When the form submits, this
>>>> value will not convert properly back into the List.  In addition, the
>>>> conversion fails if you have a list of checkboxes and the user only
>>> checks
>>>> one -  hence only a single variable being converted to a List.
>>>>
>>>> I have solved this issue by creating a MyListConverter, but I have to
>>>> declare the converter on each action in a [-conversion.properties] file
>>>> which is now becoming a bit cumbersome since this is such a common
>>>> occurrence. I have also declared some on my model/entity beans, but
>>>> still.... I would love to have a more global "List" converter, such as:
>>>>
>>>> [xwork-conversion.properties]
>>>> java.util.List=com.afs.web.converter.MyListConverter
>>>>
>>>> Thus any List that is encountered, I could attempt "my conversion" and
>>> send
>>>> up the chain of command if the resulting List is not of List<Integer> or
>>>> List<String>.
>>>>
>>>> [Psuedo_Code]
>>>> public class MyListConverter extends StrutsTypeConverter {
>>>>      public Object convertFromString(Map context, String[] values, Class
>>>> toClass) {
>>>>          // Is toClass List<Integer>, then try "my" conversion
>>>>
>>>>          // Else is toClass List<String?, then try "my" conversion
>>>>
>>>>          // Else return performFallbackConversion(context, o, toClass);
>>>>      }
>>>> }
>>>>
>>>> Any ideas?  Or am I going about this incorrectly?
>>>
>>> What version of Struts do you use? I think this was resolved in 2.5.13
>>> or 2.5.12 - I meant conversion of list of built-in types (ints,
>>> doubles, etc), to convert your own type just register it (as for the
>>> List above).
>>>
>>>
>>> Regards
>>> --
>>> Łukasz
>>> + 48 606 323 122 http://www.lenart.org.pl/
>>>
>>> ---------------------------------------------------------------------
>>> To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
>>> For additional commands, e-mail: user-help@struts.apache.org
>>>
>>>
>>
> 

Re: Extending StrutsTypeConverter :: How to detect specific type of "Class toClass"?

Posted by Burton Rhodes <bu...@gmail.com>.
Well shoot - after further testing it seems the issue is still present.  I
isolated the issue in a simple mvn webapp (see link below).  Essentially
Struts conversion fails when: 1) setting form input element to a
List<Integer>, 2) there is only one checkbox in the list, 3) the checkbox
is not checked when the form is submitted.  The situation arises for me
when I need to display a list of checkboxes, but I can't use
<s:checkboxlist/> tag because the page requires a more advanced html
layout.  Thus I am forced to display the checkbox list using an
<s:iterator/> and the <s:checkbox/> tag.  If the displayed list so happens
to have only one element, and the user doesn't check it, the conversion
fails.

I am using now Struts Version 2.5.13.

*Test Struts Webb App*
*Download*: https://www.dropbox.com/s/x27o9a8qky9nwta/listTest.zip?dl=0
*Action*: mvn jetty:run
*Url*: http://localhost:8080/ListConverterTest.action

On Fri, Sep 29, 2017 at 10:56 AM, Burton Rhodes <bu...@gmail.com>
wrote:

> Sorry for the delay.  I have upgraded to the newest version and everything
> seems to be working.  Thanks!
>
> On Mon, Sep 25, 2017 at 2:34 AM, Lukasz Lenart <lu...@apache.org>
> wrote:
>
>> 2017-09-25 5:04 GMT+02:00 Burton Rhodes <bu...@gmail.com>:
>> > When extending the StrutsTypeConverter, is there anyway to figure out if
>> > the "toClass" is a List<Integer> or a List<String>?  I have found that
>> when
>> > converting data from a submitted webpage that has a value of a List in a
>> > single variable, the standard struts conversion fails.  For example:
>> > <s:hidden name="integerList" value="%{integerList}" /> display as
>> <s:hidden
>> > name="integerList" value="[1,2,3,4,5]" />.  When the form submits, this
>> > value will not convert properly back into the List.  In addition, the
>> > conversion fails if you have a list of checkboxes and the user only
>> checks
>> > one -  hence only a single variable being converted to a List.
>> >
>> > I have solved this issue by creating a MyListConverter, but I have to
>> > declare the converter on each action in a [-conversion.properties] file
>> > which is now becoming a bit cumbersome since this is such a common
>> > occurrence. I have also declared some on my model/entity beans, but
>> > still.... I would love to have a more global "List" converter, such as:
>> >
>> > [xwork-conversion.properties]
>> > java.util.List=com.afs.web.converter.MyListConverter
>> >
>> > Thus any List that is encountered, I could attempt "my conversion" and
>> send
>> > up the chain of command if the resulting List is not of List<Integer> or
>> > List<String>.
>> >
>> > [Psuedo_Code]
>> > public class MyListConverter extends StrutsTypeConverter {
>> >     public Object convertFromString(Map context, String[] values, Class
>> > toClass) {
>> >         // Is toClass List<Integer>, then try "my" conversion
>> >
>> >         // Else is toClass List<String?, then try "my" conversion
>> >
>> >         // Else return performFallbackConversion(context, o, toClass);
>> >     }
>> > }
>> >
>> > Any ideas?  Or am I going about this incorrectly?
>>
>> What version of Struts do you use? I think this was resolved in 2.5.13
>> or 2.5.12 - I meant conversion of list of built-in types (ints,
>> doubles, etc), to convert your own type just register it (as for the
>> List above).
>>
>>
>> Regards
>> --
>> Łukasz
>> + 48 606 323 122 http://www.lenart.org.pl/
>>
>> ---------------------------------------------------------------------
>> To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
>> For additional commands, e-mail: user-help@struts.apache.org
>>
>>
>

Re: Extending StrutsTypeConverter :: How to detect specific type of "Class toClass"?

Posted by Burton Rhodes <bu...@gmail.com>.
Sorry for the delay.  I have upgraded to the newest version and everything
seems to be working.  Thanks!

On Mon, Sep 25, 2017 at 2:34 AM, Lukasz Lenart <lu...@apache.org>
wrote:

> 2017-09-25 5:04 GMT+02:00 Burton Rhodes <bu...@gmail.com>:
> > When extending the StrutsTypeConverter, is there anyway to figure out if
> > the "toClass" is a List<Integer> or a List<String>?  I have found that
> when
> > converting data from a submitted webpage that has a value of a List in a
> > single variable, the standard struts conversion fails.  For example:
> > <s:hidden name="integerList" value="%{integerList}" /> display as
> <s:hidden
> > name="integerList" value="[1,2,3,4,5]" />.  When the form submits, this
> > value will not convert properly back into the List.  In addition, the
> > conversion fails if you have a list of checkboxes and the user only
> checks
> > one -  hence only a single variable being converted to a List.
> >
> > I have solved this issue by creating a MyListConverter, but I have to
> > declare the converter on each action in a [-conversion.properties] file
> > which is now becoming a bit cumbersome since this is such a common
> > occurrence. I have also declared some on my model/entity beans, but
> > still.... I would love to have a more global "List" converter, such as:
> >
> > [xwork-conversion.properties]
> > java.util.List=com.afs.web.converter.MyListConverter
> >
> > Thus any List that is encountered, I could attempt "my conversion" and
> send
> > up the chain of command if the resulting List is not of List<Integer> or
> > List<String>.
> >
> > [Psuedo_Code]
> > public class MyListConverter extends StrutsTypeConverter {
> >     public Object convertFromString(Map context, String[] values, Class
> > toClass) {
> >         // Is toClass List<Integer>, then try "my" conversion
> >
> >         // Else is toClass List<String?, then try "my" conversion
> >
> >         // Else return performFallbackConversion(context, o, toClass);
> >     }
> > }
> >
> > Any ideas?  Or am I going about this incorrectly?
>
> What version of Struts do you use? I think this was resolved in 2.5.13
> or 2.5.12 - I meant conversion of list of built-in types (ints,
> doubles, etc), to convert your own type just register it (as for the
> List above).
>
>
> Regards
> --
> Łukasz
> + 48 606 323 122 http://www.lenart.org.pl/
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
> For additional commands, e-mail: user-help@struts.apache.org
>
>

Re: Extending StrutsTypeConverter :: How to detect specific type of "Class toClass"?

Posted by Lukasz Lenart <lu...@apache.org>.
2017-09-25 5:04 GMT+02:00 Burton Rhodes <bu...@gmail.com>:
> When extending the StrutsTypeConverter, is there anyway to figure out if
> the "toClass" is a List<Integer> or a List<String>?  I have found that when
> converting data from a submitted webpage that has a value of a List in a
> single variable, the standard struts conversion fails.  For example:
> <s:hidden name="integerList" value="%{integerList}" /> display as <s:hidden
> name="integerList" value="[1,2,3,4,5]" />.  When the form submits, this
> value will not convert properly back into the List.  In addition, the
> conversion fails if you have a list of checkboxes and the user only checks
> one -  hence only a single variable being converted to a List.
>
> I have solved this issue by creating a MyListConverter, but I have to
> declare the converter on each action in a [-conversion.properties] file
> which is now becoming a bit cumbersome since this is such a common
> occurrence. I have also declared some on my model/entity beans, but
> still.... I would love to have a more global "List" converter, such as:
>
> [xwork-conversion.properties]
> java.util.List=com.afs.web.converter.MyListConverter
>
> Thus any List that is encountered, I could attempt "my conversion" and send
> up the chain of command if the resulting List is not of List<Integer> or
> List<String>.
>
> [Psuedo_Code]
> public class MyListConverter extends StrutsTypeConverter {
>     public Object convertFromString(Map context, String[] values, Class
> toClass) {
>         // Is toClass List<Integer>, then try "my" conversion
>
>         // Else is toClass List<String?, then try "my" conversion
>
>         // Else return performFallbackConversion(context, o, toClass);
>     }
> }
>
> Any ideas?  Or am I going about this incorrectly?

What version of Struts do you use? I think this was resolved in 2.5.13
or 2.5.12 - I meant conversion of list of built-in types (ints,
doubles, etc), to convert your own type just register it (as for the
List above).


Regards
-- 
Łukasz
+ 48 606 323 122 http://www.lenart.org.pl/

---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
For additional commands, e-mail: user-help@struts.apache.org