2016-11-01 3 views
0

У меня есть объект JSON, который сопоставляется с Java-объектом. JSON содержит вложенные данные, которые обрабатывает объект Java. Мой случай большой, поэтому я использую сокращенную версию в качестве примера того, что я пытаюсь.Сопоставление Java-объектов Jackson с ошибкой представления несуществующих «известных свойств»

Мои данные JSON выглядит следующим образом:

{"name":"wmi", "data": [{"ip":"192.168.1.50", "L2CacheSize":"1024", "L2CacheSpeed":"0"}, {"ip":"192.168.1.51", "L2CacheSize":"1024", "L2CacheSpeed":"0"}] }

где поле данных содержит список дополнительных объектов JSON. Это отображается с помощью Джексона на мой Java объект, который выглядит следующим образом:

public class WmiData { 
    private String name; 
    private List<Computer> data; 

    //Getters and Setters... 

    //Constructor 
    public WmiData(String name, List<Computer> computers) { 
     this.name = name; 
     this.data = computers; 
    } 

    static class Computer { 
     private String ip; 
     private Integer L2CacheSize; 
     private Integer L2CacheSpeed; 

     public Computer(String ip, Integer L2CacheSize, Integer L2CacheSpeed) { 
      this.ip = ip; 
      this.L2CacheSize = L2CacheSize; 
      this.L2CacheSpeed = L2CacheSpeed; 
     } 

     //Getters and Setters... 

    } 
} 

и я делаю простое отображение, как это:

ObjectMapper mapper = new ObjectMapper(); 
WmiData data = mapper.readValue(jsonString, WmiData.class); 

Однако синтаксический анализ не может дать ошибку:

SEVERE: Failure to convert json to object: 
com.fasterxml.jackson.databind.exc.UnrecognizedPropertyException: Unrecognized field "L2CacheSize" (class company.Data.Wmi$Computer), not marked as ignorable (3 known properties: , "ip", "l2CacheSize", "l2CacheSpeed") 
at [Source: {"data":[{"L2CacheSize":"1024","ip":"192.168.1.50","L2CacheSpeed":"0"}, {"L2CacheSize":"1024","ip":"192.168.1.51","L2CacheSpeed":"0"}],"name":"wmi"}; line: 1, column: 26] (through reference chain: company.Data.Wmi["data"]->company.Data.Computer["L2CacheSize"]) 
     at com.fasterxml.jackson.databind.exc.UnrecognizedPropertyException.from(UnrecognizedPropertyException.java:79) 
     at com.fasterxml.jackson.databind.DeserializationContext.reportUnknownProperty(DeserializationContext.java:568) 
     at com.fasterxml.jackson.databind.deser.std.StdDeserializer.handleUnknownProperty(StdDeserializer.java:649) 
     at com.fasterxml.jackson.databind.deser.BeanDeserializerBase.handleUnknownProperty(BeanDeserializerBase.java:830) 
     at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserializeFromObject(BeanDeserializer.java:310) 
     at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserialize(BeanDeserializer.java:112) 
     at com.fasterxml.jackson.databind.deser.std.CollectionDeserializer.deserialize(CollectionDeserializer.java:226) 
     at com.fasterxml.jackson.databind.deser.std.CollectionDeserializer.deserialize(CollectionDeserializer.java:203) 
     at com.fasterxml.jackson.databind.deser.std.CollectionDeserializer.deserialize(CollectionDeserializer.java:23) 
     at com.fasterxml.jackson.databind.deser.SettableBeanProperty.deserialize(SettableBeanProperty.java:338) 
     at com.fasterxml.jackson.databind.deser.impl.FieldProperty.deserializeAndSet(FieldProperty.java:87) 
     at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserializeFromObject(BeanDeserializer.java:290) 
     at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserialize(BeanDeserializer.java:112) 
     at com.fasterxml.jackson.databind.ObjectMapper._readMapAndClose(ObjectMapper.java:2563) 
     at com.fasterxml.jackson.databind.ObjectMapper.readValue(ObjectMapper.java:1805) 
     at uk.co.humboldt.Sums.Service.MessageHandler.getPoll(MessageHandler.java:93) 
     at uk.co.humboldt.Sums.Service.MessageHandler.pollWmi(MessageHandler.java:147) 
     at uk.co.humboldt.Sums.Service.MessageHandler.pollServices(MessageHandler.java:105) 
     at uk.co.humboldt.Sums.Service.MessageHandler.lambda$new$0(MessageHandler.java:72) 
     at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) 
     at java.util.concurrent.FutureTask.run(FutureTask.java:266) 
     at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.access$201(ScheduledThreadPoolExecutor.java:180) 
     at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.run(ScheduledThreadPoolExecutor.java:293) 
     at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) 
     at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) 
     at java.lang.Thread.run(Thread.java:745) 

Ошибка выше объясняет, что Джексон знает только о трех известных свойствах ip, l2CacheSize и l2CacheSpeed, два из которых не существуют в моем определение объекта. Мои поля L2CacheSize и L2CacheSpeed, обратите внимание на столицу «L» в обоих. Источник данных, на который он, похоже, жалуется, несовместим с тем, что ясно показывает, что входящие данные находятся в том же формате, что и мои объекты Java, но все же не работают.

В чем может быть проблема?

Любая помощь приветствуется.

+0

L2CacheSize - это строка, вы сопоставили ее с int, изменяете ее на тип строки. –

ответ

1

Проблема, которую вы видите, связана с тем, что Джексон использует соглашения об именах Java Bean, чтобы понять, какие свойства Json в классе Java.

Итак, чтобы решить эту проблему, вы можете изменить свои имена собственности на те, которые Джексон говорит, что он «знает» или комментирует это с помощью примера @JsonProperty("L2CacheSize").

static class Computer { 
    private String ip; 

    @JsonProperty("L2CacheSize") 
    private Integer L2CacheSize; 

    @JsonProperty("L2CacheSpeed") 
    private Integer L2CacheSpeed; 

    public Computer(String ip, Integer L2CacheSize, Integer L2CacheSpeed) { 
     this.ip = ip; 
     this.L2CacheSize = L2CacheSize; 
     this.L2CacheSpeed = L2CacheSpeed; 
    } 

    //Getters and Setters... 

} 
+0

У меня не было этой проблемы при выполнении тех же действий над классом, который содержал гораздо более простые имена переменных. Разве это честно, просто Джексон ищет конкретные имена переменных Верблюда? – Shiri

+1

Да, поскольку я указал, что Джексон использует соглашения о присвоении имен Java-бобам, это имя должно быть верблюжьим футляром, и есть и другие правила, но тот, который вы нарушаете, является верблюжьим футляром, если вы назовете ваши переменные, такие как l2CacheSize, он должен работать без аннотация –

+0

Это кажется ужасно разработанным ИМХО, поскольку он по существу превращает уже определенное имя переменной в неправильное. Не имеет смысла, что у него не было бы явного определения свойства как обязательного в этом случае, так как молчание в соответствии с соглашениями об именах просто кажется ошибочным, запутанным и неправильным. Спасибо за вашу помощь. – Shiri

-2

Просто установите DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES ложь.

ObjectMapper mapper = new ObjectMapper(); 
mapper.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false); 
WmiData data = mapper.readValue(jsonString, WmiData.class); 
Смежные вопросы