В процессе разработки на платформе 1С:Предприятие 8 часто возникает необходимость выполнить определенные действия именно в момент сохранения данных пользователем через интерфейс. Начинающие разработчики часто ищут возможность создать стандартный объект метаданных Подписка на событие для формы, однако сталкиваются с тем, что в списке доступных источников событий формы отсутствуют. В этой статье мы разберем, почему так происходит, чем отличаются события объекта от событий формы и как правильно реализовать «подписку» на события формы, используя современные механизмы платформы.
Для начала проанализируем архитектурную логику 1С. Платформа жестко разделяет прикладную логику (работу с данными) и интерфейсную логику (взаимодействие с пользователем). Рассмотрим подробнее эти уровни:
СправочникОбъект, ДокументОбъект и т.д. Эти события срабатывают ВСЕГДА, когда объект записывается в базу данных — будь то нажатие кнопки в форме, программный вызов метода Записать() или загрузка через обмен данными.ПриЗаписи, ПередЗаписью) предназначены исключительно для обработки действий пользователя в конкретном окне программы. Стандартных подписок на них в дереве метаданных не существует, так как форма — это динамический объект визуального интерфейса, а не постоянная структура данных.Если в источнике подписки на событие вы выбираете СправочникОбъект и видите там событие ПриЗаписи, важно понимать: это событие модуля объекта, а не формы. Оно сработает при любой записи, даже если форма вообще не открывалась.
Если ваша задача — внедрить код именно в логику работы формы (например, проверить заполнение полей, которые есть только на форме, или вывести пользователю вопрос), мы должны использовать механизм расширений конфигурации. Это фактически и есть современный аналог «подписки» на форму.
Рассмотрим по шагам, как перехватить событие ПриЗаписиНаСервере в форме справочника через расширение:
Проанализируем пример кода с использованием аннотации &После. Это наиболее безопасный способ, который позволяет выполнить ваш код сразу после того, как отработал основной код формы:
&НаСервере
&После("ПриЗаписиНаСервере")
Процедура Расш1_ПриЗаписиНаСервереПосле(Отказ, ТекущийОбъект, ПараметрыЗаписи)
// Ваш код здесь
Сообщить("Данные успешно обработаны в контексте формы!");
КонецПроцедуры
Рассмотрим основные аннотации, которые позволяют нам «мимикрировать» под подписку:
Отказ = Истина, чтобы прервать запись.ПродолжитьВызов(), если вы не хотите полностью блокировать типовой функционал.Чтобы не запутаться, где именно писать код — в подписке на объект или в расширении формы — разберем последовательность событий. Выясним причину, почему в некоторых случаях подписка на объект может не подойти.
При нажатии кнопки «Записать» в форме происходит следующая цепочка:
ПередЗаписью. Здесь можно спросить пользователя (например, «Вы уверены?»).ПередЗаписьюНаСервере. Подготовка данных формы перед передачей в объект.ПередЗаписью. Здесь срабатывают системные Подписки на события («ПередЗаписью»).ПриЗаписи. Здесь срабатывают системные Подписки на события («ПриЗаписи»).ПриЗаписиНаСервере. Здесь данные уже в базе, но форма еще «знает» о контексте записи.ПослеЗаписи. Информирование пользователя об успехе.Важный нюанс: Если вы напишете код в системной подписке на событие ПриЗаписи (уровень объекта), вы не сможете обратиться к элементам формы или вызвать клиентские методы. Если же вы используете расширение формы, вам доступен весь контекст формы, но этот код не сработает, если элемент справочника будет записан программно (например, фоновым заданием).
Иногда требуется «подписаться» на события элементов формы динамически. Для этого в языке 1С предусмотрен метод УстановитьДействие(). Посмотрим на пример его использования в коде формы:
&НаКлиенте
Процедура ПриОткрытии(Отказ)
// Назначаем обработчик для кнопки
ЭтаФорма.Элементы.КнопкаВыполнить.УстановитьДействие("Нажатие", "Подключаемый_ОбработчикНажатия");
КонецПроцедуры
&НаКлиенте
Процедура Подключаемый_ОбработчикНажатия(Команда)
Сообщить("Действие перехвачено программно!");
КонецПроцедуры
Однако помните, что этот метод работает для событий элементов управления (кнопок, полей ввода), но не позволяет «подписаться» на системные события самой формы, такие как ПриЗаписи. Для них единственным верным решением остаются расширения.
Мы выяснили, что стандартная Подписка на событие как объект метаданных существует только для модулей объектов (серверная часть). Для реализации логики, привязанной именно к интерфейсу формы, следует использовать Расширения конфигурации.
При выборе места для кода руководствуйтесь правилом:
1. Нужно, чтобы код работал всегда (даже при загрузке данных)? Используйте Подписку на событие СправочникОбъект.
2. Нужно взаимодействовать с интерфейсом формы или пользователем? Используйте расширение формы и аннотации &Перед, &После.