java - Jackson Recursive Parsing into Map or List - Stack Overflow

I have a JSON input where a given field can either be an ObjectNode or ArrayNode. I have a custom deser

I have a JSON input where a given field can either be an ObjectNode or ArrayNode. I have a custom deserializer that "works" but I'm looking to find out if Jackson provides an easier way.

The "data" field of the array can be ObjectNode or ArrayNode.In addition, the fields within can also be ObjectNode or ArrayNode.

Here are some examples of JSON needing to be parsed:

ObjectNode:

{
  transactionType: "A2I",
  transactionId: 4321,
  data: {
    field1: "value",
    field2: "value"
  }
}

ArrayNode

{
  transactionType: "BXX",
  transactionId: 4322,
  data: [{
    field1: "value",
    field2: "value"
  }]
}

Finally:

{
  transactionType: "C43",
  transactionId: 4322,
  data: [{
    field1: ["value"],
    field2: {
        subfield1: "value"
    }
  }]
}

The fields need to derserialize ito either ArrayList or Map<String, Object>. I do not need to map POJOs.

As I said, I have the custom deserializer, but if Jackson can deal with this case easily, I don't want to go the custom route.

I have a JSON input where a given field can either be an ObjectNode or ArrayNode. I have a custom deserializer that "works" but I'm looking to find out if Jackson provides an easier way.

The "data" field of the array can be ObjectNode or ArrayNode.In addition, the fields within can also be ObjectNode or ArrayNode.

Here are some examples of JSON needing to be parsed:

ObjectNode:

{
  transactionType: "A2I",
  transactionId: 4321,
  data: {
    field1: "value",
    field2: "value"
  }
}

ArrayNode

{
  transactionType: "BXX",
  transactionId: 4322,
  data: [{
    field1: "value",
    field2: "value"
  }]
}

Finally:

{
  transactionType: "C43",
  transactionId: 4322,
  data: [{
    field1: ["value"],
    field2: {
        subfield1: "value"
    }
  }]
}

The fields need to derserialize ito either ArrayList or Map<String, Object>. I do not need to map POJOs.

As I said, I have the custom deserializer, but if Jackson can deal with this case easily, I don't want to go the custom route.

Share Improve this question asked Mar 4 at 11:19 JasonJason 4,17716 gold badges72 silver badges113 bronze badges 5
  • I don't think this scenario can be solved simply with configurations on the ObjectMapper or with annotations. A custom deserializer seems to be the only way, given the unpredictable nature of the JSON. – dani-vta Commented Mar 4 at 11:40
  • Fair enough. I'm just trying to make sure whoever replaces me in the future doesn't think I'm an idiot because there was an easier way. – Jason Commented Mar 4 at 11:58
  • Is there another field in the json which defines what "shape" it will be (eg maybe the transactionType)? Perhaps you could use polymorphic-deserialization – lance-java Commented Mar 4 at 12:00
  • Unfortunately not. There a about 100 transaction types, and we don't have time to define POJOs for all of them. – Jason Commented Mar 4 at 12:11
  • Do you want to transform a JSON string directly into another structure of JSON string according to the transactionType value? – Raymond Choi Commented Mar 4 at 17:31
Add a comment  | 

2 Answers 2

Reset to default 1

You could just declare the data field as TreeNode then do further logic in your application

public class Transaction {
   private String transactionType;
   private Long transactionId;
   private TreeNode data;

   // constructor / getters
}
public class MyService {
   private final ObjectMapper mapper = new ObjectMapper();

   public void doStuff(String json) {
      Transaction transaction = mapper.readValue(json, Transaction.class);
      TreeNode data = transaction.getData();
      if (data.isArray()) {
         for (int i = 0; i < data.size(); ++i) {
            processDataNode(data.get(i));
         }
      } else {
         processDataNode(data);
      }
   }

   private void processDataNode(TreeNode dataNode) {
      if (dataNode.isObject()) {
         Map<String, Object> mapValue = mapper.treeToValue(dataNode, Map.class);
         ...
      } else if (dataNode.isValueNode()) {
         String stringValue = dataNode.asText();
         ...
      } else { 
         ...
      }
   }
}

Since the data node can be anything ,can it be checked for the identifier of data and its before or after characters ,so if you put that json in and as a string you can just check for the data keyword and create a string pattern according to what node it is like data :{ or data:[{ ,this might take more computational time because inside the subfields can be those arraynode or object nodes too

发布者:admin,转转请注明出处:http://www.yc00.com/questions/1745047357a4608181.html

相关推荐

  • java - Jackson Recursive Parsing into Map or List - Stack Overflow

    I have a JSON input where a given field can either be an ObjectNode or ArrayNode. I have a custom deser

    7小时前
    20

发表回复

评论列表(0条)

  • 暂无评论

联系我们

400-800-8888

在线咨询: QQ交谈

邮件:admin@example.com

工作时间:周一至周五,9:30-18:30,节假日休息

关注微信