JQ无法解析Unicode表情符号字符。它是有效的JSON吗?

时间:2017-02-25 14:39:06

标签: json unicode clojure standards jq

我有一个JSON文件,其中包含来自Clojure< data.json库的JSON。数据来自Twitter,人们似乎对此微笑。

$ cat /tmp/myfile | jq .

我明白了:

parse error: Invalid \uXXXX\uXXXX surrogate pair escape at line 1, column 14862268

违规部分是:

$ cut -c 14862258-14862269 /tmp/2017-02-23-2
79-7\ud83d",

所以,这个转义代码是在真正的JSON文件中找到的,JQ无法读取它。

echo '"\ud83d"' | jq .

Fileformat.info seems to suggest它应该成对出现:

SMILING FACE WITH OPEN MOUTH
"\uD83D\uDE03"
  1. 这是否真的是在JSON文件中找到的无效字符?我的JSON在技术上是无效的吗?

  2. 是否有一个简单的实用程序,我可以通过管道数据在JQ之前删除这些字符?或者我可以让JQ放松它解释吗?

2 个答案:

答案 0 :(得分:4)

JSON specification说:

  

字符串是零个或多个Unicode字符的序列[UNICODE]。

从这个意义上讲,字符串“\ ud83d”无效JSON("+UD83D is not a valid Unicode character"),即使它符合JSON ABNF。正如标准文件所说,字符串规范与ABNF之间存在差异:

  

本规范中的ABNF允许成员名称和      字符串值包含不能编码Unicode的位序列      字符;例如,“\ uDEAD”(单个未配对的UTF-16      代孕)。例如,在何时观察到这种情况      库会截断UTF-16字符串而不检查是否存在      截断分割代理对。软件的行为      收到包含这些值的JSON文本是不可预测的......

所以说:

  1. “\ uD83D”不是严格有效的JSON,即使它符合ABNF;

  2. jq在此权限范围内;

  3. jsonlint接受“\ uD83D”是错误的。

答案 1 :(得分:2)

它绝对是有效的json,但代码单元D83D本身无效。请记住,jq不只是解释json,而是试图获得它的价值。所以这不仅仅是json消耗的json中存储的字符流,它是一个具有明确值的字符串。

这个值是一个高代理,它必须成对出现,你的输入显然没有。因此,文件中编码的字符串虽然是有效的json,但并不代表jq尝试解析的有效unicode字符串。

如果你想使用jq解析它,你需要浏览你的json并完成这对。

如果你至少可以确保它是有效的json,你可以使用正则表达式来扫描数据以搜索不匹配的代理。像这样:

\\u[Dd][89ABab][0-9A-Fa-f]{2}(?!\\u[Dd][C-Fc-f][0-9A-Fa-f]{2})
|
(?<!\\u[Dd][89ABab][0-9A-Fa-f]{2})\\u[Dd][C-Fc-f][0-9A-Fa-f]{2}

然后你可以将它们脱掉或者对失踪的代理进行最好的猜测。