При интеграции 1С с внешними системами (веб-приложениями, мобильными клиентами на Java, C# или JavaScript) часто возникает необходимость выполнять произвольные запросы к базе данных и получать результат в стандартном формате JSON. Рассмотрим по шагам, как устроена обработка входящих HTTP-запросов на стороне 1С, как правильно считать текст запроса и преобразовать выборку в JSON.
Разберем базовую структуру метода HTTP-сервиса. В конфигурации 1С создается объект HTTP-сервис с шаблоном URL и методом (например, GET, POST или PUT). При вызове метода платформа передает в обработчик объект типа HTTPСервисЗапрос, а функция должна вернуть объект HTTPСервисОтвет.
Передавать текст запроса можно двумя способами:
ЗапросHTTP.ПараметрыЗапроса.Получить("ИмяПараметра").POST или PUT). Текст считывается методом ЗапросHTTP.ПолучитьТелоКакСтроку().Рассмотрим пример функции-обработчика, которая принимает текст запроса из параметров, выполняет его в базе 1С и возвращает ответ в формате JSON:
Функция ВыполнитьЗапросGET(ЗапросHTTP)
Ответ = Новый HTTPСервисОтвет(200);
Ответ.Заголовки.Вставить("Content-Type", "application/json; charset=utf-8");
// Получаем текст запроса из параметров URL
ТекстЗапроса = ЗапросHTTP.ПараметрыЗапроса.Получить("QueryText");
Если Не ЗначениеЗаполнено(ТекстЗапроса) Тогда
Ответ.КодСостояния = 400;
Ответ.УстановитьТелоИзСтроки("{""error"": ""Не передан текст запроса""}");
Возврат Ответ;
КонецЕсли;
Попытка
Запрос1С = Новый Запрос;
Запрос1С.Текст = ТекстЗапроса;
РезультатЗапроса = Запрос1С.Выполнить();
ТекстJSON = ПреобразоватьРезультатВJSON(РезультатЗапроса);
Ответ.УстановитьТелоИзСтроки(ТекстJSON);
Исключение
Ответ.КодСостояния = 500;
Ответ.УстановитьТелоИзСтроки("{""error"": """ + ОписаниеОшибки() + """}");
КонецПопытки;
Возврат Ответ;
КонецФункции
Платформа 1С не умеет напрямую передавать объект РезультатЗапроса в функцию ЗаписатьJSON(). Для сериализации необходимо обойти выборку и сформировать массив структур, где ключами выступают имена колонок, а значениями — данные ячеек.
При этом важно учитывать ссылочные типы данных 1С (такие как СправочникСсылка, ДокументСсылка и др.). Если попытаться записать ссылочный объект в JSON напрямую без обработки, платформа выдаст ошибку. Ссылочные значения необходимо приводить к текстовому виду с помощью функции Строка() или XMLСтрока().
Проанализируем код функции конвертации результата запроса в строку JSON:
Функция ПреобразоватьРезультатВJSON(РезультатЗапроса)
Выборка = РезультатЗапроса.Выбрать();
МассивСтрок = Новый Массив;
КолонкиЗапроса = РезультатЗапроса.Колонки;
Пока Выборка.Следующий() Цикл
СтрокаДанных = Новый Структура;
Для Каждого Колонка Из КолонкиЗапроса Цикл
ИмяКолонки = Колонка.Имя;
Значение = Выборка[ИмяКолонки];
// Проверяем, является ли значение ссылочным типом 1С
Если ЗначениеЗаполнено(Значение) И Метаданные.НайтиПоТипу(ТипЗнч(Значение)) <> Неопределено Тогда
СтрокаДанных.Вставить(ИмяКолонки, Строка(Значение));
Иначе
СтрокаДанных.Вставить(ИмяКолонки, Значение);
КонецЕсли;
КонецЦикла;
МассивСтрок.Добавить(СтрокаДанных);
КонецЦикла;
ЗаписьJSON = Новый ЗаписьJSON;
ЗаписьJSON.УстановитьСтроку();
// Записываем массив структур в формат JSON
ЗаписатьJSON(ЗаписьJSON, МассивСтрок);
Возврат ЗаписьJSON.Закрыть();
КонецФункции
Передача произвольного текста запроса с внешнего фронтенда или сторонней системы не всегда оправдана с точки зрения безопасности и поддерживаемости кода. Изменение структуры метаданных 1С может сломать внешние запросы.
Более надежным решением является передача в HTTP-сервис не самого текста запроса, а идентификатора отчета (или операции) и параметров (например, периода или фильтра по организации). В таком случае текст запроса хранится и контролируется на стороне 1С, а внешнее приложение получает готовые структурированные данные или готовый для отображения HTML/SVG-код.