快速、正确的Python JSON库,支持dataclasses、datetimes和numpy
项目描述
orjson
orjson 是一个快速、正确的Python JSON库。它在性能基准测试中被证明是Python中最快的JSON库,并且比标准json库或其他第三方库更准确。它可以原生序列化dataclass、datetime、numpy和UUID实例。
与其它Python JSON库相比,其特性和缺点
- 序列化
dataclass
实例的速度比其他库快40-50倍 - 将
datetime
、date
和time
实例序列化为RFC 3339格式,例如,“1970-01-01T00:00:00+00:00” - 以0.3倍其他库的内存使用率,将
numpy.ndarray
实例序列化速度快4-12倍 - 比标准库快10-20倍进行美化打印
- 序列化为
bytes
而不是str
,即不是直接替换 - 不转义Unicode为ASCII序列化
str
,例如,“好”而不是“\\u597d” - 序列化
float
比其他库快10倍,反序列化比其他库快一倍 - 原生序列化
str
、int
、list
和dict
的子类,需要使用default
指定如何序列化其他类型 - 使用
default
钩子序列化任意类型 - 具有严格的UTF-8兼容性,比标准库更正确
- 严格遵循JSON规范,不支持Nan/Infinity/-Infinity
- 在53位整数上具有严格的JSON兼容性,默认支持64位
- 不提供从/向文件对象读写操作的
load()
或dump()
函数
orjson支持CPython 3.8、3.9、3.10、3.11、3.12和3.13。它为Linux提供amd64/x86_64、aarch64/armv8、arm7、POWER/ppc64le和s390x的wheels,为macOS提供amd64和aarch64的wheels,为Windows提供amd64和i686/x86的wheels。orjson不支持也不将支持PyPy。orjson不支持也不将支持PEP 554子解释器。发布遵循语义版本控制,不通过opt-in标志序列化新的对象类型被视为破坏性变更。
orjson同时受Apache 2.0和MIT许可协议的约束。仓库和问题跟踪器位于github.com/ijl/orjson,补丁可以提交到那里。仓库中提供了一个变更日志。
用法
安装
要从PyPI安装wheel,请参阅
pip install --upgrade "pip>=20.3" # manylinux_x_y, universal2 wheel support
pip install --upgrade orjson
要构建wheel,请参阅打包。
快速入门
这是一个序列化示例,其中指定了选项,并进行了反序列化
>>> import orjson, datetime, numpy
>>> data = {
"type": "job",
"created_at": datetime.datetime(1970, 1, 1),
"status": "🆗",
"payload": numpy.array([[1, 2], [3, 4]]),
}
>>> orjson.dumps(data, option=orjson.OPT_NAIVE_UTC | orjson.OPT_SERIALIZE_NUMPY)
b'{"type":"job","created_at":"1970-01-01T00:00:00+00:00","status":"\xf0\x9f\x86\x97","payload":[[1,2],[3,4]]}'
>>> orjson.loads(_)
{'type': 'job', 'created_at': '1970-01-01T00:00:00+00:00', 'status': '🆗', 'payload': [[1, 2], [3, 4]]}
迁移
orjson版本3比版本2序列化更多类型。现在序列化了str
、int
、dict
和list
的子类。这比标准库更快,更相似。可以通过orjson.OPT_PASSTHROUGH_SUBCLASS
禁用。默认情况下,dataclasses.dataclass
实例会被序列化,并且在默认函数中不能自定义,除非指定了option=orjson.OPT_PASSTHROUGH_DATACLASS
。默认情况下,uuid.UUID
实例会被序列化。对于现在被序列化的任何类型,可以在default
函数中移除其实现和启用它们的选项,但不需要这么做。反序列化没有变化。
要从标准库迁移,最大的不同是orjson.dumps
返回bytes
,而json.dumps
返回一个str
。使用非str
键的dict
对象应指定option=orjson.OPT_NON_STR_KEYS
。sort_keys
被option=orjson.OPT_SORT_KEYS
替换。indent
被option=orjson.OPT_INDENT_2
替换,其他级别的缩进不受支持。
序列化
def dumps(
__obj: Any,
default: Optional[Callable[[Any], Any]] = ...,
option: Optional[int] = ...,
) -> bytes: ...
dumps()
将Python对象序列化为JSON。
它原生序列化str
、dict
、list
、tuple
、int
、float
、bool
、None
、dataclasses.dataclass
、typing.TypedDict
、datetime.datetime
、datetime.date
、datetime.time
、uuid.UUID
、numpy.ndarray
和orjson.Fragment
实例。它通过default
支持任意类型。它序列化str
、int
、dict
、list
、dataclasses.dataclass
和enum.Enum
的子类。为了避免序列化子类,指定选项orjson.OPT_PASSTHROUGH_SUBCLASS
。
输出是一个包含UTF-8的bytes
对象。
在调用期间,全局解释器锁(GIL)被持有。
在不受支持的类型上引发JSONEncodeError
。此异常消息描述了包含错误消息类型不是可JSON序列化的:...
的无效对象。要修复此问题,请指定默认值。
如果字符串包含无效的UTF-8,则引发JSONEncodeError
。
默认情况下,它会在超过64位或使用OPT_STRICT_INTEGER
时超过53位的整数上引发JSONEncodeError
。
如果字典的键类型不是str
,除非指定了OPT_NON_STR_KEYS
,否则将引发JSONEncodeError
。
如果default
的输出递归到default
处理超过254层,则引发JSONEncodeError
。
在循环引用上引发JSONEncodeError
。
如果datetime对象上的tzinfo
不受支持,则引发JSONEncodeError
。
JSONEncodeError
是TypeError
的子类。这是为了与标准库兼容。
如果失败是由default
中的异常引起的,则JSONEncodeError
将原始异常作为__cause__
链。
默认
要序列化子类或任意类型,指定default
为返回支持类型的可调用对象。default
可以是函数、lambda或可调用类实例。要指定类型未由default
处理,引发异常,例如TypeError
。
>>> import orjson, decimal
>>>
def default(obj):
if isinstance(obj, decimal.Decimal):
return str(obj)
raise TypeError
>>> orjson.dumps(decimal.Decimal("0.0842389659712649442845"))
JSONEncodeError: Type is not JSON serializable: decimal.Decimal
>>> orjson.dumps(decimal.Decimal("0.0842389659712649442845"), default=default)
b'"0.0842389659712649442845"'
>>> orjson.dumps({1, 2}, default=default)
orjson.JSONEncodeError: Type is not JSON serializable: set
default
可调用对象可以返回一个对象,该对象本身必须由default
处理,最多254次,然后引发异常。
如果类型无法处理,default
必须引发异常。否则,Python将隐式返回None
,这对于调用者看起来是一个合法的值,并且会被序列化。
>>> import orjson, json, rapidjson
>>>
def default(obj):
if isinstance(obj, decimal.Decimal):
return str(obj)
>>> orjson.dumps({"set":{1, 2}}, default=default)
b'{"set":null}'
>>> json.dumps({"set":{1, 2}}, default=default)
'{"set":null}'
>>> rapidjson.dumps({"set":{1, 2}}, default=default)
'{"set":null}'
选项
要修改数据序列化方式,指定option
。每个option
是orjson
中的整数常量。要指定多个选项,将它们掩码在一起,例如:option=orjson.OPT_STRICT_INTEGER | orjson.OPT_NAIVE_UTC
。
OPT_APPEND_NEWLINE
将\n
追加到输出。这是一个方便的优化,用于dumps(...) + "\n"
的模式。bytes
对象是不可变的,此模式会复制原始内容。
>>> import orjson
>>> orjson.dumps([])
b"[]"
>>> orjson.dumps([], option=orjson.OPT_APPEND_NEWLINE)
b"[]\n"
OPT_INDENT_2
使用两个空格的缩进格式化输出。这相当于标准库中的indent=2
。格式化打印较慢,输出较大。orjson是在格式化打印方面速度最快的库,比标准库慢得少得多。此选项与所有其他选项兼容。
>>> import orjson
>>> orjson.dumps({"a": "b", "c": {"d": True}, "e": [1, 2]})
b'{"a":"b","c":{"d":true},"e":[1,2]}'
>>> orjson.dumps(
{"a": "b", "c": {"d": True}, "e": [1, 2]},
option=orjson.OPT_INDENT_2
)
b'{\n "a": "b",\n "c": {\n "d": true\n },\n "e": [\n 1,\n 2\n ]\n}'
如果显示,缩进和换行符将看起来像这样
{
"a": "b",
"c": {
"d": true
},
"e": [
1,
2
]
}
这衡量了将github.json固定序列化为紧凑型(52KiB)或格式化型(64KiB)
库 | 紧凑型(ms) | 格式化型(ms) | 与orjson相比 |
---|---|---|---|
orjson | 0.03 | 0.04 | 1 |
ujson | 0.18 | 0.19 | 4.6 |
rapidjson | 0.1 | 0.12 | 2.9 |
simplejson | 0.25 | 0.89 | 21.4 |
json | 0.18 | 0.71 | 17 |
这衡量了将citm_catalog.json固定序列化为紧凑型(489KiB)或格式化型(1.1MiB),这更像是最坏的情况,因为嵌套和换行符的数量较多
库 | 紧凑型(ms) | 格式化型(ms) | 与orjson相比 |
---|---|---|---|
orjson | 0.59 | 0.71 | 1 |
ujson | 2.9 | 3.59 | 5 |
rapidjson | 1.81 | 2.8 | 3.9 |
simplejson | 10.43 | 42.13 | 59.1 |
json | 4.16 | 33.42 | 46.9 |
这可以使用pyindent
脚本来重现。
OPT_NAIVE_UTC
将没有tzinfo
的datetime.datetime
对象序列化为UTC。这不会影响设置了tzinfo
的datetime.datetime
对象。
>>> import orjson, datetime
>>> orjson.dumps(
datetime.datetime(1970, 1, 1, 0, 0, 0),
)
b'"1970-01-01T00:00:00"'
>>> orjson.dumps(
datetime.datetime(1970, 1, 1, 0, 0, 0),
option=orjson.OPT_NAIVE_UTC,
)
b'"1970-01-01T00:00:00+00:00"'
OPT_NON_STR_KEYS
序列化除str
类型以外的dict
键。这允许dict
键可以是以下类型之一:str
、int
、float
、bool
、None
、datetime.datetime
、datetime.date
、datetime.time
、enum.Enum
和uuid.UUID
。相比之下,标准库默认序列化str
、int
、float
、bool
或None
。orjson的基准测试表明,在序列化非str
键方面,orjson比其他库更快。对于str
键,此选项比默认选项慢。
>>> import orjson, datetime, uuid
>>> orjson.dumps(
{uuid.UUID("7202d115-7ff3-4c81-a7c1-2a1f067b1ece"): [1, 2, 3]},
option=orjson.OPT_NON_STR_KEYS,
)
b'{"7202d115-7ff3-4c81-a7c1-2a1f067b1ece":[1,2,3]}'
>>> orjson.dumps(
{datetime.datetime(1970, 1, 1, 0, 0, 0): [1, 2, 3]},
option=orjson.OPT_NON_STR_KEYS | orjson.OPT_NAIVE_UTC,
)
b'{"1970-01-01T00:00:00+00:00":[1,2,3]}'
这些类型通常按照它们作为值的序列化方式进行序列化,例如,datetime.datetime
仍然是RFC 3339字符串,并尊重影响它的选项。例外的是,int
序列化不尊重OPT_STRICT_INTEGER
。
此选项有创建重复键的风险。这是因为非str
对象可能序列化成与现有键相同的str
,例如,{"1": true, 1: false}
。最后插入到dict
中的键将被最后序列化,JSON反序列化器可能假定最后一个键的出现(在上面的例子中,是false
)。第一个值将会丢失。
此选项与orjson.OPT_SORT_KEYS
兼容。如果使用排序,请注意排序是不稳定的,对于重复键将是不可预测的。
>>> import orjson, datetime
>>> orjson.dumps(
{"other": 1, datetime.date(1970, 1, 5): 2, datetime.date(1970, 1, 3): 3},
option=orjson.OPT_NON_STR_KEYS | orjson.OPT_SORT_KEYS
)
b'{"1970-01-03":3,"1970-01-05":2,"other":1}'
这测量了序列化589KiB JSON的过程,其中包括一个包含100个dict
的list
,每个dict
都有365个随机排序的int
键,这些键表示纪元时间戳,以及一个str
键。对于“str keys”,在序列化之前将键转换为str
,并且orjson仍然指定option=orjson.OPT_NON_STR_KEYS
(这总是稍微慢一些)。
库 | str键(毫秒) | int键(毫秒) | 排序后的int键(毫秒) |
---|---|---|---|
orjson | 1.53 | 2.16 | 4.29 |
ujson | 3.07 | 5.65 | |
rapidjson | 4.29 | ||
simplejson | 11.24 | 14.50 | 21.86 |
json | 7.17 | 8.49 |
由于ujson崩溃,因此对于排序为空白。由于在转换所有键为str
之前尝试排序而引发TypeError
,因此json为空白。rapidjson为空白,因为它不支持非str
键。可以使用pynonstr
脚本重现此问题。
OPT_OMIT_MICROSECONDS
不要序列化datetime.datetime
和datetime.time
实例上的microsecond
字段。
>>> import orjson, datetime
>>> orjson.dumps(
datetime.datetime(1970, 1, 1, 0, 0, 0, 1),
)
b'"1970-01-01T00:00:00.000001"'
>>> orjson.dumps(
datetime.datetime(1970, 1, 1, 0, 0, 0, 1),
option=orjson.OPT_OMIT_MICROSECONDS,
)
b'"1970-01-01T00:00:00"'
OPT_PASSTHROUGH_DATACLASS
将dataclasses.dataclass
实例传递给default
。这允许自定义它们的输出,但速度非常慢。
>>> import orjson, dataclasses
>>>
@dataclasses.dataclass
class User:
id: str
name: str
password: str
def default(obj):
if isinstance(obj, User):
return {"id": obj.id, "name": obj.name}
raise TypeError
>>> orjson.dumps(User("3b1", "asd", "zxc"))
b'{"id":"3b1","name":"asd","password":"zxc"}'
>>> orjson.dumps(User("3b1", "asd", "zxc"), option=orjson.OPT_PASSTHROUGH_DATACLASS)
TypeError: Type is not JSON serializable: User
>>> orjson.dumps(
User("3b1", "asd", "zxc"),
option=orjson.OPT_PASSTHROUGH_DATACLASS,
default=default,
)
b'{"id":"3b1","name":"asd"}'
OPT_PASSTHROUGH_DATETIME
将datetime.datetime
、datetime.date
和datetime.time
实例传递给default
。这允许将日期时间序列化到自定义格式,例如HTTP日期。
>>> import orjson, datetime
>>>
def default(obj):
if isinstance(obj, datetime.datetime):
return obj.strftime("%a, %d %b %Y %H:%M:%S GMT")
raise TypeError
>>> orjson.dumps({"created_at": datetime.datetime(1970, 1, 1)})
b'{"created_at":"1970-01-01T00:00:00"}'
>>> orjson.dumps({"created_at": datetime.datetime(1970, 1, 1)}, option=orjson.OPT_PASSTHROUGH_DATETIME)
TypeError: Type is not JSON serializable: datetime.datetime
>>> orjson.dumps(
{"created_at": datetime.datetime(1970, 1, 1)},
option=orjson.OPT_PASSTHROUGH_DATETIME,
default=default,
)
b'{"created_at":"Thu, 01 Jan 1970 00:00:00 GMT"}'
如果使用OPT_NON_STR_KEYS,则此选项不会影响字典键中的日期时间。
OPT_PASSTHROUGH_SUBCLASS
将内置类型的子类传递给default
。
>>> import orjson
>>>
class Secret(str):
pass
def default(obj):
if isinstance(obj, Secret):
return "******"
raise TypeError
>>> orjson.dumps(Secret("zxc"))
b'"zxc"'
>>> orjson.dumps(Secret("zxc"), option=orjson.OPT_PASSTHROUGH_SUBCLASS)
TypeError: Type is not JSON serializable: Secret
>>> orjson.dumps(Secret("zxc"), option=orjson.OPT_PASSTHROUGH_SUBCLASS, default=default)
b'"******"'
如果使用OPT_NON_STR_KEYS,则此选项不会影响作为字典键序列化子类。
OPT_SERIALIZE_DATACLASS
这已被弃用,在版本3中没有效果。在版本2中,它用于序列化dataclasses.dataclass
实例。更多详情请参阅dataclass。
OPT_SERIALIZE_NUMPY
序列化numpy.ndarray
实例。更多详情请参阅numpy。
OPT_SERIALIZE_UUID
这已被弃用,在版本3中没有效果。在版本2中,它用于序列化uuid.UUID
实例。更多详情请参阅UUID。
OPT_SORT_KEYS
按排序顺序序列化dict
键。默认情况下,序列化顺序未指定。这相当于标准库中的sort_keys=True
。
这可以用于确保顺序对于散列或测试是确定性的。它有相当大的性能惩罚,并且通常不推荐使用。
>>> import orjson
>>> orjson.dumps({"b": 1, "c": 2, "a": 3})
b'{"b":1,"c":2,"a":3}'
>>> orjson.dumps({"b": 1, "c": 2, "a": 3}, option=orjson.OPT_SORT_KEYS)
b'{"a":3,"b":1,"c":2}'
这测量了未排序和排序的twitter.json固定文件的序列化。
库 | 未排序(毫秒) | 排序(毫秒) | 与orjson相比 |
---|---|---|---|
orjson | 0.32 | 0.54 | 1 |
ujson | 1.6 | 2.07 | 3.8 |
rapidjson | 1.12 | 1.65 | 3.1 |
simplejson | 2.25 | 3.13 | 5.8 |
json | 1.78 | 2.32 | 4.3 |
可以使用pysort
脚本重现此基准测试。
排序不是排序/区域设置的感知。
>>> import orjson
>>> orjson.dumps({"a": 1, "ä": 2, "A": 3}, option=orjson.OPT_SORT_KEYS)
b'{"A":3,"a":1,"\xc3\xa4":2}'
这是与标准库、rapidjson、simplejson和ujson相同的排序行为。
dataclass
也可以序列化为映射,但这不会对它们产生影响。
OPT_STRICT_INTEGER
强制整数限制为53位。默认情况下,整数限制为64位,与Python标准库相同。更多信息请参见 int。
OPT_UTC_Z
在 datetime.datetime
实例上序列化UTC时区为 Z
而不是 +00:00
。
>>> import orjson, datetime, zoneinfo
>>> orjson.dumps(
datetime.datetime(1970, 1, 1, 0, 0, 0, tzinfo=zoneinfo.ZoneInfo("UTC")),
)
b'"1970-01-01T00:00:00+00:00"'
>>> orjson.dumps(
datetime.datetime(1970, 1, 1, 0, 0, 0, tzinfo=zoneinfo.ZoneInfo("UTC")),
option=orjson.OPT_UTC_Z
)
b'"1970-01-01T00:00:00Z"'
片段
orjson.Fragment
在文档中包含已序列化的JSON。这是在无需首先通过 loads()
反序列化为Python对象的情况下,从缓存、JSONB字段或单独序列化的对象中包含JSON blob的有效方式。
>>> import orjson
>>> orjson.dumps({"key": "zxc", "data": orjson.Fragment(b'{"a": "b", "c": 1}')})
b'{"key":"zxc","data":{"a": "b", "c": 1}}'
它不会重新格式化:orjson.OPT_INDENT_2
不会影响紧凑的blob,也不会将格式化的JSON blob重写为紧凑格式。
输入必须是 bytes
或 str
,并作为位置参数给出。
如果给出的是 str
且输入不是有效的UTF-8,则会引发 orjson.JSONEncodeError
。否则,它不会进行验证,并且可以写入无效的JSON。它不会转义字符。实现经过测试,如果给出无效字符串或无效JSON,则不会崩溃。
这与 rapidjson 中的 RawJSON
相似。
反序列化
def loads(__obj: Union[bytes, bytearray, memoryview, str]) -> Any: ...
loads()
将JSON反序列化为Python对象。它反序列化为 dict
、list
、int
、float
、str
、bool
和 None
对象。
接受 bytes
、bytearray
、memoryview
和 str
输入。如果输入存在为 memoryview
、bytearray
或 bytes
对象,则建议直接传递这些对象而不是创建不必要的 str
对象。即,使用 orjson.loads(b"{}")
而不是 orjson.loads(b"{}".decode("utf-8"))
。这具有更低的内存使用率和更低的延迟。
输入必须是有效的UTF-8。
orjson 在整个过程中维护一个映射键的缓存。这通过避免重复字符串来减少了内存使用量。键的长度必须不超过64字节才能被缓存,存储2048个条目。
在调用期间,全局解释器锁(GIL)被持有。
如果给出无效的类型或无效的JSON,则会引发 JSONDecodeError
。这包括如果输入包含 NaN
、Infinity
或 -Infinity
,虽然标准库允许这些,但它们不是有效的JSON。
如果数组或对象的组合递归到1024层深,则会引发 JSONDecodeError
。
JSONDecodeError
是 json.JSONDecodeError
和 ValueError
的子类。这是为了与标准库兼容。
类型
数据类
orjson 以原生方式序列化 dataclasses.dataclass
实例。它比其他库快40-50倍,并且避免了与其他库相比序列化 dict
时出现的严重减速。
支持传递所有数据类变体,包括使用 __slots__
的数据类、冻结数据类、具有可选或默认属性的数据类以及子类。不使用 __slots__
会有性能优势。
库 | dict (ms) | dataclass (ms) | 与orjson相比 |
---|---|---|---|
orjson | 1.40 | 1.60 | 1 |
ujson | |||
rapidjson | 3.64 | 68.48 | 42 |
simplejson | 14.21 | 92.18 | 57 |
json | 13.28 | 94.90 | 59 |
这衡量了序列化555KiB的JSON,orjson原生和其他库使用 default
来序列化 dataclasses.asdict()
的输出。这可以使用 pydataclass
脚本来重现。
数据类被序列化为映射,每个属性都会序列化,并且按照类定义上给出的顺序。
>>> import dataclasses, orjson, typing
@dataclasses.dataclass
class Member:
id: int
active: bool = dataclasses.field(default=False)
@dataclasses.dataclass
class Object:
id: int
name: str
members: typing.List[Member]
>>> orjson.dumps(Object(1, "a", [Member(1, True), Member(2)]))
b'{"id":1,"name":"a","members":[{"id":1,"active":true},{"id":2,"active":false}]}'
日期时间
orjson 将 datetime.datetime
对象序列化为 RFC 3339 格式,例如,“1970-01-01T00:00:00+00:00”。这是ISO 8601的子集,与标准库中的 isoformat()
兼容。
>>> import orjson, datetime, zoneinfo
>>> orjson.dumps(
datetime.datetime(2018, 12, 1, 2, 3, 4, 9, tzinfo=zoneinfo.ZoneInfo("Australia/Adelaide"))
)
b'"2018-12-01T02:03:04.000009+10:30"'
>>> orjson.dumps(
datetime.datetime(2100, 9, 1, 21, 55, 2).replace(tzinfo=zoneinfo.ZoneInfo("UTC"))
)
b'"2100-09-01T21:55:02+00:00"'
>>> orjson.dumps(
datetime.datetime(2100, 9, 1, 21, 55, 2)
)
b'"2100-09-01T21:55:02"'
datetime.datetime
支持具有 tzinfo
为 None
、datetime.timezone.utc
、python3.9+ zoneinfo
模块中的时区实例,或来自第三方 pendulum
、pytz
或 dateutil
/arrow
库的时区实例的时区实例。
使用标准库的 zoneinfo.ZoneInfo
处理时区是最快的。
datetime.time
对象不能有 tzinfo
。
>>> import orjson, datetime
>>> orjson.dumps(datetime.time(12, 0, 15, 290))
b'"12:00:15.000290"'
datetime.date
对象将始终序列化。
>>> import orjson, datetime
>>> orjson.dumps(datetime.date(1900, 1, 2))
b'"1900-01-02"'
有关 tzinfo
的错误会导致引发 JSONEncodeError
。
要禁用序列化 datetime
对象,请指定选项 orjson.OPT_PASSTHROUGH_DATETIME
。
使用“Z”后缀代替“+00:00”来表示UTC(“Zulu”)时间,请使用选项orjson.OPT_UTC_Z
。
假设没有时区的日期时间都是UTC,请使用选项orjson.OPT_NAIVE_UTC
。
枚举
orjson原生序列化枚举。选项应用于它们的值。
>>> import enum, datetime, orjson
>>>
class DatetimeEnum(enum.Enum):
EPOCH = datetime.datetime(1970, 1, 1, 0, 0, 0)
>>> orjson.dumps(DatetimeEnum.EPOCH)
b'"1970-01-01T00:00:00"'
>>> orjson.dumps(DatetimeEnum.EPOCH, option=orjson.OPT_NAIVE_UTC)
b'"1970-01-01T00:00:00+00:00"'
不支持类型的成员的枚举可以使用default
进行序列化。
>>> import enum, orjson
>>>
class Custom:
def __init__(self, val):
self.val = val
def default(obj):
if isinstance(obj, Custom):
return obj.val
raise TypeError
class CustomEnum(enum.Enum):
ONE = Custom(1)
>>> orjson.dumps(CustomEnum.ONE, default=default)
b'1'
浮点数
orjson在无精度损失和一致舍入的情况下序列化和反序列化双精度浮点数。
orjson.dumps()
将不合规JSON的Nan、Infinity和-Infinity序列化为null
。
>>> import orjson, ujson, rapidjson, json
>>> orjson.dumps([float("NaN"), float("Infinity"), float("-Infinity")])
b'[null,null,null]'
>>> ujson.dumps([float("NaN"), float("Infinity"), float("-Infinity")])
OverflowError: Invalid Inf value when encoding double
>>> rapidjson.dumps([float("NaN"), float("Infinity"), float("-Infinity")])
'[NaN,Infinity,-Infinity]'
>>> json.dumps([float("NaN"), float("Infinity"), float("-Infinity")])
'[NaN, Infinity, -Infinity]'
整数
orjson默认序列化和反序列化64位整数。支持的范围内是一个有符号64位整数的最小值(-9223372036854775807)到无符号64位整数的最大值(18446744073709551615)。这具有广泛的兼容性,但有些实现只支持53位的整数,例如Web浏览器。对于这些实现,dumps()
可以配置为在超过53位范围时引发JSONEncodeError
。
>>> import orjson
>>> orjson.dumps(9007199254740992)
b'9007199254740992'
>>> orjson.dumps(9007199254740992, option=orjson.OPT_STRICT_INTEGER)
JSONEncodeError: Integer exceeds 53-bit range
>>> orjson.dumps(-9007199254740992, option=orjson.OPT_STRICT_INTEGER)
JSONEncodeError: Integer exceeds 53-bit range
NumPy
orjson原生序列化numpy.ndarray
和单个numpy.float64
、numpy.float32
、numpy.float16
(numpy.half
)、numpy.int64
、numpy.int32
、numpy.int16
、numpy.int8
、numpy.uint64
、numpy.uint32
、numpy.uint16
、numpy.uint8
、numpy.uintp
、numpy.intp
、numpy.datetime64
和numpy.bool
实例。
orjson与numpy v1和v2都兼容。
orjson在序列化numpy实例方面比所有比较的库都要快。序列化numpy数据需要指定option=orjson.OPT_SERIALIZE_NUMPY
。
>>> import orjson, numpy
>>> orjson.dumps(
numpy.array([[1, 2, 3], [4, 5, 6]]),
option=orjson.OPT_SERIALIZE_NUMPY,
)
b'[[1,2,3],[4,5,6]]'
数组必须是一个连续的C数组(C_CONTIGUOUS
)和受支持的其中一种数据类型。
注意使用tolist()
或orjson.dumps(..., option=orjson.OPT_SERIALIZE_NUMPY)
序列化numpy.float32
之间的差异:tolist()
在序列化之前将转换为double
,而orjson的本地路径则不会。这可能导致不同的舍入。
numpy.datetime64
实例序列化为RFC 3339字符串,日期时间选项会影响它们。
>>> import orjson, numpy
>>> orjson.dumps(
numpy.datetime64("2021-01-01T00:00:00.172"),
option=orjson.OPT_SERIALIZE_NUMPY,
)
b'"2021-01-01T00:00:00.172000"'
>>> orjson.dumps(
numpy.datetime64("2021-01-01T00:00:00.172"),
option=(
orjson.OPT_SERIALIZE_NUMPY |
orjson.OPT_NAIVE_UTC |
orjson.OPT_OMIT_MICROSECONDS
),
)
b'"2021-01-01T00:00:00+00:00"'
如果数组不是一个连续的C数组,包含不受支持的数据类型,或包含使用不受支持表示的numpy.datetime64
(例如,皮秒),orjson将回退到default
。在default
中,可以指定obj.tolist()
。
如果数组不是本地顺序,例如在低端系统上大端值的数组,将引发orjson.JSONEncodeError
。
如果数组格式不正确,将引发orjson.JSONEncodeError
。
这测量了从具有(50000, 100)
维度和numpy.float64
值的numpy.ndarray
序列化92MiB JSON的过程。
库 | 延迟(毫秒) | RSS差(MiB) | 与orjson相比 |
---|---|---|---|
orjson | 194 | 99 | 1.0 |
ujson | |||
rapidjson | 3,048 | 309 | 15.7 |
simplejson | 3,023 | 297 | 15.6 |
json | 3,133 | 297 | 16.1 |
这测量了从具有(100000, 100)
维度和numpy.int32
值的numpy.ndarray
序列化100MiB JSON的过程。
库 | 延迟(毫秒) | RSS差(MiB) | 与orjson相比 |
---|---|---|---|
orjson | 178 | 115 | 1.0 |
ujson | |||
rapidjson | 1,512 | 551 | 8.5 |
simplejson | 1,606 | 504 | 9.0 |
json | 1,506 | 503 | 8.4 |
这测量了从具有(100000, 200)
维度和numpy.bool
值的numpy.ndarray
序列化105MiB JSON的过程。
库 | 延迟(毫秒) | RSS差(MiB) | 与orjson相比 |
---|---|---|---|
orjson | 157 | 120 | 1.0 |
ujson | |||
rapidjson | 710 | 327 | 4.5 |
simplejson | 931 | 398 | 5.9 |
json | 996 | 400 | 6.3 |
在这些基准测试中,orjson原生序列化,ujson为空,因为它不支持默认参数,其他库通过default
序列化ndarray.tolist()
。RSS列测量序列化期间的峰值内存使用。这可以使用pynumpy
脚本重现。
orjson没有安装或编译对numpy的依赖。实现是独立的,使用PyArrayInterface
读取numpy.ndarray
。
字符串
orjson对UTF-8的符合性很严格。这比标准库的json模块更严格,它将序列化和反序列化无效UTF-8的UTF-16代理,例如"\ud800"。
如果orjson.dumps()
接收到不包含有效UTF-8的str
,将引发orjson.JSONEncodeError
。如果loads()
接收到无效UTF-8,将引发orjson.JSONDecodeError
。
orjson和rapidjson是唯一在坏输入上一致引发错误的比较JSON库。
>>> import orjson, ujson, rapidjson, json
>>> orjson.dumps('\ud800')
JSONEncodeError: str is not valid UTF-8: surrogates not allowed
>>> ujson.dumps('\ud800')
UnicodeEncodeError: 'utf-8' codec ...
>>> rapidjson.dumps('\ud800')
UnicodeEncodeError: 'utf-8' codec ...
>>> json.dumps('\ud800')
'"\\ud800"'
>>> orjson.loads('"\\ud800"')
JSONDecodeError: unexpected end of hex escape at line 1 column 8: line 1 column 1 (char 0)
>>> ujson.loads('"\\ud800"')
''
>>> rapidjson.loads('"\\ud800"')
ValueError: Parse error at offset 1: The surrogate pair in string is invalid.
>>> json.loads('"\\ud800"')
'\ud800'
为了尽可能正确地反序列化无效输入,首先使用errors
参数的replace
或lossy
选项对bytes
进行解码。
>>> import orjson
>>> orjson.loads(b'"\xed\xa0\x80"')
JSONDecodeError: str is not valid UTF-8: surrogates not allowed
>>> orjson.loads(b'"\xed\xa0\x80"'.decode("utf-8", "replace"))
'���'
UUID
orjson将uuid.UUID
实例序列化为RFC 4122格式,例如,“f81d4fae-7dec-11d0-a765-00a0c91e6bf6”。
>>> import orjson, uuid
>>> orjson.dumps(uuid.UUID('f81d4fae-7dec-11d0-a765-00a0c91e6bf6'))
b'"f81d4fae-7dec-11d0-a765-00a0c91e6bf6"'
>>> orjson.dumps(uuid.uuid5(uuid.NAMESPACE_DNS, "python.org"))
b'"886313e1-3b8a-5372-9b90-0c9aee199e5d"'
测试
该库具有全面的测试。它对JSONTestSuite和nativejson-benchmark仓库中的固定值进行了测试。它被测试为不会因Big List of Naughty Strings而崩溃。它被测试为不会泄漏内存。它被测试为不会因无效的UTF-8而崩溃或不接受。它还有集成测试,用于在Web服务器(使用多进程/分叉工作进程的gunicorn)和多线程时使用库。它还使用了ultrajson库的一些测试。
orjson是所比较库中最正确的。此图显示了每个库如何处理来自JSONTestSuite和nativejson-benchmark测试的342个JSON固定值。
库 | 不拒绝无效的JSON文档 | 不反序列化有效的JSON文档 |
---|---|---|
orjson | 0 | 0 |
ujson | 31 | 0 |
rapidjson | 6 | 0 |
simplejson | 10 | 0 |
json | 17 | 0 |
这表明所有库都能反序列化有效的JSON,但只有orjson正确地拒绝了给定的无效JSON固定值。错误大部分是由于接受无效的字符串和数字。
可以使用pycorrectness
脚本来重现上面的图。
性能
orjson的序列化和反序列化性能优于ultrajson、rapidjson、simplejson和json。基准测试是在真实数据的固定值上进行的
-
twitter.json,631.5KiB,Twitter上搜索“一”的结果,包含CJK字符串、字符串字典和字典数组,缩进。
-
github.json,55.8KiB,GitHub活动源,包含字符串字典和字典数组,未缩进。
-
citm_catalog.json,1.7MiB,音乐会数据,包含嵌套的字符串字典和整数数组,缩进。
-
canada.json,2.2MiB,加拿大边界的GeoJSON格式坐标,包含浮点数和数组,缩进。
延迟
twitter.json序列化
库 | 中值延迟(毫秒) | 每秒操作数 | 相对(延迟) |
---|---|---|---|
orjson | 0.1 | 8377 | 1 |
ujson | 0.9 | 1088 | 7.3 |
rapidjson | 0.8 | 1228 | 6.8 |
simplejson | 1.9 | 531 | 15.6 |
json | 1.4 | 744 | 11.3 |
twitter.json反序列化
库 | 中值延迟(毫秒) | 每秒操作数 | 相对(延迟) |
---|---|---|---|
orjson | 0.6 | 1811 | 1 |
ujson | 1.2 | 814 | 2.1 |
rapidjson | 2.1 | 476 | 3.8 |
simplejson | 1.6 | 626 | 3 |
json | 1.8 | 557 | 3.3 |
github.json序列化
库 | 中值延迟(毫秒) | 每秒操作数 | 相对(延迟) |
---|---|---|---|
orjson | 0.01 | 104424 | 1 |
ujson | 0.09 | 10594 | 9.8 |
rapidjson | 0.07 | 13667 | 7.6 |
simplejson | 0.2 | 5051 | 20.6 |
json | 0.14 | 7133 | 14.6 |
github.json反序列化
库 | 中值延迟(毫秒) | 每秒操作数 | 相对(延迟) |
---|---|---|---|
orjson | 0.05 | 20069 | 1 |
ujson | 0.11 | 8913 | 2.3 |
rapidjson | 0.13 | 8077 | 2.6 |
simplejson | 0.11 | 9342 | 2.1 |
json | 0.11 | 9291 | 2.2 |
citm_catalog.json序列化
库 | 中值延迟(毫秒) | 每秒操作数 | 相对(延迟) |
---|---|---|---|
orjson | 0.3 | 3757 | 1 |
ujson | 1.7 | 598 | 6.3 |
rapidjson | 1.3 | 768 | 4.9 |
simplejson | 8.3 | 120 | 31.1 |
json | 3 | 331 | 11.3 |
citm_catalog.json反序列化
库 | 中值延迟(毫秒) | 每秒操作数 | 相对(延迟) |
---|---|---|---|
orjson | 1.4 | 730 | 1 |
ujson | 2.6 | 384 | 1.9 |
rapidjson | 4 | 246 | 3 |
simplejson | 3.7 | 271 | 2.7 |
json | 3.7 | 267 | 2.7 |
canada.json序列化
库 | 中值延迟(毫秒) | 每秒操作数 | 相对(延迟) |
---|---|---|---|
orjson | 2.4 | 410 | 1 |
ujson | 9.6 | 104 | 3.9 |
rapidjson | 28.7 | 34 | 11.8 |
simplejson | 49.3 | 20 | 20.3 |
json | 30.6 | 32 | 12.6 |
canada.json反序列化
库 | 中值延迟(毫秒) | 每秒操作数 | 相对(延迟) |
---|---|---|---|
orjson | 3 | 336 | 1 |
ujson | 7.1 | 141 | 2.4 |
rapidjson | 20.1 | 49 | 6.7 |
simplejson | 16.8 | 59 | 5.6 |
json | 18.2 | 55 | 6.1 |
内存
由于解析时使用持久缓冲区,orjson 3.7.0的基线内存使用量高于其他库。反序列化时的增量内存使用量与标准库和其他第三方库相似。
第一列测量在导入库并读取固定值后的RSS,第二列测量在固定值上反复调用loads()
后的RSS增加。
twitter.json
库 | 导入,read() RSS(MiB) | loads() RSS增加(MiB) |
---|---|---|
orjson | 15.7 | 3.4 |
ujson | 16.4 | 3.4 |
rapidjson | 16.6 | 4.4 |
simplejson | 14.5 | 1.8 |
json | 13.9 | 1.8 |
github.json
库 | 导入,read() RSS(MiB) | loads() RSS增加(MiB) |
---|---|---|
orjson | 15.2 | 0.4 |
ujson | 15.4 | 0.4 |
rapidjson | 15.7 | 0.5 |
simplejson | 13.7 | 0.2 |
json | 13.3 | 0.1 |
citm_catalog.json
库 | 导入,read() RSS(MiB) | loads() RSS增加(MiB) |
---|---|---|
orjson | 16.8 | 10.1 |
ujson | 17.3 | 10.2 |
rapidjson | 17.6 | 28.7 |
simplejson | 15.8 | 30.1 |
json | 14.8 | 20.5 |
canada.json
库 | 导入,read() RSS(MiB) | loads() RSS增加(MiB) |
---|---|---|
orjson | 17.2 | 22.1 |
ujson | 17.4 | 18.3 |
rapidjson | 18 | 23.5 |
simplejson | 15.7 | 21.4 |
json | 15.4 | 20.4 |
重现
上述测量是在Linux(amd64)上的Python 3.11.9和orjson 3.10.6、ujson 5.10.0、python-rapidson 1.18和simplejson 3.19.2上进行的。
可以使用pybench
和graph
脚本来重现延迟结果。可以使用pymem
脚本来重现内存结果。
问题
为什么我无法从PyPI安装它?
可能需要将pip
升级到20.3或更高版本,以支持最新的manylinux_x_y或universal2 wheel格式。
“Cargo,Rust包管理器,未安装或不在PATH中。”
当PyPI上没有针对您的平台的二进制轮子(如manylinux)时,会出现这种情况。您可以通过rustup
或包管理器安装Rust,然后它会进行编译。
它能否反序列化为dataclasses、UUIDs、十进制数等,或者支持object_hook吗?
不,这需要一个指定预期类型和处理错误等的模式。这可以通过比这更高一级的数据验证库来解决。
它能否序列化为str
?
不,序列化的blob应该使用bytes
类型。
打包
要打包或json,至少需要Rust 1.72和maturin构建工具。推荐的构建命令是
maturin build --release --strip
它还受益于有一个C构建环境来编译更快的反序列化后端。请参阅该项目使用clang和LTO的manylinux_2_28
构建示例。
项目自己的CI测试针对nightly-2024-08-05
和稳定版1.72。明智的做法是将nightly版本锁定,因为该渠道可能会引入破坏性更改。
orjson在Linux上针对amd64、aarch64、arm7、ppc64le和s390x进行了测试。在macOS上,它针对aarch64或amd64进行了测试,并根据版本进行交叉编译。对于Windows,它针对amd64和i686进行了测试。
除了libc之外,没有其他运行时依赖项。
PyPI上的源分布包含所有依赖项的源代码,并且可以在没有网络访问的情况下构建。可以从https://files.pythonhosted.org/packages/source/o/orjson/orjson-${version}.tar.gz
下载文件。
orjson的测试包含在PyPI上的源分布中。运行测试的要求在test/requirements.txt
中指定。测试应在构建过程中运行。可以使用pytest -q test
运行。
许可证
orjson由ijl编写,邮箱:[email protected],版权所有 2018 - 2024,您可以选择Apache 2许可证或MIT许可证。
项目详情
下载文件
下载适用于您平台的项目文件。如果您不确定该选择哪一个,请了解有关安装包的更多信息。
源分布
构建分布
orjson-3.10.7.tar.gz 的哈希值
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 75ef0640403f945f3a1f9f6400686560dbfb0fb5b16589ad62cd477043c4eee3 |
|
MD5 | 15887b76f1f4c03c3fb00a56c404af19 |
|
BLAKE2b-256 | 9e03821c8197d0515e46ea19439f5c5d5fd9a9889f76800613cfac947b5d7845 |
哈希值 for orjson-3.10.7-cp313-cp313-musllinux_1_2_x86_64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 11748c135f281203f4ee695b7f80bb1358a82a63905f9f0b794769483ea854ad |
|
MD5 | 853d0938a83c7fe101b5e92bbd800bec |
|
BLAKE2b-256 | e21c3ef8d83d7c6a619ad3d69a4d5318591b4ce5862e6eda7c26bbe8208652ca |
哈希值 for orjson-3.10.7-cp313-cp313-musllinux_1_2_aarch64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 3dcfbede6737fdbef3ce9c37af3fb6142e8e1ebc10336daa05872bfb1d87839c |
|
MD5 | 70a5b6ee4faca8b6e0a0725e40b0146a |
|
BLAKE2b-256 | 0465f2a03fd1d4f0308f01d372e004c049f7eb9bc5676763a15f20f383fa9c01 |
哈希值 for orjson-3.10.7-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 9ea2c232deedcb605e853ae1db2cc94f7390ac776743b699b50b071b02bea6fe |
|
MD5 | 8b6579a8e513af557efdd135418b68c2 |
|
BLAKE2b-256 | 737f8d6ccd64a6f8bdbfe6c9be7c58aeb8094aa52a01fbbb2cda42ff7e312bd7 |
哈希值 for orjson-3.10.7-cp313-cp313-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 77d325ed866876c0fa6492598ec01fe30e803272a6e8b10e992288b009cbe149 |
|
MD5 | 4ace9730c8c14691086b247027b4b7ce |
|
BLAKE2b-256 | 1505121af8a87513c56745d01ad7cf215c30d08356da9ad882ebe2ba890824cd |
哈希值 for orjson-3.10.7-cp312-cp312-musllinux_1_2_x86_64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | d2d9f990623f15c0ae7ac608103c33dfe1486d2ed974ac3f40b693bad1a22a7b |
|
MD5 | 850bf1cd2a36d77e3400348c7c57c7c4 |
|
BLAKE2b-256 | 021ad11805670c29d3a1b29fc4bd048dc90b094784779690592efe8c9f71249a |
哈希值 for orjson-3.10.7-cp312-cp312-musllinux_1_2_aarch64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | d352ee8ac1926d6193f602cbe36b1643bbd1bbcb25e3c1a657a4390f3000c9a5 |
|
MD5 | b70f8806719b27256bfe5556c9e9d085 |
|
BLAKE2b-256 | 177e254189d9b6df89660f65aec878d5eeaa5b1ae371bd2c458f85940445d36f |
哈希值 for orjson-3.10.7-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | a0c6a008e91d10a2564edbb6ee5069a9e66df3fbe11c9a005cb411f441fd2c09 |
|
MD5 | 2228ae083124649c499da37d2e892dd8 |
|
BLAKE2b-256 | a06b34e6904ac99df811a06e42d8461d47b6e0c9b86e2fe7ee84934df6e35f0d |
哈希值 for orjson-3.10.7-cp312-cp312-manylinux_2_17_s390x.manylinux2014_s390x.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 23820a1563a1d386414fef15c249040042b8e5d07b40ab3fe3efbfbbcbcb8864 |
|
MD5 | e39554017342f730212592eeeb882950 |
|
BLAKE2b-256 | b100414f8d4bc5ec3447e27b5c26b4e996e4ef08594d599e79b3648f64da060c |
哈希值 用于 orjson-3.10.7-cp312-cp312-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | b48b3db6bb6e0a08fa8c83b47bc169623f801e5cc4f24442ab2b6617da3b5313 |
|
MD5 | c47e91f03ce33ecbada084730bc7ef90 |
|
BLAKE2b-256 | 30befd646fb1a461de4958a6eacf4ecf064b8d5479c023e0e71cc89b28fa91ac |
哈希值 用于 orjson-3.10.7-cp312-cp312-manylinux_2_17_armv7l.manylinux2014_armv7l.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | bdbb61dcc365dd9be94e8f7df91975edc9364d6a78c8f7adb69c1cdff318ec93 |
|
MD5 | 300f4dc66905edeba82f17f7a3b8494e |
|
BLAKE2b-256 | c527e40bc7d79c4afb7e9264f22320c285d06d2c9574c9c682ba0f1be3012833 |
哈希值 用于 orjson-3.10.7-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 76ac14cd57df0572453543f8f2575e2d01ae9e790c21f57627803f5e79b0d3c3 |
|
MD5 | 2d89778e3c82dcad0473a6d0cd98f34c |
|
BLAKE2b-256 | 6084e495edb919ef0c98d054a9b6d05f2700fdeba3886edd58f1c4dfb25d514a |
哈希值 用于 orjson-3.10.7-cp312-cp312-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 44a96f2d4c3af51bfac6bc4ef7b182aa33f2f054fd7f34cc0ee9a320d051d41f |
|
MD5 | 134bf2d8078d89763b4131426a7d24d6 |
|
BLAKE2b-256 | 147cb4ecc2069210489696a36e42862ccccef7e49e1454a3422030ef52881b01 |
哈希值 用于 orjson-3.10.7-cp311-cp311-musllinux_1_2_x86_64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | e724cebe1fadc2b23c6f7415bad5ee6239e00a69f30ee423f319c6af70e2a5c0 |
|
MD5 | ac2d2ce1a7cfa88ccca17bb4ef3d4475 |
|
BLAKE2b-256 | 53b910abe9089bdb08cd4218cc45eb7abfd787c82cf301cecbfe7f141542d7f4 |
哈希值 用于 orjson-3.10.7-cp311-cp311-musllinux_1_2_aarch64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 33cfb96c24034a878d83d1a9415799a73dc77480e6c40417e5dda0710d559ee6 |
|
MD5 | 7755171561323635fdd680b72a268ced |
|
BLAKE2b-256 | bbab1185e472f15c00d37d09c395e478803ed0eae7a3a3d055a5f3885e1ea136 |
哈希值 用于 orjson-3.10.7-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | b58d3795dafa334fc8fd46f7c5dc013e6ad06fd5b9a4cc98cb1456e7d3558bd6 |
|
MD5 | 960590238707ee008a6d43350f834254 |
|
BLAKE2b-256 | d3cb55205f3f1ee6ba80c0a9a18ca07423003ca8de99192b18be30f1f31b4cdd |
哈希值 用于 orjson-3.10.7-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 6b0dd04483499d1de9c8f6203f8975caf17a6000b9c0c54630cef02e44ee624e |
|
MD5 | 5f8befd6891251b20bf5881fad9bb1d6 |
|
BLAKE2b-256 | 92ee702d5e8ccd42dc2b9d1043f22daa1ba75165616aa021dc19fb0c5a726ce8 |
哈希值 用于 orjson-3.10.7-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 8de062de550f63185e4c1c54151bdddfc5625e37daf0aa1e75d2a1293e3b7d9a |
|
MD5 | af0b570fe5b85f6f90b3cc883f391baf |
|
BLAKE2b-256 | 669fe6a11b5d1ad11e9dc869d938707ef93ff5ed20b53d6cda8b5e2ac532a9d2 |
哈希值 用于 orjson-3.10.7-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 8a9c9b168b3a19e37fe2778c0003359f07822c90fdff8f98d9d2a91b3144d8e0 |
|
MD5 | c35571dc56025d2bef27fdda124cab40 |
|
BLAKE2b-256 | 9db6ed61e87f327a4cbb2075ed0716e32ba68cb029aa654a68c3eb27803050d8 |
哈希值 用于 orjson-3.10.7-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 480f455222cb7a1dea35c57a67578848537d2602b46c464472c995297117fa09 |
|
MD5 | 4f158b1a876d5775ae2e03923f7fb3be |
|
BLAKE2b-256 | b972d90bd11e83a0e9623b3803b079478a93de8ec4316c98fa66110d594de5fa |
哈希值 用于 orjson-3.10.7-cp311-cp311-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 7db8539039698ddfb9a524b4dd19508256107568cdad24f3682d5773e60504a2 |
|
MD5 | a069436255f0a118c72521779a21c894 |
|
BLAKE2b-256 | 89c9dd286c97c2f478d43839bd859ca4d9820e2177d4e07a64c516dc3e018062 |
哈希值 用于 orjson-3.10.7-cp310-cp310-musllinux_1_2_x86_64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | fdf5197a21dd660cf19dfd2a3ce79574588f8f5e2dbf21bda9ee2d2b46924d84 |
|
MD5 | da6fbd2e92bfb98501a47fe2680d0dd0 |
|
BLAKE2b-256 | a6d8eee30caba21a8d6a9df06d2519bb0ecd0adbcd57f2e79d360de5570031cf |
哈希值 用于 orjson-3.10.7-cp310-cp310-musllinux_1_2_aarch64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 479fd0844ddc3ca77e0fd99644c7fe2de8e8be1efcd57705b5c92e5186e8a250 |
|
MD5 | 41de8e95b3e1c8c04e323585cc5d0c2e |
|
BLAKE2b-256 | 820a1f09c12d15b1e83156b7f3f621561d38650fe5b8f39f38f04a64de1a87fc |
哈希值 用于 orjson-3.10.7-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 348bdd16b32556cf8d7257b17cf2bdb7ab7976af4af41ebe79f9796c218f7e91 |
|
MD5 | 457e4dab60dbe286146242c7cd0faf40 |
|
BLAKE2b-256 | b6bcfbd345d771a73cacc5b0e774d034cd081590b336754c511f4ead9fdc4cf1 |
哈希值 用于 orjson-3.10.7-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | de817e2f5fc75a9e7dd350c4b0f54617b280e26d1631811a43e7e968fa71e3e9 |
|
MD5 | dae12750f1aaaa7d39134aa3fd1c719c |
|
BLAKE2b-256 | 7f7eef8522dbba112af6cc52227dcc746dd3447c7d53ea8cea35740239b547ee |
哈希值 用于 orjson-3.10.7-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | ac7cf6222b29fbda9e3a472b41e6a5538b48f2c8f99261eecd60aafbdb60690c |
|
MD5 | 536e60d7c22ac86c351f0b05ab7b8be5 |
|
BLAKE2b-256 | 04dad03d72b54bdd60d05de372114abfbd9f05050946895140c6ff5f27ab8f49 |
哈希值 用于 orjson-3.10.7-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | bf6ba8ebc8ef5792e2337fb0419f8009729335bb400ece005606336b7fd7bab7 |
|
MD5 | f50628a0e0453d464328877b10ab0a29 |
|
BLAKE2b-256 | dd471ddff6e23fe5f4aeaaed996a3cde422b3eaac4558c03751723e106184c68 |
哈希值 用于 orjson-3.10.7-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 34a566f22c28222b08875b18b0dfbf8a947e69df21a9ed5c51a6bf91cfb944ac |
|
MD5 | a6f25d06469acccd3ae132e5fb552d33 |
|
BLAKE2b-256 | fe0eefbd0a2d25f8e82b230eb20b6b8424be6dd95b6811b669be9af16234b6db |
哈希值 用于 orjson-3.10.7-cp310-cp310-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 74f4544f5a6405b90da8ea724d15ac9c36da4d72a738c64685003337401f5c12 |
|
MD5 | 73c1907bc4824c22e52225ef30e7c8c3 |
|
BLAKE2b-256 | 491260931cf808b9334f26210ab496442f4a7a3d66e29d1cf12e0a01857e756f |
哈希值 用于 orjson-3.10.7-cp39-cp39-musllinux_1_2_x86_64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 0fa5886854673222618638c6df7718ea7fe2f3f2384c452c9ccedc70b4a510a5 |
|
MD5 | 46f075ea83645b7ec01cc4d7c88962cb |
|
BLAKE2b-256 | d7152c1ca80d4e37780514cc369004fce77e2748b54857b62eb217e9a243a669 |
哈希值 用于 orjson-3.10.7-cp39-cp39-musllinux_1_2_aarch64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | f4db56635b58cd1a200b0a23744ff44206ee6aa428185e2b6c4a65b3197abdcd |
|
MD5 | b2947e0f2e9510024df54522b25e5cf3 |
|
BLAKE2b-256 | c1c65d5c556720f8a31c5618db7326f6de6c07ddfea72497c1baa69fca24e1ad |
哈希值 用于 orjson-3.10.7-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | e72591bcfe7512353bd609875ab38050efe3d55e18934e2f18950c108334b4ff |
|
MD5 | b2f514da1e166c0ebe31dbab5475098b |
|
BLAKE2b-256 | 6cc197b5bb1869572483b0e060264180fe5417a836ed46c09166f0dc6bb1d42d |
哈希值 用于 orjson-3.10.7-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 5b24a579123fa884f3a3caadaed7b75eb5715ee2b17ab5c66ac97d29b18fe57f |
|
MD5 | c5a51dd2a87c605682f6f0ae89006344 |
|
BLAKE2b-256 | 0402bcb6ee82ecb5bc8f7487bce2204db9e9d8818f5fe7a3cad1625254f8d3a7 |
哈希值 用于 orjson-3.10.7-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 09b2d92fd95ad2402188cf51573acde57eb269eddabaa60f69ea0d733e789fe9 |
|
MD5 | 7fb4b085ad57ddae29a3c24071369987 |
|
BLAKE2b-256 | ba5b89f2d5cda6c7bcad2067a87407aa492392942118969d548bc77ab4e9c818 |
哈希值 用于 orjson-3.10.7-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 144888c76f8520e39bfa121b31fd637e18d4cc2f115727865fdf9fa325b10412 |
|
MD5 | ca943a19c838b30bd846bc724be9f6e4 |
|
BLAKE2b-256 | a34aa041b6c95f623c28ccab87ce0720ac60cd0734f357774fd7212ff1fd9077 |
哈希值 用于 orjson-3.10.7-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | ed350d6978d28b92939bfeb1a0570c523f6170efc3f0a0ef1f1df287cd4f4960 |
|
MD5 | 1333e3e15a78e1ba1ce38617690ac22f |
|
BLAKE2b-256 | b8e5f3cb8f766e7f5e5197e884d63fba320aa4f32a04a21b68864c71997cb17e |
哈希值 用于 orjson-3.10.7-cp39-cp39-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | e76be12658a6fa376fcd331b1ea4e58f5a06fd0220653450f0d415b8fd0fbe20 |
|
MD5 | 1919f7b33f3d1ae7c41838b6fc26cdb0 |
|
BLAKE2b-256 | 088c23813894241f920e37ae363aa59a6a0fdb06e90afd60ad89e5a424113d1c |
哈希值 用于 orjson-3.10.7-cp38-cp38-musllinux_1_2_x86_64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | c31008598424dfbe52ce8c5b47e0752dca918a4fdc4a2a32004efd9fab41d866 |
|
MD5 | 12c1cf6528719fe8a4f3ab026411a1b8 |
|
BLAKE2b-256 | 064790ff5f8522d371b8ec117791db13a14880647cad22a6d3c4369026ec0f48 |
哈希值 用于 orjson-3.10.7-cp38-cp38-musllinux_1_2_aarch64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 4e6c3da13e5a57e4b3dca2de059f243ebec705857522f188f0180ae88badd354 |
|
MD5 | da6aa2d7f37ca13109111afb965d5d4e |
|
BLAKE2b-256 | cbddf5b385ab593974efd082986f8c6f4f6d07715f7321d908ca16bc4ecd70cd |
哈希值 用于 orjson-3.10.7-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 1193b2416cbad1a769f868b1749535d5da47626ac29445803dae7cc64b3f5c98 |
|
MD5 | 46d011f6b773509d1b204e072a0bd355 |
|
BLAKE2b-256 | 2513a66f4873ed57832aab57dd8b49c91c4c22b35fb1fa0d1dce3bf8928f2fe0 |
哈希值 用于 orjson-3.10.7-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 4829cf2195838e3f93b70fd3b4292156fc5e097aac3739859ac0dcc722b27ac0 |
|
MD5 | 897e5bfdbef3cc5d92e7b87bc3bb1aa2 |
|
BLAKE2b-256 | 571c6d195253a25fdc9770056e3fed96d2e1105b2108c2e7f05bb2178f2e89cb |
哈希值 用于 orjson-3.10.7-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 084e537806b458911137f76097e53ce7bf5806dda33ddf6aaa66a028f8d43a23 |
|
MD5 | 92f003b9d710a5b605952ae297e327ae |
|
BLAKE2b-256 | 8487272c9abc2c45f535f5b7d05219d94e3962a8cb2866a72a4778289358a873 |
哈希值 用于 orjson-3.10.7-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 4b6146e439af4c2472c56f8540d799a67a81226e11992008cb47e1267a9b3225 |
|
MD5 | fa638ae27389252913053cb266d7e9e6 |
|
BLAKE2b-256 | fe6635857fdb7883d6f51c5d212693c51ad72f8b25b73fc043f424760b735ec6 |
哈希值 用于 orjson-3.10.7-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 430ee4d85841e1483d487e7b81401785a5dfd69db5de01314538f31f8fbf7ee1 |
|
MD5 | 83eb8d43b2f753a5ecfee952907f8c24 |
|
BLAKE2b-256 | e022218233b8038a83ca8df0c6e7e28270ad5a2cd02a2e2ada0a30f33d018601 |
哈希值 用于 orjson-3.10.7-cp38-cp38-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl
算法 | 哈希摘要 | |
---|---|---|
SHA256 | 6ea2b2258eff652c82652d5e0f02bd5e0463a6a52abb78e49ac288827aaa1469 |
|
MD5 | 58b6a1bdaa0a0c0ac65f6e7f0157a4eb |
|
BLAKE2b-256 | 6e54cf4838db05cc5c3e2ccd8b85e80239789457fc8a20071910e8f97cd7fa44 |