繁体   English   中英

JSON到Java Objects,是建模json流的最佳实践

[英]JSON to Java Objects, best practice for modeling the json stream

我有一个JSON流由当前正在开发的服务器端C ++程序生成。 我已经得到了一个结果JSON的样本,我担心我将不得不手工解析json,我将无法使用GSON或Jackson等工具提供的普通类映射。

请看一下他们提供的以下(有些)人为的例子。 我关注的部分是具有不同参数的元数据“serie”数组。 键 - “键”例如仅存在于一个数组元素中。 这不会导致尝试将此数组映射到特定类的集合时出现问题吗?

最后,我担心“点”对象不相似。 我对JSON(作为一个老式的java swing开发人员)的理解非常有限,但“点”键值对可以不同的事实 - 是一个问题。

这个json流的整个想法是描述一个表,显示进度的方法,并提供一种从底层硬件中寻求“更多”的机制。 此外,如果您想知道为什么,我将与瘦客户端(HTML浏览器)共享此数据流。

所以我更正确,这不会轻易转换为java对象?

{
  "abort": "abort;session=sessionname",
  "data": {
    "metadata": [
      {
        "protocol": "HTTP",
        "serie": [
          {
            "name": "k1",
            "description": "xDR ID",
            "tooltip": "ASDR Unique Identifier - UiD",
            "type": "int64",
            "key": "1"
          },
          {
            "name": "c1",
            "description": "Answered",
            "tooltip": "Request with Response",
            "type": "bool"
          },
          {
            "name": "c2",
            "description": "Active",
            "tooltip": "Session status: active or closed/down",
            "type": "bool"
          }
        ]
      },
      {
        "protocol": "DNS",
        "serie": [
          {
            "name": "k1",
            "description": "xDR ID",
            "tooltip": "ASDR Unique Identifier - UiD",
            "type": "int64",
            "key": "1"
          },
          {
            "name": "k2",
            "description": "Transaction ID",
            "type": "int64",
            "key": "1",
            "display": "number"
          },
          {
            "name": "k3",
            "description": "Client",
            "tooltip": "Source IP Address",
            "type": "string",
            "key": "1",
            "display": "ip"
          }
        ]
      }
    ],
    "summary": [
      {
        "timestamp": "1331192727",
        "protocol": "HTTP",
        "activity": "www.google.com",
        "results": "OK",
        "point": {
          "k1": "1",
          "c1": "true",
          "c2": "true"
        }
      },
      {
        "timestamp": "1331192727",
        "protocol": "DNS",
        "activity": "www.google.com",
        "results": "OK",
        "point": {
          "k1": "1",
          "k2": "1.1.4.229"
        }
      }
    ]
  },
  "progress": {
    "perc": "100"
  },
  "more": "13,39,1331192727,1331192760,27236,1.1.4.229,limit=1000,session=sessionname"
}

感谢您提供的任何建议。

-D Klotz

使用GSON,假设您要反序列化的类具有JSON中出现的所有名称的字段,则JSON中找不到的字段将保留为null:

https://sites.google.com/site/gson/gson-user-guide#TOC-Finer-Points-with-Objects

“在反序列化时,JSON中缺少的条目导致将对象中的相应字段设置为null”

如果JSON中允许任意字段名称,事情会变得复杂一些 - 例如,如果Point允许c1,c2,... cn。 但您可以使用自定义反序列化器来处理此问题。

https://sites.google.com/site/gson/gson-user-guide#TOC-Writing-a-Deserializer

编辑:

以下是为Point编写自定义反序列化器的方法:

private class DateTimeDeserializer implements JsonDeserializer<Point> {
    public Point deserialize(JsonElement json, Type typeOfT, 
            JsonDeserializationContext context) throws JsonParseException {
        List<PointPart> parts = Lists.newArrayList();

        for(Map.Entry<String,JsonElement> entry : 
                json.getAsJsonObject().entrySet()) {
            char type = ;
            int index = Integer.parseInt(entry.getKey().substring(1)) - 1;

            while(parts.size() <= index) {
                parts.add(new PointPart());
            }

            PointPart part = parts.get(index);
            switch(entry.getKey().charAt(0)) {
            case 'c':
                part.c = entry.getValue().getAsBoolean();
                break;
            case 'k':
                part.k = entry.getValue().getAsInt();
                break;
            }
        }

        return new Point(parts);
    }
}

class Point {
    List<PointPart> parts;

    Point(List<PointPart> parts) {
        this.parts = parts;
    }
}

class PointPart {
    boolean c;
    int k;
}

我更关心的是数据流中的元数据字段。 顶级“中止”和“更多”属性看起来像某种结构化字符串,您可能需要解析它们? 除此之外,您只需要使用从外部程序发送的最广泛的字段集来为每个Java对象建模。 您不必担心传输的数据是否缺少一个或多个字段,大多数JSON库只会在这种情况下反序列化null。 此外,大多数JSON库还允许您指定要忽略未知的传入字段。

因此,在为缺少字段反序列化null和忽略额外字段之间,您应该很好地进行解析。

不,这不是特别难以反序列化为Java对象。 JSON没有很多关于键入除基元之外的信息的线索。 通过查看要反序列化的对象或让用户提供要反序列化的对象,可以恢复对丢失类型信息的大多数担忧。 这正是flexjson的工作方式,并且您可以在每个点定义如何反序列化它。 它为大多数问题提供了合理的默认值,但您始终可以在JSON流中将ObjectFactory附加到特定的类或路径。

http://flexjson.sourceforge.net

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM