2014-12-03 7 views
2

Мне нужно десериализовать объект JSON, содержащий другой объект JSON (как String) в качестве значения. Каков наилучший способ достичь этого (без создания экземпляра объекта mapper внутри getter для десериализации внутреннего объекта класса, который занимает от 50 до 100 мс на устройствах Android). Я использую аннотации Джексона, поэтому аннотирование для достижения того, что я хочу, является предпочтительным.JSON deserialisation с Jackson

upd. Я ожидаю решения на основе аннотаций. Что-то вроде

@JsonDeserialize(String as MyCustomObject) 

, который был бы равен

MyCustomObject myCustomObject = mapper.readValue(string, MyCustomObject.class) 
+1

Может быть, с помощью настраиваемого десериализации. См. Http://stackoverflow.com/questions/5269637/custom-deserialization-of-json-field-with-jackson-in-java –

+0

@andresoviedo, я обновил свой вопрос. – localhost

+1

Когда вы ожидаете обработки этих аннотаций? – sviklim

ответ

1

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

Вот пример:

public class JacksonInjectObjectMapper { 

    private static final String JSON = 
      "{\"field1\":\"{\\\"field0\\\":\\\"value0\\\"}\", " + 
      "\"field2\":\"value2\"}"; 

    public static class Foo { 
     public String field0; 

     @Override 
     public String toString() { 
      return "Foo{" + 
        "field0='" + field0 + '\'' + 
        '}'; 
     } 
    } 

    public static class Bean { 
     @JsonDeserialize(using = FooDeserializer.class) 
     public Foo field1; 
     public String field2; 

     @Override 
     public String toString() { 
      return "Bean{" + 
        "field1=" + field1 + 
        ", field2='" + field2 + '\'' + 
        '}'; 
     } 
    } 

    public static class FooDeserializer extends JsonDeserializer<Foo> { 

     @Override 
     public Foo deserialize(
       final JsonParser jp, final DeserializationContext ctxt) 
       throws IOException { 
      final ObjectMapper mapper = (ObjectMapper) ctxt.findInjectableValue(
        ObjectMapper.class.getName(), 
        null, 
        null); 
      final String json = jp.getValueAsString(); 
      System.out.println(json); 
      return mapper.readValue(json, Foo.class); 
     } 
    } 

    public static void main(String[] args) throws IOException { 
     final ObjectMapper mapper = new ObjectMapper(); 
     final InjectableValues.Std injectableValues = new InjectableValues.Std(); 
     injectableValues.addValue(ObjectMapper.class, mapper); 
     mapper.setInjectableValues(injectableValues); 

     final Bean bean = mapper.readValue(JSON, Bean.class); 
     System.out.println(bean); 
    } 
} 

Выход:

{"field0":"value0"} 
Bean{field1=Foo{field0='value0'}, field2='value 
+0

мой класс «Bean» содержит много других объектов JSON, поэтому однострочный конструктор не является решением. – localhost

+0

@localhost Я вижу. Я обновил свой ответ на примере пользовательского десериализатора, который повторно использует экземпляр mapper объекта. –

+0

это именно то, что мне нужно! – localhost