struts-user mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Shaun Lim <shaunthegr...@gmail.com>
Subject Re: Struts2 REST plugin: Passing array in JSON
Date Thu, 11 Oct 2012 19:39:45 GMT
By the way, mapping to a simple String[] works, but I'm finding it hard to
believe that the plugin does not know how to handle conversions to List..

On Thu, Oct 11, 2012 at 11:54 AM, Shaun Lim <shaunthegreat@gmail.com> wrote:

> Method public java.lang.String
> org.apache.commons.lang.exception.NestableRuntimeException.getMessage(int)
> threw an exception when invoked on net.sf.json.JSONException: Error while
> setting property=arrayListStr type interface java.util.List
>
>
> On Thu, Oct 11, 2012 at 11:19 AM, Chris Pratt <thechrispratt@gmail.com>wrote:
>
>> What's the output of the run with this class & JSON?
>>   (*Chris*)
>>
>> On Thu, Oct 11, 2012 at 10:52 AM, Shaun Lim <shaunthegreat@gmail.com>
>> wrote:
>>
>> > Hi Chris,
>> >
>> > I did start off with a List<String> implementation but started changing
>> > stuff around in futile attempts to get something working. Anyway I tried
>> > your suggestion, and am still getting the same error:
>> >
>> > //I've a whole bunch of different fields here cause i was testing
>> various
>> > things, but "arrayListStr" follows your recommendation
>> >
>> > public class Test {
>> >     private String name;
>> >     private String description;
>> >     private List countries;
>> >
>> >     private String[] array;
>> >
>> >     private TestChild testChild;
>> >     private ArrayList arrayList;
>> >     private List<String> arrayListStr;
>> >
>> >     public Test() {
>> >         arrayList = new ArrayList();
>> >         arrayListStr = new ArrayList<String>();
>> >     }
>> >
>> >     public String getName() {
>> >         return name;
>> >     }
>> >
>> >     public void setName(String name) {
>> >         System.out.println("setting name");
>> >         this.name = name;
>> >     }
>> >
>> >     public String getDescription() {
>> >         System.out.println("getting desc");
>> >         return description;
>> >     }
>> >
>> >     public void setDescription(String description) {
>> >         System.out.println("settings description");
>> >         this.description = description;
>> >     }
>> >
>> >     public List getCountries() {
>> >         return countries;
>> >     }
>> >
>> >     public void setCountries(List countries) {
>> >         System.out.println("settings countries");
>> >         this.countries = countries;
>> >     }
>> >
>> >     public TestChild getTestChild() {
>> >         return testChild;
>> >     }
>> >
>> >     public void setTestChild(TestChild testChild) {
>> >         System.out.println("setting testchild");
>> >         this.testChild = testChild;
>> >     }
>> >
>> >     public String[] getArray() {
>> >         return array;
>> >     }
>> >
>> >     public void setArray(String[] array) {
>> >         System.out.println("setting arr");
>> >         this.array = array;
>> >     }
>> >
>> >     public ArrayList getArrayList() {
>> >         return arrayList;
>> >     }
>> >
>> >     public void setArrayList(ArrayList arrayList) {
>> >         System.out.println("setting arrlist");
>> >         this.arrayList = arrayList;
>> >     }
>> >
>> >     public List<String> getArrayListStr() {
>> >         return arrayListStr;
>> >     }
>> >
>> >     public void setArrayListStr(List<String> arrayListStr) {
>> >         System.out.println("setting arrliststr");
>> >         this.arrayListStr = arrayListStr;
>> >     }
>> > }
>> >
>> > And the JSON:
>> >
>> > {"testChild": {"description":"kid"},"description":"whee", "name":
>> > "foo","array":["CA","SG"],"arrayListStr":["CA","SG"]}
>> >
>> > Thanks for your help!
>> >
>> > Shaun
>> >
>> > On Wed, Oct 10, 2012 at 11:33 PM, Chris Pratt <thechrispratt@gmail.com
>> > >wrote:
>> >
>> > > You *might* need to initialize the countries array.  I wouldn't be
>> > > surprised if internally the JSON library is doing a
>> > > getCountries().add("CA") and throwing a null pointer exception because
>> > > getCountries is returning a null.
>> > >
>> > > Also, you should really be programming to interfaces, not
>> > implementations.
>> > > Define your methods to take and return the List<String> interface
>> instead
>> > > of the ArrayList<String> specific implementation and your programs
>> will
>> > be
>> > > much more flexible and reusable in the future.  See if this works
>> better:
>> > >   (*Chris*)
>> > >
>> > > public class Test {
>> > >     private String name;
>> > >     private String description;
>> > >     private List<String> countries;
>> > >
>> > >     public Test() {
>> > >        countries = new ArrayList<>();
>> > >     }
>> > >
>> > >     public String getName() {
>> > >         return name;
>> > >     }
>> > >
>> > >     public void setName(String name) {
>> > >         this.name = name;
>> > >     }
>> > >
>> > >     public String getDescription() {
>> > >         return description;
>> > >     }
>> > >
>> > >     public void setDescription(String description) {
>> > >         this.description = description;
>> > >     }
>> > >
>> > >     public List<String> getCountries() {
>> > >         return countries;
>> > >     }
>> > >
>> > >     public void setCountries(List<String> countries) {
>> > >         this.countries = countries;
>> > >     }
>> > > }
>> > >
>> > > On Wed, Oct 10, 2012 at 11:23 PM, Shaun Lim <shaunthegreat@gmail.com>
>> > > wrote:
>> > >
>> > > > My entity class:
>> > > >
>> > > > import java.util.ArrayList;
>> > > >
>> > > >
>> > > > public class Test {
>> > > >     private String name;
>> > > >     private String description;
>> > > >     private ArrayList<String> countries;
>> > > >
>> > > >     public Test() {
>> > > >
>> > > >     }
>> > > >
>> > > >     public String getName() {
>> > > >         return name;
>> > > >     }
>> > > >
>> > > >     public void setName(String name) {
>> > > >         this.name = name;
>> > > >     }
>> > > >
>> > > >     public String getDescription() {
>> > > >         return description;
>> > > >     }
>> > > >
>> > > >     public void setDescription(String description) {
>> > > >         this.description = description;
>> > > >     }
>> > > >
>> > > >     public ArrayList<String> getCountries() {
>> > > >         return countries;
>> > > >     }
>> > > >
>> > > >     public void setCountries(ArrayList<String> countries) {
>> > > >         this.countries = countries;
>> > > >     }
>> > > > }
>> > > >
>> > > > The JSON I'm trying to send:
>> > > >
>> > > > {"countries": ["CA", "SG"], "description":"whee", "name": "foo"}
>> > > >
>> > > > The error:
>> > > >
>> > > > 2345447 [http-bio-8080-exec-1] ERROR freemarker.runtime  - Method
>> > > > public java.lang.String
>> > > >
>> > >
>> >
>> org.apache.commons.lang.exception.NestableRuntimeException.getMessage(int)
>> > > > threw an exception when invoked on net.sf.json.JSONException: Error
>> > > > while setting property=countries type interface java.util.List
>> > > >
>> > > > Method public java.lang.String
>> > > >
>> > >
>> >
>> org.apache.commons.lang.exception.NestableRuntimeException.getMessage(int)
>> > > > threw an exception when invoked on net.sf.json.JSONException: Error
>> > > > while setting property=countries type interface java.util.List
>> > > > The problematic instruction:
>> > > > ----------
>> > > > ==> ${msgs[0][0]} [on line 76, column 25 in
>> > > > org/apache/struts2/dispatcher/error.ftl]
>> > > > ----------
>> > > >
>> > > > Java backtrace for programmers:
>> > > > ----------
>> > > > freemarker.template.TemplateModelException: Method public
>> > > > java.lang.String
>> > > >
>> > >
>> >
>> org.apache.commons.lang.exception.NestableRuntimeException.getMessage(int)
>> > > > threw an exception when invoked on net.sf.json.JSONException: Error
>> > > > while setting property=countries type interface java.util.List
>> > > >     at
>> > > >
>> freemarker.ext.beans.SimpleMethodModel.exec(SimpleMethodModel.java:130)
>> > > >     at
>> > > >
>> freemarker.ext.beans.SimpleMethodModel.get(SimpleMethodModel.java:138)
>> > > >     at
>> > > >
>> > >
>> >
>> freemarker.core.DynamicKeyName.dealWithNumericalKey(DynamicKeyName.java:111)
>> > > >     at
>> > > >
>> > >
>> >
>> freemarker.core.DynamicKeyName._getAsTemplateModel(DynamicKeyName.java:90)
>> > > >     at
>> > freemarker.core.Expression.getAsTemplateModel(Expression.java:89)
>> > > >     at freemarker.core.Expression.getStringValue(Expression.java:93)
>> > > >     at freemarker.core.DollarVariable.accept(DollarVariable.java:76)
>> > > >     at freemarker.core.Environment.visit(Environment.java:210)
>> > > >     at freemarker.core.MixedContent.accept(MixedContent.java:92)
>> > > >     at freemarker.core.Environment.visit(Environment.java:210)
>> > > >     at freemarker.core.IfBlock.accept(IfBlock.java:82)
>> > > >     at freemarker.core.Environment.visit(Environment.java:210)
>> > > >     at freemarker.core.IfBlock.accept(IfBlock.java:82)
>> > > >     at freemarker.core.Environment.visit(Environment.java:210)
>> > > >     at freemarker.core.MixedContent.accept(MixedContent.java:92)
>> > > >     at freemarker.core.Environment.visit(Environment.java:210)
>> > > >     at freemarker.core.Environment.process(Environment.java:190)
>> > > >     at freemarker.template.Template.process(Template.java:237)
>> > > >     at
>> > > >
>> org.apache.struts2.dispatcher.Dispatcher.sendError(Dispatcher.java:797)
>> > > >     at
>> > > >
>> > >
>> >
>> org.apache.struts2.dispatcher.Dispatcher.serviceAction(Dispatcher.java:519)
>> > > >     at
>> > > >
>> > >
>> >
>> org.apache.struts2.dispatcher.ng.ExecuteOperations.executeAction(ExecuteOperations.java:77)
>> > > >     at
>> > > >
>> > >
>> >
>> org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter.doFilter(StrutsPrepareAndExecuteFilter.java:91)
>> > > >     at
>> > > >
>> > >
>> >
>> org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:243)
>> > > >     at
>> > > >
>> > >
>> >
>> org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
>> > > >     at
>> > > >
>> > >
>> >
>> org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:224)
>> > > >     at
>> > > >
>> > >
>> >
>> org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:175)
>> > > >     at
>> > > >
>> > >
>> >
>> org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:462)
>> > > >     at
>> > > >
>> > >
>> >
>> org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:164)
>> > > >     at
>> > > >
>> > >
>> >
>> org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:100)
>> > > >     at
>> > > >
>> >
>> org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:851)
>> > > >     at
>> > > >
>> > >
>> >
>> org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118)
>> > > >     at
>> > > >
>> > >
>> >
>> org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:405)
>> > > >     at
>> > > >
>> > >
>> >
>> org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:278)
>> > > >     at
>> > > >
>> > >
>> >
>> org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:515)
>> > > >     at
>> > > >
>> > >
>> >
>> org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:300)
>> > > >     at
>> > > >
>> > >
>> >
>> java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:886)
>> > > >     at
>> > > >
>> > >
>> >
>> java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:908)
>> > > >     at java.lang.Thread.run(Thread.java:680)
>> > > > Caused by: java.lang.NullPointerException
>> > > >     at
>> > > >
>> > >
>> >
>> freemarker.ext.beans.SimpleMemberModel.unwrapArguments(SimpleMemberModel.java:85)
>> > > >     at
>> > > >
>> freemarker.ext.beans.SimpleMethodModel.exec(SimpleMethodModel.java:106)
>> > > >     ... 37 more
>> > > >
>> > > > Setting "name" and "description" without attempting to pass in
>> > > "countries"
>> > > > work - the values are successfully mapped.
>> > > >
>> > > > Using the following XML works too:
>> > > >
>> > > > <com.foo.bar.entity.Test>
>> > > > <countries>
>> > > > <string>SG</string>
>> > > > </countries>
>> > > > <description>testt</description>
>> > > > </com.foo.bar.entity.Test>
>> > > >
>> > >
>> >
>>
>
>

Mime
  • Unnamed multipart/alternative (inline, None, 0 bytes)
View raw message