在使用 Python 做 Redis 开发时,发现 Python 自带的序列化都不太好用,对于复杂的数据结构的处理都不到位,经过领导推荐,开始使用 MessagePack 进行序列化编程。它是一个跨语言工具,支持十几种语言,在传输数据上号称比 JSON 更小更快。
本文以 Python 为例简单介绍
下载
1 | $ pip install msgpack-python |
Hello World
MessagePack 的序列化方法很简单 packb()
,反序列 unpackb()
1
2
3
4
5
6
7In [1]: import msgpack
In [2]: msgpack.packb('Hello World') # 序列化
Out[2]: b'\xabHello World'
In [3]: msgpack.unpackb(msgpack.packb('Hello World')) # 反序列
Out[3]: b'Hello World'
反序列后输出结果依然是字节数组类型,这不是我们想要的,想要得到字符串类型,我们需要用到 encoding
参数1
2In [4]: msgpack.unpackb(msgpack.packb('Hello World'), encoding='utf-8')
Out[4]: 'Hello World'
JSON
1 | In [10]: msgpack.unpackb(msgpack.packb({"name": "wxnacy"}), encoding='utf-8') |
简单的 JSON 数据直接使用即可,但是如果 JSON 中的数据类型比较特殊,比如 datetime
就会有点麻烦1
2
3
4
5
6
7
8
9
10
11
12#!/usr/bin/env python
# -*- coding:utf-8 -*-
# Author: wxnacy([email protected])
import msgpack
from datetime import datetime
useful_dict = {
"id": 1,
"created": datetime.now(),
}
packed_dict = msgpack.packb(useful_dict)
1 | TypeError: can't serialize datetime.datetime(2017, 12, 25, 21, 26, 48, 277551) |
如上,直接进行序列化会报错,此时需要教给它怎么处理这种类型1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24#!/usr/bin/env python
# -*- coding:utf-8 -*-
# Author: wxnacy([email protected])
import msgpack
from datetime import datetime
useful_dict = {
"id": 1,
"created": datetime.now(),
}
def decode_datetime(obj):
if '__datetime__' in obj:
obj = datetime.strptime(obj["as_str"], "%Y%m%dT%H:%M:%S.%f")
return obj
def encode_datetime(obj):
if isinstance(obj, datetime):
return {'__datetime__': True, 'as_str': obj.strftime("%Y%m%dT%H:%M:%S.%f")}
return obj
packed_dict = msgpack.packb(useful_dict, default=encode_datetime)
this_dict_again = msgpack.unpackb(packed_dict, object_hook=decode_datetime,
encoding='utf-8')
通过 default
和 object_hook
分别制定序列和反序列的解析方法,通过上边这个例子,我们照葫芦画瓢把其他它不能识别的类都解析出来。