В современной разработке на платформе 1С:Предприятие 8.3 работа с форматом JSON стала стандартом де-факто для обмена данными между различными информационными системами (в том числе через универсальный Python-коннектор к 1С). Будь то интеграция с интернет-магазином, тестирование http-сервисов, взаимодействие с государственными сервисами, импорт задач из Jira в 1С или мобильными приложениями — везде мы сталкиваемся с необходимостью быстро и надежно преобразовывать JSON в объекты 1С и обратно. В этой статье мы подробно разберем, как эффективно работать с этим форматом, рассмотрим доступные инструменты и проанализируем нюансы их применения.
Прежде чем приступать к написанию кода, проанализируем, какие механизмы предоставляет нам платформа. Существует два основных подхода к чтению JSON в 1С:
ПрочитатьJSON. Этот метод автоматически преобразует всю структуру JSON-файла в коллекции 1С (Структура, Соответствие, Массив). Он прост в использовании, но потребляет значительный объем оперативной памяти при работе с очень большими файлами.ЧтениеJSON. Это более низкоуровневый подход, позволяющий читать файл «по кусочкам» (токен за токеном). Он идеально подходит для обработки гигантских массивов данных, так как не загружает весь файл в память целиком.Рассмотрим подробнее первый, наиболее популярный способ. Он идеально подходит для большинства повседневных задач интеграции.
ПрочитатьJSONРазберем типичную ситуацию: у нас есть файл или строка в формате JSON, которую необходимо преобразовать в структуру 1С для дальнейшей обработки. Посмотрим на пример кода, который реализует эту задачу:
// Создаем объект для чтения JSON
Чтение = Новый ЧтениеJSON;
// Открываем файл (или строку методом УстановитьСтроку)
Чтение.ОткрытьФайл("C:\temp\data.json");
// Читаем данные в переменную.
// Платформа сама определит типы (числа, строки, булево, массивы)
ДанныеJSON = ПрочитатьJSON(Чтение);
// Обязательно закрываем объект чтения
Чтение.Закрыть();
Выясним причину, по которой иногда стоит использовать Соответствие вместо Структура. В JSON ключи могут содержать символы, которые недопустимы для ключей структуры в 1С (например, пробелы, дефисы или цифры в начале имени). Если мы ожидаем такие данные, нам нужно указать платформе, что мы хотим получить на выходе Соответствие.
Посмотрим на пример настройки функции ПрочитатьJSON для работы с нестандартными именами полей:
Чтение = Новый ЧтениеJSON;
Чтение.УстановитьСтроку(ТекстJSON);
// Третий параметр ИменаСвойствСоответствиями определяет тип результата
Данные = ПрочитатьJSON(Чтение, Ложь, "ИменаСвойствСоответствиями");
// Теперь мы можем обращаться к полям с любыми именами
ЗначениеПоля = Данные.Получить("field-name-with-dash");
Проанализируем ситуацию, когда размер файла JSON превышает несколько сотен мегабайт. Попытка прочитать его целиком через ПрочитатьJSON может привести к ошибке нехватки памяти. В этом случае мы будем использовать объект ЧтениеJSON в цикле.
Разберем по шагам, как работает потоковое чтение:
Чтение = Новый ЧтениеJSON;
Чтение.ОткрытьФайл("C:\temp\huge_data.json");
Пока Чтение.Прочитать() Цикл
ТипУзла = Чтение.ТипТекущегоЗначения;
Если ТипУзла = ТипУзлаJSON.ИмяСвойства Тогда
ИмяСвойства = Чтение.ТекущееЗначение;
// Проверяем интересующее нас свойство
Если ИмяСвойства = "items" Тогда
// Если это начало массива, мы можем прочитать его элементы
// или продолжить чтение токенов
КонецЕсли;
ИначеЕсли ТипУзла = ТипУзлаJSON.Число
Или ТипУзла = ТипУзлаJSON.Строка Тогда
Значение = Чтение.ТекущееЗначение;
// Обрабатываем значение
КонецЕсли;
КонецЦикла;
Чтение.Закрыть();
Такой подход требует написания большего количества кода, но гарантирует стабильную работу системы даже на слабых серверах при обработке огромных выгрузок.
Одной из главных проблем при работе с JSON является формат даты. В самом стандарте JSON нет типа «Дата», поэтому разработчики используют разные способы передачи времени (ISO 8601, метки времени и т.д.). В 1С 8.3 реализована отличная поддержка дат в формате ISO 8601.
Рассмотрим, как заставить платформу автоматически распознавать даты. Для этого используется параметр ФункцияВосстановления. Мы можем передать туда имя функции, которая будет анализировать каждое значение и при необходимости преобразовывать его в Дата 1С.
Посмотрим на пример реализации такой функции:
&НаСервере
Функция МояФункцияВосстановления(Свойство, Значение, ДополнительныеПараметры) Экспорт
// Если значение подозрительно похоже на дату в формате ISO
Если ТипЗнч(Значение) = Тип("Строка") И СтрДлина(Значение) = 19 Тогда
// Пытаемся преобразовать строку в дату
Попытка
Возврат Дата(СтрЗаменить(СтрЗаменить(Значение, "T", ""), "-", ""));
Исключение
Возврат Значение;
КонецПопытки;
КонецЕсли;
Возврат Значение;
КонецФункции
Запуск чтения с использованием функции восстановления выглядит так:
Чтение = Новый ЧтениеJSON;
Чтение.УстановитьСтроку(ТекстJSON);
Данные = ПрочитатьJSON(Чтение, Ложь, , "МояФункцияВосстановления", ЭтотОбъект);
Проанализируем несколько важных моментов, которые помогут избежать ошибок при работе с JSON:
Попытка...Исключение. Это спасет вашу программу от аварийного завершения при получении некорректного JSON.ЗаписатьJSON работает по тем же принципам. Если вам нужно выгрузить данные, используйте этот объект для формирования правильной структуры.СериализаторXDTO может быть эффективнее, так как он позволяет напрямую преобразовывать JSON в объекты метаданных (например, в СправочникОбъект или ДокументОбъект).Рассмотрим краткий пример использования ЗаписатьJSON для создания файла:
Запись = Новый ЗаписьJSON;
Запись.ОткрытьФайл("C:\temp\output.json");
// Настройки сериализации (отступы для читаемости)
ПараметрыЗаписи = Новый ПараметрыЗаписиJSON(Ложь, Символы.Таб);
// Записываем структуру
ЗаписатьJSON(Запись, СтруктураДанных, ПараметрыЗаписи);
Запись.Закрыть();
Подводя итог, можно сказать, что механизмы 1С для работы с JSON являются очень гибкими и мощными. Выбор между ПрочитатьJSON и потоковым чтением ЧтениеJSON должен зависеть исключительно от объема обрабатываемых данных и требований к производительности. Мы рекомендуем начинать с более простых методов и переходить к сложным только при возникновении реальных проблем с памятью или скоростью работы.