2017-02-21 23 views
0

Я не уверен, как десериализации массив, содержащий простой strings.I'm пытается проанализировать следующие JSONдесериализации JSON массив

{ 
    "state":"RT", 
    "testMethod":"electronic", 
    "testElements":[ 
     { 
     "testId":[ 
      "UT_ITXref", 
      "Fed_ITXref" 
     ] 
     }, 
     "testStartDate", 
     "testEndDate", 
     "testDueDate" 
    ] 
} 

Я получаю следующее сообщение об ошибке:

com.fasterxml.jackson.databind.JsonMappingException: Can not construct instance of com.test.rules.model.TestElements: no String-argument constructor/factory method to deserialize from String value ('testStartDate') 
at [Source: {"state":"RT","testMethod":"electronic","testElements":[{"testId":["UT_ITXref","Fed_ITXref"]},"testStartDate","testEndDate","testDueDate"}]}; line: 1, column: 247] (through reference chain: com.test.rules.model.TestRules["testElements"]->java.lang.Object[][1]) 
    at com.fasterxml.jackson.databind.JsonMappingException.from(JsonMappingException.java:270) 
    at com.fasterxml.jackson.databind.DeserializationContext.instantiationException(DeserializationContext.java:1456) 
    at com.fasterxml.jackson.databind.DeserializationContext.handleMissingInstantiator(DeserializationContext.java:1012) 
    at com.fasterxml.jackson.databind.deser.ValueInstantiator._createFromStringFallbacks(ValueInstantiator.java:370) 
    at com.fasterxml.jackson.databind.deser.std.StdValueInstantiator.createFromString(StdValueInstantiator.java:315) 
    at com.fasterxml.jackson.databind.deser.BeanDeserializerBase.deserializeFromString(BeanDeserializerBase.java:1282) 
    at com.fasterxml.jackson.databind.deser.BeanDeserializer._deserializeOther(BeanDeserializer.java:159) 
    at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserialize(BeanDeserializer.java:150) 
    at com.fasterxml.jackson.databind.deser.std.ObjectArrayDeserializer.deserialize(ObjectArrayDeserializer.java:196) 
    at com.fasterxml.jackson.databind.deser.std.ObjectArrayDeserializer.deserialize(ObjectArrayDeserializer.java:20) 
    at com.fasterxml.jackson.databind.deser.SettableBeanProperty.deserialize(SettableBeanProperty.java:499) 
    at com.fasterxml.jackson.databind.deser.BeanDeserializer._deserializeWithErrorWrapping(BeanDeserializer.java:511) 
    at com.fasterxml.jackson.databind.deser.BeanDeserializer._deserializeUsingPropertyBased(BeanDeserializer.java:396) 
    at com.fasterxml.jackson.databind.deser.BeanDeserializerBase.deserializeFromObjectUsingNonDefault(BeanDeserializerBase.java:1198) 
    at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserializeFromObject(BeanDeserializer.java:314) 
    at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserialize(BeanDeserializer.java:148) 
    at com.fasterxml.jackson.databind.ObjectReader._bindAndClose(ObjectReader.java:1626) 
    at com.fasterxml.jackson.databind.ObjectReader.readValue(ObjectReader.java:1220) 

Вот что я сделал, я использовал @JsonCreator аннотацию десериализовать

public class TestRules { 

    private String state; 
    private String testMethod; 
    private TestElements[] testElements;  

    @JsonCreator 
     public TaxRules(
      @JsonProperty("state") String state,  
      @JsonProperty("testMethod") String testMethod,   
      @JsonProperty("testElements") TestElements[] testElements 
     ) { 
      this.state = state;   
      this.testMethod = testMethod;   
      this.testElements = testElements;   
     } 

} 

public class TestElements { 
    private List<String> testId; 
    private List<String> elements; 

    public List<String> getElements() { 
      return elements; 
     } 
     public void setElements(List<String> elements) { 
      this.elements = elements; 
     } 
     public List<String> getTestId() { 
      return testId; 
     } 
     public void setTestId(List<String> testId) { 
      this.testId = testId; 
     } 

} 

Должен ли я писать пользовательские десериализатор или Is есть способ, которым я могу использовать API Jackson для этого. Мы ценим любые предложения.

+3

'json', кажется, недействителен. Вы уверены, что 'testStartDate',' testEndDate' и т. Д. Не имеют значений? –

+1

либо json недействителен, либо классы, представляющие json, являются недопустимыми. Json отлично соответствует спецификации json; но похоже, что 'testElements' представляет собой смесь объектов и строк в json, но pojos ожидают только объекты определенной формы. – Atreys

+0

Возможно, вам понадобится создать собственный сериализатор, если ваш json правильный. http://stackoverflow.com/questions/40915356/json-deserialization-in-java-w-jackson-of-mixed-types-contained-in-one-array имеет аналогичную ситуацию, но с двумя разными типами объектов – Atreys

ответ

1

На самом деле ошибки сообщают что-то.

Парсер JSON обнаружил, что для свойства testElements существует массив объектов, но ваш Json-файл имеет смешанный контент.

первый элемент - объект (предположим, TestElement класс). Затем парсер создает этот объект с пустым конструктором и вызывает соответствующие настройки для своих свойств. но ...

второй, третий и четвертый элементы являются строками, поэтому ошибка говорит, что парсер пытается найти constrictor со String в качестве аргумента.

Итак, вы можете попробовать сделать этот конструктор в классе TestElement и посмотреть, будет ли он работать или нет ... Не забудьте также сохранить пустой конструктор.

Я не могу гарантировать, что он будет работать, но, по крайней мере, ошибка говорит об этом.

ОТВЕТ: Вы уверены, что ваш объект Json верен? но не что-то в этом роде?

{ 
"state":"RT", 
"testMethod":"electronic", 
"testElements":[ 
    { 
    "testId":[ 
     "UT_ITXref", 
     "Fed_ITXref" 
    ] 
    }], 
    "testStartDate":"01-01-2017", 
    "testEndDate":"01-02-2017", 
    "testDueDate":"01-03-2017" 
} 

Я немного смущен, потому что StartDate, EndDate, DueDate семантически выглядеть как тест атрибутов, а не в качестве элементов в массиве testElements

+0

Спасибо, я попробую с конструктором строковых аргументов. JSON, который я предоставил, является допустимым.Мне нужно передать этот json в другую службу, чтобы получить значения testElements. – PKR

+0

Строковый конструктор аргументов сделал трюк. Благодарю. – PKR

+0

Рад это услышать. Для меня это тоже ново, я буду иметь в виду, что это возможно с Джексоном. – Vadim

0
{ 
    "state": "RT", 
    "testMethod": "electronic", 
    "testElements": [ 
     { 
      "testId": [ 
       "UT_ITXref", // <-- this object is deserialized just fine 
       "Fed_ITXref" 
      ] 
     }, 
     "testStartDate",  // <-- this is where the error is happening 
     "testEndDate", 
     "testDueDate" 
    ] 
} 

ли вы собираетесь в JSON, чтобы быть истолковано, как если бы оно выглядел следующим образом?

{ 
    "state": "RT", 
    "testMethod": "electronic", 
    "testElements": [ 
     { 
      "testId": [ 
       "UT_ITXref", 
       "Fed_ITXref" 
      ] 
     }, 
     { 
      testId: [ 
       "testStartDate" 
      ] 
     }, 
     { 
      testId: [ 
       "testEndDate" 
      ] 
     }, 
     { 
      testId: [ 
       "testDueDate" 
      ] 
     } 
    ] 
} 

Если да, то вам нужно сделать пользовательский десериализатор обнаружить элемент в массиве является ли объект или строка. Если это строка, вы, вероятно, захотите сами построить TestElement.

+0

Спасибо за ваше время. К сожалению, это не сработает для меня. Я дал вам образец json. Фактический JSON имеет больше элементов разных объектов (например, testId) и строк. Попробует конструктор аргументов String, предложенный Вадимом, если он работает нормально, иначе я бы пошел на собственный сериализатор. – PKR

Смежные вопросы