Какой код состояния HTTP возвращать в 1С и как правильно передавать ошибки

Программист 1С v8.3 (Управляемые формы) IT и автоматизация бизнеса
← На главную

При разработке интеграций через HTTP-сервисы в системе 1С:Предприятие программисты часто сталкиваются с дилеммой: какой код состояния (Status Code) вернуть клиенту, если данных нет или произошла ошибка. Использование стандартного кода 200 OK для всех ситуаций упрощает разработку, но нарушает общепринятые стандарты REST API. С другой стороны, использование кодов ошибок (4xx, 5xx) в 1С может сопровождаться трудностями при передаче описания проблемы. В этой статье мы подробно разберем, как правильно проектировать ответы ваших сервисов.

Разбираемся с кодами 200, 204 и 404 для пустых результатов

Рассмотрим ситуацию: клиент запрашивает список заказов по определенному контрагенту, но заказов в базе нет. Какой код должен вернуть сервер? Проанализируем три основных варианта:

  1. Код 200 OK + пустой массив: Это наиболее правильный подход для запросов списков. Если запрос корректен, фильтры понятны серверу, но данных просто нет — это успешная операция. Мы возвращаем пустую коллекцию (например, [] в JSON). Это не является ошибкой сервера или отсутствием ресурса.
  2. Код 204 No Content: Согласно спецификации, этот код означает, что запрос обработан успешно, но сервер намеренно не возвращает никакого содержимого. Обычно его используют для методов PUT или POST, когда клиенту не нужно подтверждение в виде обновленного объекта. Использовать его для GET-запросов на получение данных не рекомендуется, так как многие библиотеки-клиенты могут интерпретировать отсутствие тела как технический сбой.
  3. Код 404 Not Found: Этот код следует возвращать только тогда, когда запрашивается конкретный уникальный ресурс по его идентификатору (ID, GUID). Если вы обратились по адресу /orders/123 и заказа 123 не существует — это 404. Но если вы обратились к /orders?client=123 и список пуст — это 200.

Проблема передачи тела ответа при ошибках в 1С

Часто разработчики замечают, что при установке кода, отличного от 200, метод УстановитьТелоИзСтроки() в объекте HTTPСервисОтвет как будто игнорируется, и клиент получает стандартную страницу ошибки веб-сервера. Разберем, почему так происходит.

Выясним причину: в большинстве случаев виноват не код в 1С, а настройки веб-сервера (IIS или Apache), на котором опубликован сервис. Веб-серверы по умолчанию перехватывают ответы с кодами 4xx и 5xx, заменяя ваше информативное JSON-описание своей стандартной разметкой (Custom Errors).

Для решения этой проблемы в IIS: необходимо в файле web.config вашего приложения установить параметр existingResponse="PassThrough". Это заставит IIS пропускать ответ от 1С "как есть", сохраняя ваше тело сообщения.

Также важно помнить: свойство Причина (Reason Phrase) в ответе — это устаревающая практика. В протоколе HTTP/2 текст причины вообще не передается. Всю информацию об ошибке нужно помещать именно в тело ответа в формате JSON.

Стандарт RFC 7807: Правильное описание ошибок

Вместо того чтобы изобретать свой формат передачи ошибок, проанализируем стандарт RFC 7807 (Problem Details for HTTP APIs). Согласно ему, при возникновении ошибки (например, 400 Bad Request), сервер должен вернуть JSON со структурой, понятной любому разработчику:

Рассмотрим пример формирования такого ответа на стороне 1С:


Ответ = Новый HTTPСервисОтвет(400);
ДанныеОшибки = Новый Структура;
ДанныеОшибки.Вставить("status", 400);
ДанныеОшибки.Вставить("title", "Ошибка валидации данных");
ДанныеОшибки.Вставить("detail", "Поле 'ИНН' должно содержать 10 или 12 цифр.");

ЗаписьJSON = Новый ЗаписьJSON;
ЗаписьJSON.УстановитьСтроку();
ЗаписатьJSON(ЗаписьJSON, ДанныеОшибки);
СтрокаJSON = ЗаписьJSON.Закрыть();

Ответ.УстановитьТелоИзСтроки(СтрокаJSON, КодировкаТекста.UTF8, ИспользованиеByteOrderMark.НеИспользовать);
Ответ.Заголовки.Вставить("Content-Type", "application/problem+json");
Возврат Ответ;

Обработка ошибок на стороне клиента в 1С

Когда вы вызываете внешний сервис из 1С с помощью объекта HTTPСоединение, важно правильно обработать результат. По умолчанию методы типа ВызватьHTTPМетод() или Получить() могут вызывать исключение при кодах 4xx и 5xx, если не настроены определенные параметры.

Рассмотрим правильную схему обработки ответа на стороне клиента:


Попытка
    Ответ = Соединение.ВызватьHTTPМетод("GET", "api/v1/resource");
    
    Если Ответ.КодСостояния = 200 Тогда
        // Обрабатываем успешные данные
        ЧтениеJSON = Новый ЧтениеJSON;
        ЧтениеJSON.УстановитьСтроку(Ответ.ПолучитьТелоКакСтроку());
        Результат = ПрочитатьJSON(ЧтениеJSON);
    ИначеЕсли Ответ.КодСостояния = 404 Тогда
        Сообщить("Объект не найден в базе источника");
    Иначе
        // Обрабатываем бизнес-ошибку из тела ответа
        ТелоОшибки = Ответ.ПолучитьТелоКакСтроку();
        Сообщить("Сервер вернул ошибку: " + ТелоОшибки);
    КонецЕсли;
    
Исключение
    // Сюда мы попадем при сетевых ошибках или таймаутах
    Сообщить("Ошибка связи: " + ОписаниеОшибки());
КонецПопытки;

Иерархия кодов и миф о "404.1"

В обсуждениях иногда всплывают коды с точкой, например 404.1. Важно понимать: в протоколе HTTP таких кодов не существует. Это внутренние подкоды веб-сервера IIS, которые он использует для своих логов. По сети клиенту всегда уходит только основной трехзначный код. Если вам нужно передать специфический код бизнес-ошибки (например, "Ошибка №15: Недостаточно остатка на складе"), передавайте его внутри JSON-тела, оставляя HTTP-код на уровне общей категории 400 Bad Request или 422 Unprocessable Entity.

Резюме и рекомендации

Подведем итог наших изысканий по работе с HTTP в 1С:

  1. Для пустых списков всегда возвращайте 200 OK и пустой массив [].
  2. Для отсутствующих конкретных объектов (по ID) используйте 404 Not Found.
  3. Для ошибок бизнес-логики (не прошли проверки) используйте 400 Bad Request.
  4. Никогда не полагайтесь на текст "Причины" в заголовке ответа, всегда используйте тело (Body) в формате JSON.
  5. Проверьте настройки веб-сервера, если при попытке вернуть 4xx код вы получаете стандартную страницу "Internal Server Error" или "Not Found" от самого сервера, а не данные из 1С.

Следуя этим правилам, вы сделаете свои интеграции предсказуемыми, надежными и соответствующими мировым стандартам разработки ПО.

← На главную