Почему не работает отправка JSON из 1С и как исправить ошибки 415 и 422

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

При интеграции 1С с внешними информационными системами (например, ГИС ТКО или сервисами ППК РЭО) разработчики часто сталкиваются с ситуацией, когда запрос возвращает ошибки 415 Unsupported Media Type или 422 Unprocessable Entity. В этой статье мы подробно разберем причины возникновения этих ошибок на примере реального кейса, проанализируем типичные ошибки при формировании JSON и выясним, как правильно передавать данные в формате multipart/form-data.

Разбор первой ошибки: Почему Строка(Данные) — это не JSON

Рассмотрим ситуацию, когда разработчик пытается преобразовать структуру 1С в текст для отправки. Одной из самых распространенных ошибок является использование встроенной функции Строка(). Давайте проанализируем, что происходит в коде:


// ОШИБОЧНЫЙ КОД
Данные = Новый Структура;
Данные.Вставить("objectId", "ce0dec40-5f72-447c-9d5e-abe4bebffdaa");
// ... заполнение данных ...
СтрокаДанных = Строка(Данные); 
// В переменную СтрокаДанных попадет текст "Структура", а не содержимое полей!

В системе 1С функция Строка() для объекта типа Структура возвращает лишь строковое представление типа объекта. В результате на сервер уходит текст "Структура", который не является валидным JSON-объектом. Это гарантированно приведет к ошибке 422 (если сервер ожидал JSON, но получил неверный формат) или ошибке парсинга на стороне принимающего шлюза.

Для правильного преобразования данных в формат JSON необходимо использовать объект ЗаписьJSON. Разберем правильный подход:


ЗаписьJSON = Новый ЗаписьJSON;
ПараметрыЗаписиJSON = Новый ПараметрыЗаписиJSON(ПереносСтрокJSON.Нет);
ЗаписьJSON.УстановитьСтроку(ПараметрыЗаписиJSON);
ЗаписатьJSON(ЗаписьJSON, Данные);
РезультатJSON = ЗаписьJSON.Закрыть();
// Теперь в РезультатJSON действительно находится валидная JSON-строка

Проблема использования синтаксиса curl в методах COM-объектов

Проанализируем еще одну критическую ошибку. В попытках отправить файл через MSXML2.XMLHTTP, разработчики часто копируют синтаксис консольной утилиты curl, указывая символ @ перед путем к файлу:

Запрос.send("file=@" + ПутьКФайлу);

Важно понимать: COM-объекты Windows или стандартные объекты 1С (HTTPЗапрос) не умеют интерпретировать символ @ как команду «прочитать файл с диска». Они воспринимают это выражение как обычную текстовую строку. В итоге сервер получает не содержимое файла, а просто путь к нему (который ему бесполезен), что снова вызывает ошибку 422, так как данные не прошли валидацию.

Формат multipart/form-data: особенности реализации

Если спецификация API (как в случае с ГИС ТКО) требует использования multipart/form-data, это означает, что данные должны передаваться не в виде «чистого» JSON в теле запроса, а как часть сложной многокомпонентной формы. Ошибка 415 как раз указывает на то, что вы пытаетесь отправить application/json там, где сервер ждет составную форму.

Рассмотрим, как правильно сформировать такой запрос. Современная платформа 1С (начиная с 8.3.10) предоставляет для этого удобные инструменты. Вместо ручной сборки границ (boundary), мы можем использовать метод СформироватьТелоСМногокомпонентнымиДанными объекта HTTPЗапрос.

Выясним, как это реализовать пошагово:

  1. Создаем массив элементов тела запроса.
  2. Помещаем туда JSON-данные как «файл».
  3. Устанавливаем соответствие параметров, которые ожидает сервер (обычно параметр называется file).

// 1. Формируем JSON
ЗаписьJSON = Новый ЗаписьJSON;
ЗаписьJSON.УстановитьСтроку();
ЗаписатьJSON(ЗаписьJSON, СтруктураДанных);
СтрокаJSON = ЗаписьJSON.Закрыть();

// 2. Подготавливаем HTTP запрос
Граница = СтрЗаменить(Строка(Новый УникальныйИдентификатор), "-", "");
Запрос = Новый HTTPЗапрос("/api/v1/upload");
Запрос.Заголовки.Вставить("Content-Type", "multipart/form-data; boundary=" + Граница);

// 3. Формируем тело запроса
Разделитель = "--" + Граница;
Тело = Новый ПотокВПамяти;
ЗаписьТекста = Новый ЗаписьТекста(Тело, КодировкаТекста.UTF8);

ЗаписьТекста.ЗаписатьСтроку(Разделитель);
// Имя "file" должно соответствовать требованиям документации API
ЗаписьТекста.ЗаписатьСтроку("Content-Disposition: form-data; name=""file""; filename=""data.json""");
ЗаписьТекста.ЗаписатьСтроку("Content-Type: application/json");
ЗаписьТекста.ЗаписатьСтроку(""); // Пустая строка перед данными
ЗаписьТекста.ЗаписатьСтроку(СтрокаJSON);
ЗаписьТекста.ЗаписатьСтроку(Разделитель + "--");

ЗаписьТекста.Закрыть();
Запрос.УстановитьТелоИзПотока(Тело);

Почему возникает ошибка 422 при валидном JSON?

Если формат запроса исправлен (используется multipart/form-data), а JSON сформирован корректно, но сервер все равно возвращает 422 Unprocessable Entity, значит проблема кроется в содержимом данных. Проанализируем типичные причины для систем учета (например, весового контроля):

Рекомендации по отладке

Для того чтобы точно понять, что именно уходит из 1С на сервер, мы рекомендуем использовать прокси-отладчики, такие как Fiddler или Charles. Настройте 1С на работу через прокси:


Прокси = Новый ИнтернетПрокси;
Прокси.Установить("http", "127.0.0.1", 8888); // Порт Fiddler
Соединение = Новый HTTPСоединение("api.server.ru",,,, Прокси);

Проанализировав "сырой" HTTP-трафик, вы сразу увидите, действительно ли там JSON или просто слово "Структура", а также правильно ли расставлены границы boundary в многокомпонентном запросе.

Подводя итог, отметим, что успешная интеграция зависит от трех факторов: правильной сериализации через ЗаписатьJSON, корректного указания Content-Type и строгого соблюдения типов данных (числа как числа, даты в ISO-формате), требуемых внешней системой.

← На главную