json — Кодировщик и декодер JSON
Исходный код: Lib/json/__init__.py
JSON (JavaScript Object Notation), определённый в RFC 7159 (который устарел RFC 4627) и ECMA-404, является лёгким форматом обмена данными, вдохновлённым синтаксисом литералов объектов JavaScript (хотя он не является строгой подмножеством JavaScript 1 ).
json предоставляет API, знакомый пользователям стандартной библиотеки marshal и pickle модулей.
Кодирование базовых иерархий объектов Python:
>>> import json
>>> json.dumps(['foo', {'bar': ('baz', None, 1.0, 2)}])
'["foo", {"bar": ["baz", null, 1.0, 2]}]'
>>> print(json.dumps("\"foo\bar"))
"\"foo\bar"
>>> print(json.dumps('\u1234'))
"\u1234"
>>> print(json.dumps('\\'))
"\\"
>>> print(json.dumps({"c": 0, "b": 0, "a": 0}, sort_keys=True))
{"a": 0, "b": 0, "c": 0}
>>> from io import StringIO
>>> io = StringIO()
>>> json.dump(['streaming API'], io)
>>> io.getvalue()
'["streaming API"]'
Кодирование в компактном формате:
>>> import json
>>> json.dumps([1, 2, 3, {'4': 5, '6': 7}], separators=(',', ':'))
'[1,2,3,{"4":5,"6":7}]'
Красивая печать:
>>> import json
>>> print(json.dumps({'4': 5, '6': 7}, sort_keys=True, indent=4))
{
"4": 5,
"6": 7
}
Декодирование JSON:
>>> import json
>>> json.loads('["foo", {"bar":["baz", null, 1.0, 2]}]')
['foo', {'bar': ['baz', None, 1.0, 2]}]
>>> json.loads('"\\"foo\\bar"')
'"foo\x08ar'
>>> from io import StringIO
>>> io = StringIO('["streaming API"]')
>>> json.load(io)
['streaming API']
Настройка декодирования объектов JSON:
>>> import json
>>> def as_complex(dct):
... if '__complex__' in dct:
... return complex(dct['real'], dct['imag'])
... return dct
...
>>> json.loads('{"__complex__": true, "real": 1, "imag": 2}',
... object_hook=as_complex)
(1+2j)
>>> import decimal
>>> json.loads('1.1', parse_float=decimal.Decimal)
Decimal('1.1')
Расширение JSONEncoder:
>>> import json >>> class ComplexEncoder(json.JSONEncoder): ... def default(self, obj): ... if isinstance(obj, complex): ... return [obj.real, obj.imag] ... # Let the base class default method raise the TypeError ... return json.JSONEncoder.default(self, obj) ... >>> json.dumps(2 + 1j, cls=ComplexEncoder) '[2.0, 1.0]' >>> ComplexEncoder().encode(2 + 1j) '[2.0, 1.0]' >>> list(ComplexEncoder().iterencode(2 + 1j)) ['[2.0', ', 1.0', ']']
Использование json.tool из командной строки для проверки и красивой печати:
$ echo '{"json":"obj"}' | python -m json.tool
{
"json": "obj"
}
$ echo '{1.2:3.4}' | python -m json.tool
Expecting property name enclosed in double quotes: line 1 column 2 (char 1)
См. Командную строку для подробной документации.
Примечание
JSON является подмножеством YAML 1.2. JSON, сгенерированный по умолчанию настройками этого модуля (в частности, значение по умолчанию separators), также является подмножеством YAML 1.0 и 1.1. Таким образом, этот модуль также может быть использован как сериализатор YAML.
Базовое использование
-
json.dump(obj, fp, *, skipkeys=False, ensure_ascii=True, check_circular=True, allow_nan=True, cls=None, indent=None, separators=None, default=None, sort_keys=False, **kw) -
Сериализует obj как поток JSON в fp (объект, поддерживающий
.write()подобный файлу), используя эту таблицу преобразований.Если skipkeys истинно (по умолчанию:
False), то ключи словарей, которые не являются базовыми типами (str,int,float,bool,None) будут пропущены вместо повышенияTypeError.Модуль
jsonвсегда производит объектыstr, а неbytes. Поэтому,fp.write()должен поддерживать вводstr.Если ensure_ascii истинно (по умолчанию), выход гарантированно будет содержать все не-ASCII символы, экранированные. Если ensure_ascii ложно, эти символы будут выведены как есть.
Если check_circular ложно (по умолчанию:
True), то проверка циклических ссылок для контейнерных типов будет пропущена, и циклическая ссылка приведёт кOverflowError(или худшему).Если allow_nan ложно (по умолчанию:
True), то сериализация значенийfloatвне диапазона (nan,inf,-inf) будет вызыватьValueErrorв строгом соответствии со спецификацией JSON. Если allow_nan истинно, будут использованы их JavaScript эквиваленты (NaN,Infinity,-Infinity)Если indent является неотрицательным целым числом или строкой, элементы массива JSON и члены объектов будут отформатированы с этим уровнем отступа. Уровень отступа 0, отрицательный или
""будет вставлять только новые строки.None(по умолчанию) выбирает наиболее компактное представление. Использование положительного целого числа indent отступает на столько пробелов на каждый уровень. Если indent является строкой (например,"\t"), эта строка используется для отступа каждого уровня.Изменено в версии 3.2: Поддержка строк для indent в дополнение к целым числам.
Если указано, separators должно быть кортежем
(item_separator, key_separator). По умолчанию это(', ', ': ')если indentNoneи(',', ': ')иначе. Для получения наиболее компактного представления JSON необходимо указать(',', ':')для удаления пробелов.Изменено в версии 3.4: Используйте
(',', ': ')в качестве значения по умолчанию, если indent неNone.Если указано, default должно быть функцией, которая вызывается для объектов, которые нельзя иначе сериализовать. Она должна вернуть JSON-сериализуемую версию объекта или вызвать
TypeError. Если не указано, то вызываетсяTypeError.Если sort_keys истинно (по умолчанию:
False), то выход словарей будет отсортирован по ключам.Для использования пользовательского подкласса
JSONEncoder(например, одного, который переопределяет методdefault()для сериализации дополнительных типов), укажите его с аргументом cls; в противном случае используетсяJSONEncoder.Изменено в версии 3.6: Все необязательные параметры теперь только ключевые.
-
json.dumps(obj, *, skipkeys=False, ensure_ascii=True, check_circular=True, allow_nan=True, cls=None, indent=None, separators=None, default=None, sort_keys=False, **kw) -
Сериализует obj в строку JSON
strс помощью этой таблицы преобразований. Аргументы имеют то же значение, что и вdump().Примечание
Ключи в парах «ключ/значение» JSON всегда имеют тип
str. Когда словарь преобразуется в JSON, все ключи словаря приводятся к строкам. В результате этого, если словарь преобразуется в JSON и затем обратно в словарь, словарь может не совпадать с исходным, т.е.loads(dumps(x)) != xесли у x есть ключи, не являющиеся строками.
-
json.load(fp, *, cls=None, object_hook=None, parse_float=None, parse_int=None, parse_constant=None, object_pairs_hook=None, **kw) -
Десериализуйте fp (a
.read()-поддерживающий текстовый файл или бинарный файл содержащий JSON-документ) в объект Python, используя эту таблицу преобразования.object_hook — это необязательная функция, которая будет вызвана с результатом любого декодированного объекта литерала (a
dict). Возвращаемое значение object_hook будет использоваться вместоdict. Эта функция может использоваться для реализации пользовательских декодеров (например, JSON-RPC с указанием класса).object_pairs_hook — это необязательная функция, которая будет вызвана с результатом любого декодированного объекта литерала с упорядоченным списком пар. Возвращаемое значение object_pairs_hook будет использоваться вместо
dict. Эта функция может использоваться для реализации пользовательских декодеров. Если также определен object_hook, то object_pairs_hook имеет приоритет.Изменено в версии 3.1: Добавлена поддержка object_pairs_hook.
parse_float, если указан, будет вызван со строкой каждого JSON-числа с плавающей запятой, который должен быть декодирован. По умолчанию это эквивалентно
float(num_str). Это можно использовать для использования другого типа данных или парсера для JSON-чисел с плавающей запятой (например,decimal.Decimal).parse_int, если указан, будет вызван со строкой каждого JSON целого числа, которое должно быть декодировано. По умолчанию это эквивалентно
int(num_str). Это можно использовать для использования другого типа данных или парсера для JSON-целых чисел (например,float).parse_constant, если указан, будет вызван со строкой одного из следующих значений:
'-Infinity','Infinity','NaN'. Это можно использовать для вызова исключения, если встретятся недопустимые JSON-числа.Изменено в версии 3.1: parse_constant больше не вызывается для ‘null’, ‘true’, ‘false’.
Чтобы использовать пользовательский подкласс
JSONDecoder, укажите его с помощью параметраcls; в противном случае используетсяJSONDecoder. Дополнительные ключевые аргументы будут переданы в конструктор класса.Если данные, которые нужно десериализовать, не являются допустимым JSON-документом, будет поднято исключение
JSONDecodeError.Изменено в версии 3.6: Все необязательные параметры теперь являются ключевыми параметрами.
Изменено в версии 3.6: fp теперь может быть бинарным файлом. Кодировка входных данных должна быть UTF-8, UTF-16 или UTF-32.
-
json.loads(s, *, encoding=None, cls=None, object_hook=None, parse_float=None, parse_int=None, parse_constant=None, object_pairs_hook=None, **kw) -
Десериализуйте s (a
str,bytesилиbytearrayinstance содержащий JSON-документ) в объект Python, используя эту таблицу преобразования.Другие аргументы имеют то же значение, что и в
load(), за исключением encoding, который игнорируется и устарел.Если данные, которые нужно десериализовать, не являются допустимым JSON-документом, будет поднято исключение
JSONDecodeError.
Кодировщики и Декодировщики
-
class json.JSONDecoder(*, object_hook=None, parse_float=None, parse_int=None, parse_constant=None, strict=True, object_pairs_hook=None) -
Простой декодер JSON.
По умолчанию выполняет следующие преобразования при декодировании:
JSON
Python
объект
словарь
массив
список
строка
строка
число (целое)
целое число
число (вещественное)
число с плавающей точкой
true
True
false
False
null
None
Также понимает
NaN,Infinity, и-Infinityкак соответствующие имfloatзначения, что выходит за рамки спецификации JSON.object_hook, если указан, будет вызываться с результатом каждого декодированного JSON-объекта, и его возвращаемое значение будет использоваться вместо заданного
dict. Это можно использовать для предоставления пользовательской десериализации (например, для поддержки JSON-RPC с указанием класса).object_pairs_hook, если указан, будет вызываться с результатом каждого декодированного JSON-объекта с упорядоченным списком пар. Возвращаемое значение object_pairs_hook будет использоваться вместо
dict. Эта функция может использоваться для реализации пользовательских декодеров. Если также определен object_hook, то object_pairs_hook имеет приоритет.Изменено в версии 3.1: Добавлена поддержка object_pairs_hook.
parse_float, если указан, будет вызываться со строкой каждого JSON-числа с плавающей точкой, который должен быть декодирован. По умолчанию это эквивалентно
float(num_str). Это можно использовать для использования другого типа данных или парсера для JSON-чисел с плавающей запятой (например,decimal.Decimal).parse_int, если указан, будет вызываться со строкой каждого JSON целого числа, которое должно быть декодировано. По умолчанию это эквивалентно
int(num_str). Это можно использовать для использования другого типа данных или парсера для JSON-целых чисел (например,float).parse_constant, если указан, будет вызываться со строкой одного из следующих значений:
'-Infinity','Infinity','NaN'. Это можно использовать для вызова исключения, если встретятся недопустимые JSON-числа.Если strict равен false (
True— значение по умолчанию), тогда управляющие символы будут разрешены внутри строк. Управляющие символы в данном контексте — это те, у которых коды символов находятся в диапазоне от 0 до 31, включая'\t'(табуляцию),'\n','\r'и'\0'.Если данные, которые нужно десериализовать, не являются допустимым JSON-документом, будет поднято исключение
JSONDecodeError.Изменено в версии 3.6: Все параметры теперь являются ключевыми параметрами.
-
decode(s) -
Возвращает представление Python объекта s (a
strinstance содержащий JSON-документ).Исключение
JSONDecodeErrorбудет поднято, если заданный JSON-документ не является валидным.
-
raw_decode(s) -
Декодирует JSON-документ из s (a
strначинающийся с JSON-документа) и возвращает кортеж из 2 элементов: представление Python объекта и индекс в s, где документ закончился.Это можно использовать для декодирования JSON-документа из строки, которая может содержать дополнительные данные в конце.
-
-
class json.JSONEncoder(*, skipkeys=False, ensure_ascii=True, check_circular=True, allow_nan=True, sort_keys=False, indent=None, separators=None, default=None) -
Расширяемый кодировщик JSON для структур данных Python.
По умолчанию поддерживает следующие объекты и типы:
Python
JSON
dict
object
list, tuple
array
str
string
int, float, целые и вещественные Enums
number
True
true
False
false
None
null
Изменено в версии 3.4: Добавлена поддержка целых и вещественных классов Enum.
Чтобы расширить поддержку других объектов, необходимо создать подкласс и реализовать метод
default()с другим методом, который возвращает сериализуемый объект дляo, если это возможно, в противном случае следует вызвать реализацию базового класса (чтобы вызвать исключениеTypeError).Если skipkeys имеет значение false (по умолчанию), то попытка закодировать ключи, которые не являются
str,int,floatилиNone, приведёт к исключениюTypeError. Если skipkeys имеет значение true, такие элементы просто пропускаются.Если ensure_ascii имеет значение true (по умолчанию), выходные данные гарантированно содержат все входящие не-ASCII символы, закодированные в виде escape-последовательностей. Если ensure_ascii имеет значение false, эти символы будут выведены как есть.
Если check_circular имеет значение true (по умолчанию), то списки, словари и пользовательские закодированные объекты будут проверены на наличие циклических ссылок во время кодирования, чтобы предотвратить бесконечную рекурсию (что приведёт к
OverflowError). В противном случае такая проверка не выполняется.Если allow_nan имеет значение true (по умолчанию), то
NaN,Infinity, и-Infinityбудут закодированы как есть. Это поведение не соответствует спецификации JSON, но согласуется с большинством JavaScript-кодировщиков и декодировщиков. В противном случае, кодирование таких чисел с плавающей точкой приведёт к исключениюValueError.Если sort_keys имеет значение true (по умолчанию:
False), то вывод словарей будет отсортирован по ключам; это полезно для регрессионных тестов, чтобы обеспечить возможность сравнения JSON-сериализаций каждый день.Если indent — целое число больше или равно 0 или строка, то элементы массива JSON и члены объекта будут красиво отформатированы с указанным уровнем отступа. Уровень отступа 0, отрицательное значение или
""будут вставлять только новые строки.None(по умолчанию) выбирает наиболее компактное представление. Использование положительного целого числа для indent вставляет отступы на столько пробелов на каждый уровень. Если indent — строка (например,"\t"), эта строка используется для отступа каждого уровня.Изменено в версии 3.2: В качестве indent помимо целых чисел теперь разрешены строки.
Если указано, separators должно быть кортежем из
(item_separator, key_separator). По умолчанию это(', ', ': ')если indent имеет значениеNone, и(',', ': ')в противном случае. Для получения наиболее компактного представления JSON необходимо указать(',', ':')для удаления пробелов.Изменено в версии 3.4: Используется
(',', ': ')в качестве значения по умолчанию, если indent неNone.Если указано, default должен быть функцией, которая вызывается для объектов, которые не могут быть сериализованы другим способом. Она должна возвращать JSON-кодируемую версию объекта или вызывать исключение
TypeError. Если не указано, будет вызвано исключениеTypeError.Изменено в версии 3.6: Все параметры теперь имеют ключевое слово.
-
default(o) -
Реализуйте этот метод в подклассе таким образом, чтобы он возвращал сериализуемый объект для o или вызывал базовый метод (чтобы вызвалось исключение
TypeError).Например, для поддержки произвольных итераторов, вы можете реализовать default так:
def default(self, o): try: iterable = iter(o) except TypeError: pass else: return list(iterable) # Let the base class default method raise the TypeError return json.JSONEncoder.default(self, o)
-
encode(o) -
Возвращает JSON-строковое представление структуры данных Python, o. Например:
>>> json.JSONEncoder().encode({"foo": ["bar", "baz"]}) '{"foo": ["bar", "baz"]}'
-
iterencode(o) -
Кодирует заданный объект, o, и возвращает каждое строковое представление по мере его доступности. Например:
for chunk in json.JSONEncoder().iterencode(bigobject): mysocket.write(chunk)
-
Исключения
-
exception json.JSONDecodeError(msg, doc, pos) -
Подкласс
ValueErrorс дополнительными атрибутами:-
msg -
Неформализованное сообщение об ошибке.
-
doc -
Документ JSON, который парсится.
-
pos -
Начальный индекс doc, где произошла ошибка парсинга.
-
lineno -
Строка, соответствующая pos.
-
colno -
Столбец, соответствующий pos.
Новое в версии 3.5.
-
Соответствие стандартам и взаимодействие
Формат JSON определён в RFC 7159 и в ECMA-404. Этот раздел описывает уровень соответствия этого модуля RFC. Для простоты, подклассы JSONEncoder и JSONDecoder, и параметры, отличные от явно указанных, не рассматриваются.
Этот модуль не строго соответствует RFC, реализуя некоторые расширения, которые являются допустимыми для JavaScript, но не для JSON. В частности:
- Бесконечные и NaN значения чисел принимаются и выводятся;
- Повторные имена в объекте принимаются, и используется только значение последней пары имя-значение.
Так как RFC разрешает RFC-совместимым парсерам принимать тексты ввода, которые не являются RFC-совместимыми, десериализатор этого модуля технически RFC-совместим при стандартных настройках.
Кодировки символов
RFC требует, чтобы JSON представлялся с использованием UTF-8, UTF-16 или UTF-32, причём UTF-8 рекомендуется по умолчанию для максимального взаимодействия.
Как разрешено, хотя и не обязательно, RFC, сериализатор этого модуля устанавливает ensure_ascii=True по умолчанию, тем самым избегая символы, не входящие в ASCII, в выходных строках.
За исключением параметра ensure_ascii, этот модуль определяется строго в терминах преобразования между объектами Python и Unicode strings, и поэтому не рассматривает проблему кодировок символов напрямую.
RFC запрещает добавление маркера порядка байтов (BOM) в начало текста JSON, и сериализатор этого модуля не добавляет BOM в свой вывод. RFC разрешает, но не требует, чтобы десериализаторы JSON игнорировали начальный BOM в своём вводе. Этот модуль десериализатор поднимает исключение ValueError, когда присутствует начальный BOM.
RFC не запрещает явно JSON-строки, которые содержат последовательности байтов, не соответствующие допустимым символам Unicode (например, непопарные суррогаты UTF-16), но отмечает, что они могут вызвать проблемы взаимодействия. По умолчанию этот модуль принимает и выводит (при наличии в исходной str) кодовые точки для таких последовательностей.
Бесконечные и NaN значения чисел
RFC не разрешает представление бесконечных или NaN значений чисел. Несмотря на это, по умолчанию этот модуль принимает и выводит Infinity, -Infinity, и NaN так, как будто они являются допустимыми литералами чисел JSON:
>>> # Neither of these calls raises an exception, but the results are not valid JSON
>>> json.dumps(float('-inf'))
'-Infinity'
>>> json.dumps(float('nan'))
'NaN'
>>> # Same when deserializing
>>> json.loads('-Infinity')
-inf
>>> json.loads('NaN')
nan
В сериализаторе параметр allow_nan может быть использован для изменения этого поведения. В десериализаторе параметр parse_constant может быть использован для изменения этого поведения.
Повторные имена в объекте
RFC определяет, что имена в объекте JSON должны быть уникальными, но не предписывает, как должны обрабатываться повторяющиеся имена в объектах JSON. По умолчанию этот модуль не поднимает исключения; вместо этого он игнорирует все, кроме последней пары имя-значение для данного имени:
>>> weird_json = '{"x": 1, "x": 2, "x": 3}'
>>> json.loads(weird_json)
{'x': 3}
Параметр object_pairs_hook может быть использован для изменения этого поведения.
Значения верхнего уровня, не являющиеся объектами и массивами
Старая версия JSON, определённая устаревшим RFC 4627, требовала, чтобы верхнеуровневое значение в JSON-тексте должно было быть либо JSON-объектом, либо массивом (Python dict или list), и не могло быть JSON-значением null, boolean, number или string. RFC 7159 убрало это ограничение, и этот модуль не накладывал и никогда не накладывал это ограничение ни на свой сериализатор, ни на десериализатор.
Тем не менее, для максимальной совместимости вы можете добровольно придерживаться этого ограничения.
Ограничения реализации
Некоторые реализации JSON-десериализаторов могут устанавливать ограничения на:
- размер принимаемых JSON-текстов
- максимальный уровень вложенности JSON-объектов и массивов
- диапазон и точность JSON-чисел
- содержание и максимальную длину JSON-строк
Этот модуль не накладывает никаких таких ограничений, кроме тех, которые существуют для соответствующих типов данных Python или самого интерпретатора Python.
При сериализации в JSON следует учитывать любые такие ограничения в приложениях, которые могут использовать ваш JSON. В частности, JSON-числа обычно десериализуются в числа двойной точности IEEE 754 и, следовательно, подвержены ограничениям по диапазону и точности этой системы представления. Это особенно важно при сериализации значений Python int с чрезвычайно большой величиной или при сериализации экземпляров «экзотических» числовых типов, таких как decimal.Decimal.
Командная строка
Исходный код: Lib/json/tool.py
Модуль json.tool предоставляет простой интерфейс командной строки для проверки и красивого вывода JSON-объектов.
Если необязательные аргументы infile и outfile не указаны, будут использоваться соответственно sys.stdin и sys.stdout:
$ echo '{"json": "obj"}' | python -m json.tool
{
"json": "obj"
}
$ echo '{1.2:3.4}' | python -m json.tool
Expecting property name enclosed in double quotes: line 1 column 2 (char 1)
Изменено в версии 3.5: Вывод теперь в том же порядке, что и вход. Используйте опцию --sort-keys для сортировки вывода словарей в алфавитном порядке по ключу.
Параметры командной строки
-
infile -
Файл JSON для проверки или форматированного вывода:
$ python -m json.tool mp_films.json [ { "title": "And Now for Something Completely Different", "year": 1971 }, { "title": "Monty Python and the Holy Grail", "year": 1975 } ]Если infile не указан, читается из
sys.stdin.
-
outfile -
Записать вывод из infile в указанный outfile. В противном случае, вывести в
sys.stdout.
-
--sort-keys -
Сортировать вывод словарей в алфавитном порядке по ключу.
Добавлена в версии 3.5.
-
-h, --help -
Показать сообщение справки.
Примечания
-
1 -
Как отмечается в ошибках RFC 7159, JSON допускает символы U+2028 (РАЗДЕЛИТЕЛЬ СТРОК) и U+2029 (РАЗДЕЛИТЕЛЬ АБЗАЦОВ) в строках, в то время как JavaScript (по состоянию на ECMAScript Edition 5.1) этого не делает.
© 2001–2020 Python Software Foundation
Licensed under the PSF License.
https://docs.python.org/3.7/library/json.html