【Golang】格式化JSON字符串,方便查看


分别介绍golang及Python格式化接口返回JSON数据的方法,及Python json.dumps方法出现NameError: name 'true' is not defined原因解析及解决方案介绍。

格式化JSON字符串

我们经常会遇到接口返回的字符串类型的JSON数据,在其中查找数据的时候很不方便,所以一般会选择将他们格式化,在python中我们通常会使用json.dumps方法来格式化数据,其实golang中也有类似的方法--json.Indent,我们一起来看实例。

{"args": {},"headers": {"Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8","Accept-Encoding": "gzip, deflate","Accept-Language": "zh-CN,zh;q=0.9","Connection": "close","Host": "httpbin.org","Upgrade-Insecure-Requests": "1","User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_13_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/69.0.3497.100 Safari/537.36"},"origin": "103.*.*.*","url": "http://httpbin.org/get"}

Golang实现

package main

import (
	"bytes"
	"encoding/json"
	"fmt"
)

func main() {
	data := `{"args": {},"headers": {"Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8","Accept-Encoding": "gzip, deflate","Accept-Language": "zh-CN,zh;q=0.9","Connection": "close","Host": "httpbin.org","Upgrade-Insecure-Requests": "1","User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_13_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/69.0.3497.100 Safari/537.36"},"origin": "103.*.*.*","url": "http://httpbin.org/get"}`

	var str bytes.Buffer
	_ = json.Indent(&str, []byte(data), "", "    ")
	fmt.Println("formated: ", str.String())
	fmt.Println("data: ", data)
}

实际效果

python实现

参考代码

import json

data = '{"args": {},"headers": {"Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8","Accept-Encoding": "gzip, deflate","Accept-Language": "zh-CN,zh;q=0.9","Connection": "close","Host": "httpbin.org","Upgrade-Insecure-Requests": "1","User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_13_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/69.0.3497.100 Safari/537.36"},"origin": "103.*.*.*","url": "http://httpbin.org/get"}'
print(json.dumps(eval(data), indent=4))

局限

其实上面的的Python实现有一定的局限性,因为在Python当中是不存在true/false/null这样的标准json参数的,取而代之的是True/ False/None ,这就回导致一个问题,如果接口返回的数据中含有true/false/null,直接使用eval进行转化会出现比如:NameError: name 'true' is not defined这样的错误,那么怎么解决呢?

其实答案就是前面的藐视中:true/false/null是标准的JSON格式,那么我们便先把数据转化为JSON,再进行格式化即可:

json.dumps(json.loads(data), indent=4, ensure_ascii=False)

解释:ensure_ascii会保留中文而非转化为Unicode码,即\uxxxx形式

当然,如果大家使用的是requests库,接口返回的数据中已经携带了,可以直接调用其已经为返回结果(Response类)封装好的的json()方法:

import requests
import json

resp = requests.get("http://httpbin.org/get")
print(json.dumps(resp.json(), indent=4))

其实它最后也是调用的json.loads()

总结

  • JSON格式化,ensure_ascii
  • resp.json()
  • 当然,我们在命令行中也可以格式化Json 标准输出数据:
curl  http://xxx |python -m json.tool