json_encode 处理中文和链接

接口开发中我们常用 json 传输数据,因为它相比 xml 更轻量、简洁,而且在 PHP 下将多维数组转为 json 字符串十分方便,只需要使用 json_encode 方法编码即可。

假设把一个数组用 json 格式存储到日志文件中,内容如下:

1
2
3
4
$log = array(
'status' => 1,
'error' => '请求失败,详见 http://ccbaba.cn/',
);

如果直接 json_encode 并输出:

1
2
3
echo json_encode($log);
// 输出结果如下:
{"status":1,"error":"\u8bf7\u6c42\u5931\u8d25\uff0c\u8be6\u89c1 http:\/\/ccbaba.cn\/"}

显然这样的日志存储起来,要查看的时候还得 json_decode 才能让人看明白,不够清晰明朗。
不过只要稍加处理就能直接让人看懂:

1
2
3
echo json_encode($log, JSON_UNESCAPED_UNICODE);
// 输出结果如下:
{"status":1,"error":"请求失败,详见 http:\/\/ccbaba.cn\/"}

注意,这里使用了常量 JSON_UNESCAPED_UNICODE 使编码的时候保留 Unicode。
这个常量需要 PHP 5.4 及以上的版本。

接下来我们看到,链接中的“/”被转义成“\/”,链接若是太长还是比较难看的。
可以使用常量 JSON_UNESCAPED_SLASHES 保留“/”。
这个常量也需要 PHP 5.4 及以上的版本。

1
2
3
4
echo json_encode($log, JSON_UNESCAPED_UNICODE|JSON_UNESCAPED_SLASHES);
// 两个常量之间用“|”隔开,表示同时使用这些常量。
// 输出结果如下:
{"status":1,"error":"请求失败,详见 http://www.baidu.com/"}
现在 json_encode 输出的信息就可以既简短又好看了。


附录(摘自PHP 手册):
你可以在 json_encode 的第二个参数使用更多常量

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
// 所有的 < 和 > 转换成 \u003C 和 \u003E。 自 PHP 5.3.0 起生效。
JSON_HEX_TAG (integer)
// 所有的 & 转换成 \u0026。 自 PHP 5.3.0 起生效。
JSON_HEX_AMP (integer)
// 所有的 ' 转换成 \u0027。 自 PHP 5.3.0 起生效。
JSON_HEX_APOS (integer)
// 所有的 " 转换成 \u0022。 自 PHP 5.3.0 起生效。
JSON_HEX_QUOT (integer)
// 使一个非关联数组输出一个类(Object)而非数组。 在数组为空而接受者需要一个类(Object)的时候尤其有用。 自 PHP 5.3.0 起生效。
JSON_FORCE_OBJECT (integer)
// 将所有数字字符串编码成数字(numbers)。 自 PHP 5.3.3 起生效。
JSON_NUMERIC_CHECK (integer)
// 用空白字符格式化返回的数据。 自 PHP 5.4.0 起生效。
JSON_PRETTY_PRINT (integer)
// 不要编码 /。 自 PHP 5.4.0 起生效。
JSON_UNESCAPED_SLASHES (integer)
// 以字面编码多字节 Unicode 字符(默认是编码成 \uXXXX)。 自 PHP 5.4.0 起生效。
JSON_UNESCAPED_UNICODE (integer)