При интеграции 1С с внешними системами (биржевыми терминалами, оборудованием или поставщиками данных) часто возникает необходимость подписки на события COM-объекта. В платформе 1С для этих целей предусмотрена команда ДобавитьОбработчик. Однако при работе с подпиской на события возникает множество нюансов: как вызываются процедуры-обработчики, куда деваются события при высокой частоте поступления и стоит ли использовать асинхронный вызов через ОписаниеОповещения.
Разберем подробнее технические особенности работы этого механизма и проанализируем, как избежать падения приложения и потери данных.
Рассмотрим, что происходит «под капотом» 1С, когда выполняется команда подписки на событие COM-объекта. Связывание события с процедурой 1С выполняется следующим образом:
// Прикрепление процедуры-обработчика к событию COM-объекта
ДобавитьОбработчик SmartCOM.AddTick, SmartCOM_AddTick;
С точки зрения платформы вызов процедуры-обработчика происходить синхронно. Попытка обернуть код внутри процедуры в Новый ОписаниеОповещения не сделает выполнение многопоточным, так как платформа 1С исполняет код в одном главном потоке клиенского приложения.
Поведение системы зависит от типа самого COM-объекта:
Процедура 1С будет вызвана только тогда, когда главный поток 1С свободен и забирает сообщения из очереди. Если внутри обработчика выполняется длительный вызов или тяжелый расчет, события начинают накапливаться в очереди. При превышении таймаута ожидания со стороны COM-объекта или переполнении буфера новые тики и события теряются, а система может выдать ошибку взаимодействия или аварийно завершить работу.
Проанализируем ключевые ограничения, с которыми сталкиваются разработчики при использовании ДобавитьОбработчик:
ДобавитьОбработчик работает только в клиентском контексте (тонкий или толстый клиент). На стороне сервера (в фоновых заданиях или процессе rphost) отсутствует петля обработки сообщений GUI Windows (GetMessage / DispatchMessage), поэтому подписка на события COM на сервере приведет к зависанию или ошибке.ОбработкаПрерыванияПользователя), приостанавливают вызов обработчиков. В этот момент входящие события накапливаются и могут быть утеряны.dllhost.exe).Если входящий поток событий слишком интенсивный (например, биржевые тики котировок, поступающие несколько раз в секунду), прямая обработка через 1С становится нестабильной. Рассмотрим три проверенных подхода для решения этой задачи.
Создается внешняя компонента (например, на C# или C++), которая подключается к COM-объекту в отдельном потоке. Компонента самостоятельно принимает события и складывает их в кольцевой буфер в оперативной памяти. Передача данных в 1С происходит либо пачками (раз в 200–500 мс), либо через стандартный механизм ОбработкаВнешнегоСобытия.
Если COM-объект позволяет считывать данные по запросу, подписку через ДобавитьОбработчик отключают вовсе. В 1С настраивается регулярный опрос с помощью функции ПодключитьОбработчикОжидания:
// Подключение опроса каждые 2 секунды
ПодключитьОбработчикОжидания("ЗапроситьДанныеCOM", 2, Ложь);
Процедура ЗапроситьДанныеCOM() Экспорт
// Получение массива последних событий напрямую из объекта
Данные = COMОбъект.GetLastTicks();
// Обработка полученного массива
КонецПроцедуры
Для создания отказоустойчивых систем сбора данных создается отдельная служба или скрипт (на C#, Python или Go), которая работает в фоновом режиме 24/7 и взаимодействует с COM-объектом. При наступлении нужного бизнес-условия сервис передает итоговую информацию в 1С через HTTP-сервис или напрямую отправляет уведомление пользователю.
Выяснив особенности работы очереди сообщений Windows и платформы 1С, вы сможете выбрать наиболее надежный способ взаимодействия с COM-объектами и избежать потерь важных данных.