При работе с JSON в среде 1С:Предприятие программисты часто сталкиваются с трудностями при попытке вставить готовый JSON-код непосредственно в текст модуля. Основная проблема заключается в том, что стандарт JSON активно использует двойные кавычки и фигурные скобки, которые в 1С имеют специальное назначение. Если просто скопировать JSON-структуру в переменную, конфигуратор выдаст ошибку синтаксиса, например, «Ожидается ключевое слово 'КонецПроцедуры'», так как парсер 1С воспримет первую же кавычку внутри JSON как завершение строки кода.
В данной статье мы подробно рассмотрим, как правильно оформлять такие строки, разберем механизмы экранирования и изучим современные инструменты платформы для автоматизации этой задачи.
Давайте проанализируем ситуацию: когда вы пишете СтрокаJSON = "{"widget": "on"}";, платформа интерпретирует это следующим образом: открывается строковый литерал символом ", затем идет текст до следующей кавычки перед словом widget. В этот момент 1С считает, что строка закончилась. Все последующие символы (текст JSON) воспринимаются как ошибочный код вне контекста строки, что и приводит к аварийному завершению компиляции модуля.
Если нам необходимо жестко прописать JSON внутри кода, мы должны соблюдать два правила синтаксиса 1С:
|."").Рассмотрим пример правильного написания JSON-структуры в коде:
Процедура Кнопка1Нажатие(Элемент)
СтрокаJSON =
"{
|""widget"": {
| ""debug"": ""on"",
| ""window"": {
| ""title"": ""Sample Widget"",
| ""width"": 500
| }
|}
|}";
// Теперь строку можно прочитать
Чтение = Новый ЧтениеJSON;
Чтение.УстановитьСтроку(СтрокаJSON);
Данные = ПрочитатьJSON(Чтение);
Чтение.Закрыть();
КонецПроцедуры
Обратите внимание, что использование вертикальной черты позволяет сохранять структуру JSON наглядной, а удвоенные кавычки корректно интерпретируются платформой как часть текстовых данных. Для автоматической генерации такого кода 1С, валидации и форматирования JSON-строк можно использовать инструмент для валидации и генерации кода 1С.
Иногда JSON формируется динамически из строковых переменных. В этом случае нам нужно самостоятельно «маскировать» символы, которые могут нарушить структуру JSON (переносы строк, табуляции, обратные слеши). Проанализируем вспомогательную функцию, которая поможет подготовить обычный текст для вставки в значение JSON-поля:
Функция MyJSONМаскировать(Знач Стр)
// Важно: сначала заменяем обратный слеш, чтобы не испортить последующие замены
Стр = СтрЗаменить(Стр, "\", "\\");
Стр = СтрЗаменить(Стр, Символы.ПС, "\n");
Стр = СтрЗаменить(Стр, Символы.ВК, "\r");
Стр = СтрЗаменить(Стр, Символы.Таб, "\t");
Стр = СтрЗаменить(Стр, "/", "\/");
Стр = СтрЗаменить(Стр, """", "\""");
Возврат Стр;
КонецФункции
Эта функция реализует базовые требования стандарта RFC 7159. Выясним причину важности порядка замен: если вы сначала замените символ переноса строки на \n, а потом начнете заменять одиночный слеш на двойной, то ваш \n превратится в \\n, что будет воспринято парсером как обычный текст, а не управляющий символ.
Выясним наиболее надежный способ работы с JSON. Вместо того чтобы вручную склеивать строки и следить за кавычками, следует использовать штатные средства платформы. Объекты ЗаписьJSON и ПараметрыЗаписиJSON автоматически выполняют все правила экранирования.
Рассмотрим по шагам процесс создания валидного JSON:
// 1. Подготовим данные в виде Структуры или Массива
ДанныеДляЗаписи = Новый Структура;
ДанныеДляЗаписи.Вставить("Название", "Пример ""Экранирования""");
ДанныеДляЗаписи.Вставить("Путь", "C:\Windows\System32");
// 2. Настроим запись
Запись = Новый ЗаписьJSON;
ПараметрыЗаписи = Новый ПараметрыЗаписиJSON(ПереносСтрокJSON.Авто, " ");
Запись.УстановитьСтроку(ПараметрыЗаписи);
// 3. Сериализуем данные
ЗаписатьJSON(Запись, ДанныеДляЗаписи);
// 4. Получим результат
РезультатJSON = Запись.Закрыть();
// Результат будет: {"Название": "Пример \"Экранирования\"", "Путь": "C:\\Windows\\System32"}
Использование метода ЗаписатьJSON() гарантирует, что все вложенные кавычки будут экранированы символом \, а пути к файлам получат правильные двойные слеши. Это исключает ошибки при передаче данных через веб-сервисы или HTTP-запросы.
Если JSON-данные приходят извне (например, от другого приложения или API), не стоит пытаться копировать их содержимое в код вручную. Проанализируем ситуацию, когда данные находятся в текстовом файле. Вместо копирования текста в конфигуратор, используем объект ТекстовыйДокумент или чтение напрямую из файла:
ИмяФайла = "C:\temp\data.json";
ТекстДок = Новый ТекстовыйДокумент;
ТекстДок.Прочитать(ИмяФайла, КодировкаТекста.UTF8);
СтрокаJSON = ТекстДок.ПолучитьТекст();
// Теперь разбираем строку в объект 1С
Чтение = Новый ЧтениеJSON;
Чтение.УстановитьСтроку(СтрокаJSON);
СтруктураДанных = ПрочитатьJSON(Чтение);
Чтение.Закрыть();
Этот подход позволяет избежать любых проблем с синтаксисом 1С, так как данные загружаются напрямую в память как значение переменной, минуя этап компиляции исходного кода модуля. При регулярном получении файлов извне задачу можно автоматизировать с помощью программы для автоматического сбора файлов из почты, FTP и HTTP.
Стоит учитывать, что в старых версиях платформы (8.1, 8.2 до определенных релизов) нативной поддержки JSON нет. Если вам нужно передать JSON из современной базы 8.3 в старую систему на 8.1, рекомендуется использовать максимально простой формат данных:
Content-Type: application/json.Для передачи данных из 8.3 в 8.1 через POST-запрос, используйте следующий шаблон:
Запрос = Новый HTTPЗапрос("/api/data");
Запрос.Заголовки.Вставить("Content-Type", "application/json");
// Важно явно указать кодировку без BOM
Запрос.УстановитьТелоИзСтроки(РезультатJSON, КодировкаТекста.UTF8, ИспользованиеByteOrderMark.НеИспользовать);
Таким образом, мы рассмотрели все основные способы работы с экранированием. Помните: ручное экранирование в коде допустимо только для коротких констант. Для любых реальных данных всегда выбирайте объект ЗаписьJSON, который сделает работу за вас и обеспечит стопроцентную валидность итогового файла.