javascript
$.ajax({
headers : {
'Accept' : 'application/json' ,
'Content-Type' : 'application/json'
},
url : "/realgrid/product/addOd.do",
type : "post",
data : JSON.stringify(JsonOrderDetailValues),
dataType : "json",
success : function(data){
var json = eval(data);
if (json.result == 1) {
alert("insert.");
}else if(json.result == 2){
alert("update.")
}else {
alert("error.");
}
},
error : function(request,status,error){
alert("code:"+request.status+"\n"+"error:"+error);
}
});
console.log(JsonOrderDetailValues)
[Object, Object, Object, Object]
0: Object
categoryCode: "AC-MV"
categoryName: undefined
costPrice: 168050
date: undefined
modelCode: "YP-GB70"
modelName: undefined
no: 1
number: "201309120932"
total: 88
totalPrice: 14788400
typeCode: "AV"
typeName: undefined
unitPrice: 294500
__proto__: Object
1: Object
2: Object
3: Object
java spring Controller
@RequestMapping (value="/addOd.do",method=RequestMethod.POST)
public ModelAndView addOdMaster(@RequestBody List<OrderDetails> od){
//java.lang.ClassCastException: java.util.LinkedHashMap cannot be cast
System.out.println(od.get(0).getNumber());
Map<String, Integer> result = new HashMap<String,Integer>();
result.put("result", 0);
return new ModelAndView("jsonView",result);
}
vo
public class OrderDetails {
private String number;
private int no;
private String typeCode;
private String categoryCode;
private String modelCode;
private int total;
private int costPrice;
private int unitPrice;
private int totalPrice;
public int getTotalPrice() {
return totalPrice;
}
public void setTotalPrice(int totalPrice) {
this.totalPrice = totalPrice;
}
public String getNumber() {
return number;
}
public void setNumber(String number) {
this.number = number;
}
public int getNo() {
return no;
}
public void setNo(int no) {
this.no = no;
}
public String getTypeCode() {
return typeCode;
}
public void setTypeCode(String typeCode) {
this.typeCode = typeCode;
}
public String getCategoryCode() {
return categoryCode;
}
public void setCategoryCode(String categoryCode) {
this.categoryCode = categoryCode;
}
public String getModelCode() {
return modelCode;
}
public void setModelCode(String modelCode) {
this.modelCode = modelCode;
}
public int getTotal() {
return total;
}
public void setTotal(int total) {
this.total = total;
}
public int getCostPrice() {
return costPrice;
}
public void setCostPrice(int costPrice) {
this.costPrice = costPrice;
}
public int getUnitPrice() {
return unitPrice;
}
public void setUnitPrice(int unitPrice) {
this.unitPrice = unitPrice;
}
}
error message
FATAL: Servlet.service() for servlet [dispatcher] in context with path [/realgrid] threw exception [Request processing failed; nested exception is java.lang.ClassCastException: java.util.LinkedHashMap cannot be cast to com.realgrid.productControl.model.OrderDetails] with root cause
java.lang.ClassCastException: java.util.LinkedHashMap cannot be cast to com.realgrid.productControl.model.OrderDetails
at com.realgrid.productControl.controller.ProductControlController.addOdMaster(ProductControlController.java:181)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at org.springframework.web.method.support.InvocableHandlerMethod.invoke(InvocableHandlerMethod.java:213)
at org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:126)
at org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:96)
at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.invokeHandlerMethod(RequestMappingHandlerAdapter.java:617)
at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.handleInternal(RequestMappingHandlerAdapter.java:578)
at org.springframework.web.servlet.mvc.method.AbstractHandlerMethodAdapter.handle(AbstractHandlerMethodAdapter.java:80)
at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:923)
at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:852)
at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:882)
at org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:789)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:641)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:722)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:304)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:88)
at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:76)
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:240)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:164)
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:562)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:395)
at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:250)
at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:188)
at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:302)
at java.util.concurrent.ThreadPoolExecutor.runWorker(Unknown Source)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source)
at java.lang.Thread.run(Unknown Source)
Why not?
-
What Spring version are you using?Sotirios Delimanolis– Sotirios Delimanolis2014年06月20日 02:10:54 +00:00Commented Jun 20, 2014 at 2:10
1 Answer 1
In older versions of Spring, Spring couldn't (or rather wouldn't) determine that
@RequestBody List<OrderDetails> od
had a generic type of OrderDetails
and therefore Jackson (the JSON deserialiser) would use LinkedHashMap
as a default type. Type safety would break as in your case because all this whole request handling invocation (@RequestMapping
method and its arguments) is done through reflection.
The solution for those versions is to create your own type
public class OrderDetailsList extends ArrayList<OrderDetails> {}
and use that as a parameter
@RequestBody OrderDetailsList od
(Or upgrade to Spring 4.)
-
Or you could use od.get(0).get("number")vs4vijay– vs4vijay2014年08月08日 09:38:19 +00:00Commented Aug 8, 2014 at 9:38
-
@vs4vijay Actually they couldn't.
get(0)
, because of the generic type argument, returns aOrderDetails
and that does not have aget(String)
method. The actual object returned does, but theClassCastException
rightfully breaks the operation as soon as possible.Sotirios Delimanolis– Sotirios Delimanolis2014年08月08日 15:11:54 +00:00Commented Aug 8, 2014 at 15:11