При интеграции «1С:Предприятия» с внешними облачными API, веб-сервисами или государственными информационными порталами по протоколу HTTPS разработчики часто сталкиваются с исключением:
«Ошибка работы с Интернет: Удаленный узел не прошел проверку»
Чаще всего эта ошибка проявляется при вызове методов HTTPСоединение.Получить(), HTTPСоединение.ОтправитьДляОбработки() или HTTPСоединение.ВызватьHTTPМетод(). При этом в веб-браузере тот же самый адрес открывается корректно и без предупреждений безопасности. Разберем по шагам, почему возникает эта проблема, как устроена работа с TLS/SSL в платформе 1С и какие существуют способы устранения ошибки — от быстрого тестового решения до надежной настройки в промышленной среде.
Начиная с версии платформы 8.3.10, механизмы работы с защищенными сетевыми протоколами были существенно переработаны. Платформа перешла на использование современных версий криптографических библиотек OpenSSL, протокола TLS 1.2 по умолчанию и строгую валидацию всей цепочки доверия SSL-сертификатов.
Выясним причину, почему браузер открывает страницу без ошибок, а 1С возвращает сбой валидации:
USR1CV8). У этой учетной записи изолированный профиль и свое хранилище доверенных корневых центров, в котором могут отсутствовать сертификаты, установленные для обычных пользователей.Новый ЗащищенноеСоединениеOpenSSL() неинициализированных или некорректных объектов сертификатов клиента и УЦ активирует нежелательные режимы строгой взаимной проверки (mTLS).Рассмотрим подробнее практические варианты решения задачи.
Проанализируем базовый конструктор объекта ЗащищенноеСоединениеOpenSSL. Согласно документации 1С, если в конструктор не передаются параметры удостоверяющих центров, проверка подлинности сертификата сервера и проверка цепочки доверия отключаются. При этом сам трафик по-прежнему шифруется по стандарту TLS/HTTPS.
Посмотрим на пример кода с инициализацией пустого защищенного соединения:
// Создаем защищенное соединение без проверки цепочки сертификатов
ЗащищенноеСоединение = Новый ЗащищенноеСоединениеOpenSSL();
// Инициализируем HTTP-соединение с защищенным каналом
Сервер = "www.googleapis.com";
Порт = 443;
Таймаут = 30;
Соединение = Новый HTTPСоединение(
Сервер,
Порт,
, // Пользователь
, // Пароль
, // Прокси
Таймаут,
ЗащищенноеСоединение
);
Запрос = Новый HTTPЗапрос("drive/v3/files/ИДЕНТИФИКАТОР_ФАЙЛА/?key=ВАШ_API_КЛЮЧ");
Ответ = Соединение.Получить(Запрос);
Если Ответ.КодСостояния = 200 Тогда
ТелоОтвета = Ответ.ПолучитьТелоКакСтроку();
// Обработка полученного JSON
КонецЕсли;
Преимущества: Простота реализации, отсутствие привязки к локальным базам сертификатов Windows, одинаковое поведение на клиентских и серверных машинах под Windows и Linux.
Ограничения: Данный способ не проверяет подлинность сервера, что теоретически делает канал уязвимым к атакам типа Man-in-the-Middle (MitM) в незащищенных локальных сетях. Для внутренних сервисов, тестовых сред и интеграций общего назначения этот вариант является наиболее популярным.
Если проект требует строгого контроля безопасности и проверки подлинности удаленного узла, наилучшим решением является использование актуального бандла корневых сертификатов в формате PEM. Это избавляет от зависимости от операционной системы и корректно работает на серверах под управлением Linux.
Разберем по шагам реализацию этого способа:
cacert.pem из репозитория cURL/Mozilla).USR1CV8 (например, C:\1C_Cert\cacert.pem или /opt/1c/certs/cacert.pem).СертификатыУдостоверяющихЦентровФайлы для инициализации защищенного соединения.Посмотрим на пример реализации в программном коде:
ПутьКСерт = "C:\1C_Cert\cacert.pem";
// Указываем путь к файлу с доверенными корневыми центрами
СертификатыУЦ = Новый СертификатыУдостоверяющихЦентровФайлы(ПутьКСерт);
// Первый параметр (сертификат клиента) оставляем Неопределено, если mTLS не требуется
ЗащищенноеСоединение = Новый ЗащищенноеСоединениеOpenSSL(Неопределено, СертификатыУЦ);
Соединение = Новый HTTPСоединение(
"www.googleapis.com",
443,
,
,
,
30,
ЗащищенноеСоединение
);
Запрос = Новый HTTPЗапрос("drive/v3/files/ИД_ФАЙЛА/?key=API_KEY");
Ответ = Соединение.Получить(Запрос);
Этот метод гарантирует строгую проверку удаленного сервера без риска возникновения ошибок из-за особенностей системного хранилища Windows.
Если необходимо использовать системное хранилище через объект Новый СертификатыУдостоверяющихЦентровWindows(), следует убедиться, что в операционной системе обновлены доверенные корневые центры сертификации (включая GTS Root R1/R2, GlobalSign, DigiCert, ISRG Root X1 и др.).
Разберем шаги обновления сертификатов в Windows:
certutil -generateSSTFromWU roots.sst
certutil -addstore -f Root roots.sst
При написании кода обратите внимание на параметры конструктора клиентских сертификатов: если сервис не требует авторизации по личному сертификату пользователя (mTLS), первым параметром всегда следует передавать Неопределено, а не пустой объект Новый СертификатКлиентаWindows().
Посмотрим на корректный пример использования системных сертификатов:
// Передаем Неопределено в качестве первого параметра, чтобы не инициировать поиск клиентских сертификатов
СертификатыУЦ = Новый СертификатыУдостоверяющихЦентровWindows();
ЗащищенноеСоединение = Новый ЗащищенноеСоединениеOpenSSL(Неопределено, СертификатыУЦ);
Соединение = Новый HTTPСоединение("www.googleapis.com", 443, , , , 30, ЗащищенноеСоединение);
Запрос = Новый HTTPЗапрос("drive/v3/files/?key=API_KEY");
Ответ = Соединение.Получить(Запрос);
Проанализируем, в каких ситуациях какой метод предпочтителен: