通过Fegin远程调用 ,返回JPA Page 对象报错
Caused by: com.fasterxml.jackson.databind.JsonMappingException: Can not construct instance of org.springframework.data.domain.Page: abstract types either need to be mapped to concrete types, have custom deserializer, or contain additional type information
at [Source: java.io.PushbackInputStream@5ebf9e24; line: 2, column: 12] (through reference chain: com.sysware.cloud.plugin.bean.Response["data"])
at com.fasterxml.jackson.databind.JsonMappingException.from(JsonMappingException.java:270) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.DeserializationContext.instantiationException(DeserializationContext.java:1456) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.DeserializationContext.handleMissingInstantiator(DeserializationContext.java:1012) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.AbstractDeserializer.deserialize(AbstractDeserializer.java:216) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.SettableBeanProperty.deserialize(SettableBeanProperty.java:504) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.impl.MethodProperty.deserializeAndSet(MethodProperty.java:104) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserializeFromObject(BeanDeserializer.java:357) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserialize(BeanDeserializer.java:148) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.ObjectMapper._readMapAndClose(ObjectMapper.java:3814) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.ObjectMapper.readValue(ObjectMapper.java:2938) ~[jackson-databind-2.8.10.jar:2.8.10]
at org.springframework.http.converter.json.AbstractJackson2HttpMessageConverter.readJavaType(AbstractJackson2HttpMessageConverter.java:235) ~[spring-web-4.3.13.RELEASE.jar:4.3.13.RELEASE]
at org.springframework.http.converter.json.AbstractJackson2HttpMessageConverter.read(AbstractJackson2HttpMessageConverter.java:223) ~[spring-web-4.3.13.RELEASE.jar:4.3.13.RELEASE]
at org.springframework.web.client.HttpMessageConverterExtractor.extractData(HttpMessageConverterExtractor.java:96) ~[spring-web-4.3.13.RELEASE.jar:4.3.13.RELEASE]
at org.springframework.cloud.netflix.feign.support.SpringDecoder.decode(SpringDecoder.java:59) ~[spring-cloud-netflix-core-1.4.2.RELEASE.jar:1.4.2.RELEASE]
at org.springframework.cloud.netflix.feign.support.ResponseEntityDecoder.decode(ResponseEntityDecoder.java:45) ~[spring-cloud-netflix-core-1.4.2.RELEASE.jar:1.4.2.RELEASE]
at feign.SynchronousMethodHandler.decode(SynchronousMethodHandler.java:165) ~[feign-core-9.5.0.jar:?]
at feign.SynchronousMethodHandler.executeAndDecode(SynchronousMethodHandler.java:133) ~[feign-core-9.5.0.jar:?]
at feign.SynchronousMethodHandler.invoke(SynchronousMethodHandler.java:76) ~[feign-core-9.5.0.jar:?]
at feign.hystrix.HystrixInvocationHandler$1.run(HystrixInvocationHandler.java:108) ~[feign-hystrix-9.5.0.jar:?]
at com.netflix.hystrix.HystrixCommand$2.call(HystrixCommand.java:302) ~[hystrix-core-1.5.12.jar:1.5.12]
at com.netflix.hystrix.HystrixCommand$2.call(HystrixCommand.java:298) ~[hystrix-core-1.5.12.jar:1.5.12]
at rx.internal.operators.OnSubscribeDefer.call(OnSubscribeDefer.java:46) ~[rxjava-1.2.0.jar:1.2.0]
... 26 more
大概意思是:不能构造实例org.springframework.data.domain.Page :抽象类型要么需要映射到具体类型,要么有自定义反序列化器,要么用额外的类型信息进行实例化 。
解释下啊,第一种办法就是page是一个接口,反序列化需要配置映射到具体的类型在Page类上面加@JsonDeserialize注解,指定反序列化的具体实现,但是Page类并不是我们自定义的类,所以在Page接口上加注解应该是不现实的
第二种办法就是,需要自定义反序列化器,大概就是说序列化和反序列化是使用默认的readOjbect ,和 writeObject ,但是通过默认的readOject解析不了,需要用户自定义解析Page的解析。
第三方式就是,自定义抽象类型的实现类,用实现类接受。
我们查找到Page的实现类,框架本身已经提供PageImpl,所以我们换成PageImpl接受返回值。
然而,换成PageImpl接受报如下错误:
Caused by: com.fasterxml.jackson.databind.JsonMappingException: Can not construct instance of org.springframework.data.domain.PageImpl: no suitable constructor found, can not deserialize from Object value (missing default constructor or creator, or perhaps need to add/enable type information?)
at [Source: java.io.PushbackInputStream@6e88a853; line: 3, column: 5] (through reference chain: com.sysware.cloud.plugin.bean.Response["data"])
at com.fasterxml.jackson.databind.JsonMappingException.from(JsonMappingException.java:270) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.DeserializationContext.instantiationException(DeserializationContext.java:1456) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.DeserializationContext.handleMissingInstantiator(DeserializationContext.java:1012) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.BeanDeserializerBase.deserializeFromObjectUsingNonDefault(BeanDeserializerBase.java:1206) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserializeFromObject(BeanDeserializer.java:314) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserialize(BeanDeserializer.java:148) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.SettableBeanProperty.deserialize(SettableBeanProperty.java:504) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.impl.MethodProperty.deserializeAndSet(MethodProperty.java:104) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserializeFromObject(BeanDeserializer.java:357) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserialize(BeanDeserializer.java:148) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.ObjectMapper._readMapAndClose(ObjectMapper.java:3814) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.ObjectMapper.readValue(ObjectMapper.java:2938) ~[jackson-databind-2.8.10.jar:2.8.10]
at org.springframework.http.converter.json.AbstractJackson2HttpMessageConverter.readJavaType(AbstractJackson2HttpMessageConverter.java:235) ~[spring-web-4.3.13.RELEASE.jar:4.3.13.RELEASE]
at org.springframework.http.converter.json.AbstractJackson2HttpMessageConverter.read(AbstractJackson2HttpMessageConverter.java:223) ~[spring-web-4.3.13.RELEASE.jar:4.3.13.RELEASE]
at org.springframework.web.client.HttpMessageConverterExtractor.extractData(HttpMessageConverterExtractor.java:96) ~[spring-web-4.3.13.RELEASE.jar:4.3.13.RELEASE]
at org.springframework.cloud.netflix.feign.support.SpringDecoder.decode(SpringDecoder.java:59) ~[spring-cloud-netflix-core-1.4.2.RELEASE.jar:1.4.2.RELEASE]
at org.springframework.cloud.netflix.feign.support.ResponseEntityDecoder.decode(ResponseEntityDecoder.java:45) ~[spring-cloud-netflix-core-1.4.2.RELEASE.jar:1.4.2.RELEASE]
at feign.SynchronousMethodHandler.decode(SynchronousMethodHandler.java:165) ~[feign-core-9.5.0.jar:?]
at feign.SynchronousMethodHandler.executeAndDecode(SynchronousMethodHandler.java:133) ~[feign-core-9.5.0.jar:?]
at feign.SynchronousMethodHandler.invoke(SynchronousMethodHandler.java:76) ~[feign-core-9.5.0.jar:?]
at feign.hystrix.HystrixInvocationHandler$1.run(HystrixInvocationHandler.java:108) ~[feign-hystrix-9.5.0.jar:?]
at com.netflix.hystrix.HystrixCommand$2.call(HystrixCommand.java:302) ~[hystrix-core-1.5.12.jar:1.5.12]
at com.netflix.hystrix.HystrixCommand$2.call(HystrixCommand.java:298) ~[hystrix-core-1.5.12.jar:1.5.12]
at rx.internal.operators.OnSubscribeDefer.call(OnSubscribeDefer.java:46) ~[rxjava-1.2.0.jar:1.2.0]
... 26 more
大概意思是说:不能构造实例 org.springframework.data.domain.PageImpl : 没有合适的构造函数(此处还在查资料jackson反序列化和构造函数的关系),然后查阅PageImpl的源码,发现确实没有无参的构造函数
public PageImpl(List<T> content, Pageable pageable, long total) {
super(content, pageable);
this.pageable = pageable;
this.total = !content.isEmpty() && pageable != null && (long)(pageable.getOffset() + pageable.getPageSize()) > total?(long)(pageable.getOffset() + content.size()):total;
}
public PageImpl(List<T> content) {
this(content, (Pageable)null, null == content?0L:(long)content.size());
}
然后我们通过自定义类继承PageImpl ,并添加无参构造函数,代码如下(这是最终版,其实刚开始的时候Sort上没有加@JsonDeserialize(using=CustomSortDeserializer.class)),后面说加这个注解的作用。
package com.sysware.cloud.plugin.commons.http; import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
import lombok.Data;
import org.springframework.data.domain.PageImpl;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.domain.Sort; import java.util.ArrayList;
import java.util.List; /**
* Created by tianwenqing on 2018/7/9.
*/
@Data
public class RestResponsePage<T> extends PageImpl<T> {
public RestResponsePage(List<T> content, Pageable pageable, long total) {
super(content, pageable, total);
} private int number;
private int size;
private int totalPages;
private int numberOfElements;
private long totalElements;
private boolean previousPage;
private boolean first;
private boolean nextPage;
private boolean last;
private List<T> content;
@JsonDeserialize(using=CustomSortDeserializer.class)
private Sort sort; public RestResponsePage(List<T> content) {
super(content);
} public RestResponsePage() {
super(new ArrayList<T>());
} public PageImpl<T> pageImpl() {
return new PageImpl<T>(getContent(), new PageRequest(getNumber(),
getSize(), getSort()), getTotalElements());
}
}
package com.sysware.cloud.plugin.commons.http; import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.DeserializationContext;
import com.fasterxml.jackson.databind.JsonDeserializer;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.node.ArrayNode;
import org.springframework.data.domain.Sort; import java.io.IOException; /**
* Created by tianwenqing on 2018/7/9.
*/
public class CustomSortDeserializer extends JsonDeserializer<Sort> {
@Override
public Sort deserialize(JsonParser jp, DeserializationContext deserializationContext) throws IOException, JsonProcessingException {
ArrayNode node = jp.getCodec().readTree(jp);
Sort.Order[] orders = new Sort.Order[node.size()];
int i = 0;
for(JsonNode obj : node){
orders[i] = new Sort.Order(Sort.Direction.valueOf(obj.get("direction").asText()), obj.get("property").asText());
i++;
}
Sort sort = new Sort(orders);
return sort;
}
}
上面的的两个类就是最终代码,然后FeginClient端接受的时候用RestResponsePage替代Page,即可。
下面介绍@JsonDeserialize(using=CustomSortDeserializer.class)
刚开始创建完RestResponsePage类,没有加@JsonDeserialize(using=CustomSortDeserializer.class) 直接引用,结果又报下面的错:
Caused by: com.fasterxml.jackson.databind.JsonMappingException: Can not deserialize instance of org.springframework.data.domain.Sort out of START_ARRAY token
at [Source: java.io.PushbackInputStream@5f88be0f; line: 84, column: 14] (through reference chain: com.sysware.cloud.plugin.bean.Response["data"]->com.sysware.cloud.test.aggregation.RestResponsePage["sort"])
at com.fasterxml.jackson.databind.JsonMappingException.from(JsonMappingException.java:270) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.DeserializationContext.reportMappingException(DeserializationContext.java:1234) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.DeserializationContext.handleUnexpectedToken(DeserializationContext.java:1122) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.DeserializationContext.handleUnexpectedToken(DeserializationContext.java:1075) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.BeanDeserializerBase.deserializeFromArray(BeanDeserializerBase.java:1370) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.BeanDeserializer._deserializeOther(BeanDeserializer.java:174) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserialize(BeanDeserializer.java:150) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.SettableBeanProperty.deserialize(SettableBeanProperty.java:504) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.impl.MethodProperty.deserializeAndSet(MethodProperty.java:104) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserializeFromObject(BeanDeserializer.java:357) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserialize(BeanDeserializer.java:148) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.SettableBeanProperty.deserialize(SettableBeanProperty.java:504) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.impl.MethodProperty.deserializeAndSet(MethodProperty.java:104) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserializeFromObject(BeanDeserializer.java:357) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserialize(BeanDeserializer.java:148) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.ObjectMapper._readMapAndClose(ObjectMapper.java:3814) ~[jackson-databind-2.8.10.jar:2.8.10]
at com.fasterxml.jackson.databind.ObjectMapper.readValue(ObjectMapper.java:2938) ~[jackson-databind-2.8.10.jar:2.8.10]
at org.springframework.http.converter.json.AbstractJackson2HttpMessageConverter.readJavaType(AbstractJackson2HttpMessageConverter.java:235) ~[spring-web-4.3.13.RELEASE.jar:4.3.13.RELEASE]
at org.springframework.http.converter.json.AbstractJackson2HttpMessageConverter.read(AbstractJackson2HttpMessageConverter.java:223) ~[spring-web-4.3.13.RELEASE.jar:4.3.13.RELEASE]
at org.springframework.web.client.HttpMessageConverterExtractor.extractData(HttpMessageConverterExtractor.java:96) ~[spring-web-4.3.13.RELEASE.jar:4.3.13.RELEASE]
at org.springframework.cloud.netflix.feign.support.SpringDecoder.decode(SpringDecoder.java:59) ~[spring-cloud-netflix-core-1.4.2.RELEASE.jar:1.4.2.RELEASE]
at org.springframework.cloud.netflix.feign.support.ResponseEntityDecoder.decode(ResponseEntityDecoder.java:45) ~[spring-cloud-netflix-core-1.4.2.RELEASE.jar:1.4.2.RELEASE]
at feign.SynchronousMethodHandler.decode(SynchronousMethodHandler.java:165) ~[feign-core-9.5.0.jar:?]
at feign.SynchronousMethodHandler.executeAndDecode(SynchronousMethodHandler.java:133) ~[feign-core-9.5.0.jar:?]
at feign.SynchronousMethodHandler.invoke(SynchronousMethodHandler.java:76) ~[feign-core-9.5.0.jar:?]
at feign.hystrix.HystrixInvocationHandler$1.run(HystrixInvocationHandler.java:108) ~[feign-hystrix-9.5.0.jar:?]
at com.netflix.hystrix.HystrixCommand$2.call(HystrixCommand.java:302) ~[hystrix-core-1.5.12.jar:1.5.12]
at com.netflix.hystrix.HystrixCommand$2.call(HystrixCommand.java:298) ~[hystrix-core-1.5.12.jar:1.5.12]
at rx.internal.operators.OnSubscribeDefer.call(OnSubscribeDefer.java:46) ~[rxjava-1.2.0.jar:1.2.0]
... 26 more
大概意思是说不能反序列化Sort属性,所以我们使用自定义反序列化器序列化Sort,至于为什么不能反序列化,google找到如下解释,还没有看太懂
If you look at Sort, you'll see that it implements Iteratable for Order. And if you examine Order defined in the same class, you'll see the fields in my example JSON. So when Sort is serialized, it is serialized as a list of Order, which is why deserializing into Sort needs a custom deserializer implementation, and also why deserializing without a custom implementation fails (because it's trying to deserialize an array into a single object).
During deserialization, when a setter annotated with @JsonDeserializer is encountered as each property is deserialized, Jackson uses the supplied deserializer to deserialize that specific property.
通过Fegin远程调用 ,返回JPA Page 对象报错的更多相关文章
- ajax 调用 .net core WebAPI,报错 400 (Bad Request) Unexpected character encountered while parsing value
此文由博主前两天的提问及 dudu 的回答整理,地址:https://q.cnblogs.com/list/myquestion 情况说明 基于 .net core 写了一个 Web API,用 po ...
- Jpa自定义查询报错(Failed to convert from type [java.lang.Object[]] to type)
Jpa自定义查询报错 问题背景 今天遇到一个奇怪的报错"Failed to convert from type [java.lang.Object[]] to type",这个报错 ...
- java调用本地方法的时候报错 could not find the main class:xx.program will exit
如图所示,当在java调用本地方法的时候报错 我的解决办法是把dll文件放到System.out.println(System.getProperty("java.library.path& ...
- 关于 JavaScript 中一个小细节问题 (在控制台中直接 {Name:'王尼玛',Age:20} 对象报错问题)
在 Chrome 浏览器,大家可能遇到这样一个小问题. 随便输入一个 Object 对象 ,比如 {Name:'王尼玛',Age:20} ,将会报错.之前,也从来没去考虑过到底是为啥原因. 今天,刚 ...
- js Fetch返回数据res.json()报错问题
前言 一直以来在简单的场景中经常使用fetch代替第三方请求库, fetch是JavaScript的原生函数, 简单.高效.快速.稳定.可定制等等诸多优点.一直也是用着很是舒服,直到有一天它竟然报错了 ...
- vc调用BCB的dll 参数传递 报错
可能原因: 调用方式约定不一致. 函数调用约定如下: 1. __cdecl:C 和 C++ 程序的缺省调用规范. 2. __stdcall:标准调用约定(即WINAPI调用约定),也就是pascal调 ...
- List转换成JSON对象报错(二)
List转换成JSON对象 1.具体报错如下 Exception in thread "main" java.lang.NoClassDefFoundError: org/apac ...
- List转换成JSON对象报错(一)
List转换成JSON对象 1.具体报错如下 Exception in thread "main" java.lang.NoClassDefFoundError: org/apac ...
- 微信授权、获取用户openid-纯前端实现——jsonp跨域访问返回json数据会报错的纯前端解决办法
近来,倒霉的后台跟我说让我拿个openid做微信支付使用,寻思很简单,开始干活. 首先引导用户打开如下链接,只需要将appid修改为自己的就可以,redirect_url写你的重定向url https ...
随机推荐
- Use the SVN command-line tool
欢迎关注我的社交账号: 博客园地址: http://www.cnblogs.com/jiangxinnju/p/4781259.html GitHub地址: https://github.com/ji ...
- win7系统下查看端口的占用情况以及如何删除端口进程
经常在本地测试开发使用tomcat的时候容易报端口占用的情况,比如我要查看8080端口的使用情况 1.按如下操作,输入 cmd 回车 2.在doc窗口中输入命令 netstat -ano | f ...
- iOS开发之UITableViewController重写
# UITablViewController方法的使用介绍 - (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView { // ...
- 图片上传ie与chrome总结
if(brow.msie) // ie浏览器执行此代码 { // data 可以是字符串 eval("data = " + data); } else // 其他浏览器执 ...
- 20145310《Java程序设计》第4次实验报告
20145310<Java程序设计>第4次实验报告 实验内容 搭建Android环境 运行Android 修改代码并输出自己的学号 实验步骤 搭建Android环境 安装Android S ...
- Java对map进行排序并生成序号
最近做的项目有这样一个需求:要求对map中的值进行排序并生成序号.如果值相等则序号不变:如果不相等序号为该数数值在所有元素中的索引.如下表所示: Key(String) Value(Float) Id ...
- maven项目引入本地包,不使用中央仓库
1. dependendy引入 <dependency> <groupId>com.taobao</groupId> <artifactId>taoba ...
- 关于xftp连接不了Linux,但是却可以用xshell连接Linux
解决方法:用sftp协议,不要用ftp协议
- L1-3 宇宙无敌加法器 - 令人激动的一道题目
L1-3 宇宙无敌加法器 - 令人激动的一道题目 感觉好久没有这么认真的做一道题了,今天看到一句话, 说是编程是一个工程型的工作,想要学好,"无他,唯手熟尔" 之前觉得自己笨,怀疑 ...
- 基于Redis的限流系统的设计
本文讲述基于Redis的限流系统的设计,主要会谈及限流系统中限流策略这个功能的设计:在实现方面,算法使用的是令牌桶算法来,访问Redis使用lua脚本. 1.概念 In computer netw ...