Разработка и Конфигурация · 11 мин
Как сделать подписку на событие в 1С
Как сделать подписку на событие в 1С: создание обработчиков ПриЗаписи и ОбработкаПроведения, настройка источников, типичные ошибки и проверка результата.
Подписка на событие в 1С — это механизм, который позволяет выполнять собственный код при наступлении стандартных событий объектов: записи документа, проведения, установки пометки удаления и других. Главное преимущество подписок — возможность расширять логику конфигурации, не изменяя типовые модули объектов, что критично для конфигураций на поддержке.
Механизм работает одинаково в большинстве типовых конфигураций на платформе 8.3: вы создаёте объект метаданных «Подписка на событие», указываете источник (типы объектов, для которых она сработает), выбираете событие и пишете обработчик в общем модуле. Дальше платформа сама вызывает ваш код каждый раз, когда происходит указанное событие.
Типичные сценарии применения: автоматическое заполнение реквизитов при записи, контроль дублей, запись в регистры сведений, отправка уведомлений, синхронизация с внешними системами. Ниже разобраны пошаговое создание подписки, выбор события, требования к обработчику, проверка результата и частые ошибки.
Когда подписка на событие — правильный инструмент
Подписка оправдана, когда одна и та же логика должна срабатывать для нескольких типов объектов. Например, нужно фиксировать автора последнего изменения для всех документов — вместо правки каждого модуля объекта создаётся одна подписка с источником «ДокументОбъект» по всем нужным типам.
Второй случай — конфигурация на полной поддержке, где изменение типовых модулей нежелательно. Подписка добавляется как новый объект метаданных и не затрагивает типовой код, поэтому обновление конфигурации проходит без конфликтов.
Подписка не подходит, когда нужно изменить поведение только одного конкретного объекта сложным образом или когда требуется интерактивное взаимодействие с пользователем: обработчики подписок выполняются на сервере и не могут открывать формы или задавать вопросы пользователю.
Способы добавить свою логику
Подходит для нескольких типов объектов и конфигураций на поддержке. Ограничение: только серверный контекст, нет интерактива.
Полный контроль над конкретным объектом, но требует снятия с поддержки или расширения.
Позволяет дополнять модули объектов без снятия с поддержки, но сложнее в сопровождении при множестве объектов.
Пошаговое создание подписки в конфигураторе
Откройте конфигуратор, разверните в дереве конфигурации ветку «Общие» и найдите пункт «Подписки на события». Через контекстное меню выберите «Добавить» — откроется палитра свойств нового объекта.
Задайте имя подписки, например «ЗаписатьИсториюИзменений». Затем настройте три ключевых свойства: источник, событие и обработчик. Источник выбирается кнопкой выбора в поле «Источник» — откроется окно с деревом типов, где нужно отметить конкретные объекты (например, документы «РеализацияТоваровУслуг» и «ПоступлениеТоваровУслуг»).
В свойстве «Событие» выберите нужное событие из выпадающего списка, затем нажмите лупу у поля «Обработчик» — платформа предложит создать процедуру в общем модуле. Если подходящего модуля нет, создайте новый общий модуль заранее.
- 1Создайте общий модуль (например, ПодпискиНаСобытия) с флагами «Сервер» и «Вызов сервера» при необходимости
- 2Добавьте объект «Подписка на событие» в ветке «Общие»
- 3Укажите источник — отметьте нужные типы объектов
- 4Выберите событие, например ПриЗаписи или ОбработкаПроведения
- 5Нажмите лупу у поля «Обработчик» и создайте процедуру в общем модуле
- 6Напишите код обработчика с параметрами Источник и Отказ
- 7Обновите конфигурацию базы данных и проверьте срабатывание
Выбор события: чем отличаются варианты
Набор доступных событий зависит от типа источника. Для документов чаще всего используются ПриЗаписи, ОбработкаПроведения, ПередЗаписью и ОбработкаУдаленияПроведения. Для справочников и планов видов характеристик типичны ПередЗаписью, ПриЗаписи и ПриУстановкеПометкиУдаления.
Событие ПередЗаписью срабатывает до записи объекта в базу — здесь удобно проверять и изменять реквизиты, потому что изменения ещё попадут в транзакцию записи. Событие ПриЗаписи происходит уже внутри транзакции записи: объект изменять поздно, зато можно записывать связанные данные в другие объекты, и при ошибке вся транзакция откатится целиком.
Событие ОбработкаПроведения вызывается только при проведении документа и позволяет формировать дополнительные движения по регистрам. Учитывайте, что у подписки с этим событием обработчик получает параметры Источник, Отказ и РежимПроведения.
Требования к общему модулю и обработчику
Обработчик подписки должен находиться в общем модуле с установленным флагом «Сервер». Флаг «Клиент (обычное приложение)» или «Клиент (управляемое приложение)» для такого модуля не нужен — обработчики событий объектов всегда выполняются на сервере. Флаг «Привилегированный режим» ставьте только осознанно: он отключает проверку прав, что может стать уязвимостью.
Сигнатура процедуры зависит от события. Для ПередЗаписью и ПриЗаписи это Процедура ИмяОбработчика(Источник, Отказ) Экспорт, для ОбработкаПроведения — (Источник, Отказ, РежимПроведения). Ключевое слово Экспорт обязательно, иначе платформа не сможет вызвать процедуру.
Пример простого обработчика, который при записи документа проверяет заполненность комментария:
Процедура ПроверитьКомментарийПриЗаписи(Источник, Отказ) Экспорт
Если Отказ Тогда
Возврат;
КонецЕсли;
Если Не ЗначениеЗаполнено(Источник.Комментарий) Тогда
ОбщегоНазначения.СообщитьПользователю(
"Не заполнен комментарий", , , , Отказ);
КонецЕсли;
КонецПроцедуры
Проверка результата и отладка
После обновления конфигурации базы данных откройте пользовательский режим и выполните действие, которое должно вызвать событие: запишите документ или проведите его. Если обработчик устанавливает Отказ = Истина, запись должна прерваться с вашим сообщением — это самый наглядный признак срабатывания.
Для отладки поставьте точку останова в обработчике и запустите отладку в конфигураторе. Если точка не срабатывает, проверьте: обновлена ли конфигурация базы данных, выбран ли правильный источник, есть ли слово Экспорт у процедуры, серверный ли общий модуль.
Как проверить результат
Точка останова в отладчике останавливается при записи объекта
Запись проходит, отладчик не останавливается — проверяйте источник и экспортность процедуры
При Отказ = Истина объект не записывается, пользователь видит сообщение
Сообщение выводится, но объект всё равно записался — параметр Отказ не передан по ссылке корректно или ошибка в логике
Запись объекта занимает примерно столько же времени, что и раньше
Запись стала заметно медленнее — в обработчике тяжёлые запросы или циклы
Типичные ошибки и ограничения
Самая частая ошибка — отсутствие проверки параметра Отказ в начале обработчика. Если другой обработчик уже отказал в записи, ваша логика не должна выполняться, иначе возможны некорректные данные и лишние сообщения пользователю.
Вторая распространённая проблема — слишком широкий источник. Если подписаться на все документы конфигурации, обработчик будет вызываться при каждой записи любого документа, и даже быстрый код суммарно замедлит работу системы. Отмечайте только те типы, для которых логика действительно нужна.
Также помните об ограничениях: подписки не срабатывают при обмене данными с отключёнными обработчиками только если в коде обмена это предусмотрено; при загрузке данных через обмен у объекта Источник установлено ОбменДанными.Загрузка = Истина — часто в начале обработчика стоит добавить проверку этого флага, чтобы не выполнять бизнес-логику при загрузке.
Производительность и безопасная работа
Обработчик подписки выполняется синхронно в транзакции записи объекта. Любой тяжёлый код — запросы в цикле, обращения к внешним сервисам, запись больших наборов данных — удерживает транзакцию и блокировки дольше, что в многопользовательской базе ведёт к конфликтам блокировок.
Практические правила: выносите обращения к внешним системам в фоновые задания или регламентные операции, а в подписке только фиксируйте факт необходимости обмена. Используйте запросы с явными полями вместо обхода табличных частей через объект. Перед внедрением на рабочей базе протестируйте подписку на копии.
Что важно запомнить
Подписка на событие создаётся в ветке «Общие» конфигуратора: источник, событие и экспортная процедура в серверном общем модуле. Всегда проверяйте Отказ и ОбменДанными.Загрузка, не записывайте Источник повторно и тестируйте на копии базы.
Частые вопросы
Можно ли создать подписку на событие без изменения конфигурации?
Нет, объект «Подписка на событие» — это метаданные, поэтому потребуется изменение конфигурации и обновление базы данных. Альтернатива без снятия с поддержки — расширение конфигурации, где тоже можно создавать подписки на события.
Почему подписка не срабатывает, хотя всё настроено?
Чаще всего причины: конфигурация базы данных не обновлена, у процедуры нет слова Экспорт, общий модуль не серверный, в источнике не отмечен нужный тип объекта или запись выполняется в режиме загрузки с пропуском бизнес-логики. Проверяйте по списку и через точку останова в отладчике.
Можно ли одной подпиской обрабатывать разные типы объектов?
Да, в свойстве «Источник» можно отметить несколько типов. Внутри обработчика различайте их через ТипЗнч(Источник) или Источник.Метаданные(). Учтите, что обращение к реквизитам, которых нет у части типов, вызовет ошибку — проверяйте наличие реквизита через метаданные.
Чем ПередЗаписью отличается от ПриЗаписи на практике?
ПередЗаписью вызывается до начала записи в базу: здесь можно менять реквизиты объекта, и изменения сохранятся. ПриЗаписи вызывается внутри транзакции записи: объект уже записывается, менять его поздно, но можно записывать связанные данные — при ошибке всё откатится вместе.
Срабатывает ли подписка при программной записи объекта?
Да, подписка вызывается при любой записи объекта — и интерактивной из формы, и программной через метод Записать(). Исключение — если код записи специально обходит бизнес-логику через установку ОбменДанными.Загрузка, а в обработчике есть соответствующая проверка.
Как отключить подписку без удаления?
Штатного флага «отключено» у подписки нет. Варианты: очистить источник, закомментировать код обработчика или добавить в начало обработчика проверку функциональной опции или константы-переключателя, которой можно управлять из пользовательского режима.