使用 LinkedTreeMap 从 Json 字符串中删除键值对(嵌套在任何级别)

Remove the key-value pairs (nested at any level) from a Json String using LinkedTreeMap

我有一个 Json String 表示一个对象,该对象还有另一个嵌套对象。另外,我有一个键列表,我需要从 Json String 中删除这些键。这些键可以位于此字符串内的任何嵌套对象级别。最后,我需要将这个编辑后的 ​​Json 字符串与另一个字符串进行比较并输出差异。我需要从第一个 Json 字符串中删除那些键值对,因为我需要在比较过程中忽略这些键。目前,我正在将 Json 字符串转换为 Gson API 提供的 LinkedTreeMap,然后进行 Map.difference() 比较。请提出解决方案。

我通过在 Nested LinkedTreeMap 中递归遍历直到找到该字段并将其删除(如果存在)来完成此操作。需要提供 Key 的完整路径以获取对象内的确切键值位置(如下面 Json 示例中的 "objects.desc"从 Json 字符串中删除 desc)

Json 样本:

{
    "message": "MSG",
    "code": "COD001",
    "objects": [
        {
            "resource": "Student",
            "field": "StudentId",
            "desc": "Student Description"
        }
    ]
}

代码示例:

public MapDifference<String, Object> getMapDifference(String jsonString1, String jsonString2) {
    MapDifference<String, Object> mapDifference = null;
    Gson gson = new Gson();
    Type mapType = new TypeToken<Map<String, Object>>() {
    }.getType();
    Map<String, Object> firstMap = gson.fromJson(jsonString1, mapType);
    Map<String, Object> secondMap = gson.fromJson(jsonString2, mapType);
    firstMap = CollectionUtils.isEmpty(firstMap) ? new HashMap<>() : firstMap;
    secondMap = CollectionUtils.isEmpty(secondMap) ? new HashMap<>() : secondMap;
    //This contains the List of keys that is required to be filtered out from Json Strings before comparision like {"message", "objects.desc"}
    List<String> firstIgnoreList = getIgnoreList1();
    List<String> secondIgnoreList = getIgnoreList2();

    filterKeys(firstMap, firstIgnoreList);
    filterKeys(secondMap, secondIgnoreList);

    mapDifference = Maps.difference(firstMap, secondMap);
    return mapDifference;
  }


private void filterKeys(Map<String, Object> keyMap, List<String> ignoreList) {
    if (!(CollectionUtils.isEmpty(keyMap) || CollectionUtils.isEmpty(ignoreList))) {
        ignoreList.stream().parallel().forEach(key -> recursiveRemove(keyMap, key));
    }
  }

private static void recursiveRemove(Map<String, Object> keyMap, String key) {
    List<String> path = Arrays.asList(StringUtils.split(key.trim(), "."));
    int size = path.size();
    int index = 0;
    List<LinkedTreeMap> treeMapList = new ArrayList<LinkedTreeMap>();
    treeMapList.add((LinkedTreeMap) keyMap);
    while (index != size - 1) {
      int i = index++;
      List<LinkedTreeMap> treeMapListTemp = new ArrayList<LinkedTreeMap>();
      treeMapList.stream().parallel().forEach(treeMap -> {
        Object obj = treeMap.get(path.get(i));
        if (obj instanceof List) {
          treeMapListTemp.addAll((List<LinkedTreeMap>) obj);
        } else if (obj instanceof LinkedTreeMap) {
          treeMapListTemp.add((LinkedTreeMap) obj);
        }
      });
      treeMapList = treeMapListTemp;
    }
    treeMapList.stream().parallel().forEach(treeMap -> treeMap.remove(path.get(size - 1)));
  }