如何将Json请求中的Unicode值转换为简单字符?

时间:2018-12-06 16:21:45

标签: java json unicode json-rpc

有时,客户端将Json值作为单线符号发送Json-RPC请求。 示例:

{ "jsonrpc": "2.0", "method": "add", "params": { "fields": [ { "id": 1, "val": "\u0414\u0435\u043d\u0438\u0441" }, { "id": 2, "val": "\u041c\u043e\u044f" } ] }, "id": "564b0f7d-868a-4ff0-9703-17e4f768699d" }

如何处理Json-RPC请求:

  1. 我的服务器收到byte[]之类的请求;
  2. 将其转换为io.vertx.core.json.JsonObject;
  3. 进行一些操作;
  4. 保存到数据库;

我在数据库记录中发现:

"val": "\u0414\u0435\u043d\u0438\u0441"

这是这个故事中最糟糕的。如果客户尝试搜索此数据,他将得到:

"val": "\\u0414\\u0435\\u043d\\u0438\\u0441"

所以我认为,我需要在反序列化到JsonObject之前转换请求数据。 我尝试了,但没有帮助:

String json = new String(incomingJsonBytes, StandardCharsets.UTF_8);
return json.getBytes(StandardCharsets.UTF_8);

我也尝试使用StandardCharsets.US_ASCII

注意:我无法使用StringEscapeUtils.unescapeJava()的变体,因为它会取消转义所有必要和不必要的'\'符号。

如果有人知道如何解决?还是已经做到的图书馆? 非常感谢。

1 个答案:

答案 0 :(得分:3)

io.vertx.core.json.JsonObject取决于Jackson ObjectMapper来执行实际的JSON反序列化(例如,io.vertx.core.json.Json有一个ObjectMapper字段)。默认情况下,杰克逊会将\u0414\u0435\u043d\u0438\u0441转换为Денис。您可以使用简单的代码段进行验证:

String json = "{ \"jsonrpc\": \"2.0\", \"method\": \"add\", \"params\": { \"fields\": [ { \"id\": 1, \"val\": \"\\u0414\\u0435\\u043d\\u0438\\u0441\" }, { \"id\": 2, \"val\": \"\\u041c\\u043e\\u044f\" } ] }, \"id\": \"564b0f7d-868a-4ff0-9703-17e4f768699d\" }";
ObjectMapper mapper = new ObjectMapper();
Map map = mapper.readValue(json, Map.class);
System.out.println(map); // {jsonrpc=2.0, method=add, params={fields=[{id=1, val=Денис}, {id=2, val=Моя}]}, id=564b0f7d-868a-4ff0-9703-17e4f768699d}

由于您的示例值正确反序列化,因此客户端很可能正在发送其他内容。也许是翻倍的\\u0414\\u0435\\u043d\\u0438\\u0441值,杰克逊将其转换为\u0414\u0435\u043d\u0438\u0441,从而消除了一层逃逸现象?

没有魔术解决方案。编写您自己的Jackson反序列化配置,或者使客户端停止发送垃圾。