我正在尝试从Java中的json字符串中提取属性,并且正在编写JsonDeseriizer来实现。
我的尝试如下所示:
public class testJacksonSimple {
@JsonDeserialize(using = ItemDeserializerJson.class)
public static class Item {
public int id;
public String itemName;
public Item(){};
public Item(int id, String itemName) {
this.id = id;
this.itemName = itemName;
}
public void setId(int id) {
this.id = id;
}
public int getId() {
return id;
}
}
public static class ItemDeserializerJson extends JsonDeserializer<Item> {
ObjectReader reader = new ObjectMapper().reader();
@Override
public Item deserialize(JsonParser jp, DeserializationContext context) throws IOException {
if(jp.currentToken() != JsonToken.VALUE_NULL) {
return reader.readValue(jp, Item.class);
} else {
return null;
}
}
}
}
这是我的测试用例:
public class test {
public static void main(String[] args){
ObjectMapper mapper = new ObjectMapper();
String json = "{\n" +
" \"id\": 1,\n" +
" \"itemName\": \"theItem\"\n" +
"}";
System.out.println(json);
testJacksonSimple.Item itemWithOwner = null;
try {
itemWithOwner = new ObjectMapper().readValue(json, testJacksonSimple.Item.class);
} catch (Exception e) {
e.printStackTrace();
}
System.out.println(itemWithOwner.id);
System.out.println(itemWithOwner.itemName);
}
}
我得到了错误:
Exception in thread "main" java.lang.StackOverflowError
at java.lang.reflect.Method.getParameterTypes(Method.java:264)
at sun.reflect.annotation.AnnotationInvocationHandler.invoke(AnnotationInvocationHandler.java:59)
at com.sun.proxy.$Proxy2.annotationType(Unknown Source)
at com.fasterxml.jackson.databind.introspect.AnnotationMap._add(AnnotationMap.java:135)
at com.fasterxml.jackson.databind.introspect.AnnotationMap.addIfNotPresent(AnnotationMap.java:101)
at com.fasterxml.jackson.databind.introspect.AnnotatedClass._addAnnotationsIfNotPresent(AnnotatedClass.java:1061)
at com.fasterxml.jackson.databind.introspect.AnnotatedClass._resolveClassAnnotations(AnnotatedClass.java:399)
at com.fasterxml.jackson.databind.introspect.AnnotatedClass._classAnnotations(AnnotatedClass.java:376)
at com.fasterxml.jackson.databind.introspect.AnnotatedClass.getAnnotation(AnnotatedClass.java:248)
at com.fasterxml.jackson.databind.AnnotationIntrospector._findAnnotation(AnnotationIntrospector.java:1436)
at com.fasterxml.jackson.databind.introspect.JacksonAnnotationIntrospector.findAutoDetectVisibility(JacksonAnnotationIntrospector.java:349)
at com.fasterxml.jackson.databind.introspect.POJOPropertiesCollector.<init>(POJOPropertiesCollector.java:129)
只是不明白为什么我会出现错误stackoverflow。我可以在不使用自定义JSONDeserializer的情况下获得正确的结果,但是我想对其进行测试。任何帮助表示赞赏。
答案 0 :(得分:3)
您已经通过调用objectmapper并请求其从自定义反序列化器内部反序列化json来创建无限循环。对象映射器将调用您的自定义解串器,然后您的自定义解串器将调用对象映射器。因此,stackoverflow。
以下对我有用:
Kotlin
答案 1 :(得分:0)
因此,基本上reader.readValue(jp, Item.class);
会循环调用反序列化方法。
顺便说一下,请保持命名约定(类名应为UpperCamelCase):http://www.oracle.com/technetwork/java/javase/overview/codeconventions-135099.html