Как вывести сообщение в форму списка после нажатия Провести и закрыть в форме документа

Программист 1С v8.3 (Управляемые формы) 1С:Управление торговлей Управленческий учет Торговля и дистрибуция
← На главную

В практике разработки на платформе 1С:Предприятие 8.3 часто возникает задача: при выполнении определенных действий в форме документа (например, при проведении) программно создать другой связанный объект и уведомить об этом пользователя. Сложность заключается в том, что если пользователь нажимает кнопку Провести и закрыть, форма документа мгновенно закрывается, и стандартные методы вывода сообщений, привязанные к этой форме, могут не сработать или остаться незамеченными. Разберем, как правильно организовать оповещение пользователя и какую архитектуру взаимодействия выбрать, чтобы избежать блокировок интерфейса.

Анализ проблемы: почему СообщитьПользователю не всегда подходит

Рассмотрим ситуацию: в документе ПриобретениеТоваровУслуг при выполнении определенных условий создается ЗаказКлиента. Если использовать метод ОбщегоНазначения.СообщитьПользователю, пытаясь направить сообщение в форму списка, мы столкнемся с проблемой области видимости. Метод Сообщить без привязки к конкретному идентификатору формы выводит информацию в общее окно сообщений, которое пользователь может пропустить, если форма документа уже закрылась. Привязка же сообщения к закрывающейся форме приводит к тому, что сообщение «умирает» вместе с формой.

Проанализируем ситуацию: нам нужно передать данные из одной формы (которая закрывается) в другую (которая уже открыта или будет активна — форму списка). Для этого в 1С предусмотрены механизмы глобальных оповещений и всплывающих уведомлений.

Решение 1: Использование механизма Оповестить и ОбработкаОповещения

Это классический и самый надежный способ взаимодействия между формами в управляемом приложении. Метод Оповестить рассылает сигнал всем открытым формам текущего сеанса. Рассмотрим подробнее, как это реализовать.

В форме документа, в обработчике события, который срабатывает после записи (когда ссылка на новый объект уже гарантированно создана), мы вызываем клиентский метод:


&НаКлиенте
Процедура ПослеЗаписи(ПараметрыЗаписи)
    // Предположим, ссылка на созданный заказ сохранена в реквизите формы
    Если ЗначениеЗаполнено(СозданныйЗаказКлиента) Тогда
        СтруктураОповещения = Новый Структура;
        СтруктураОповещения.Вставить("Ссылка", СозданныйЗаказКлиента);
        СтруктураОповещения.Вставить("Текст", "Создан новый заказ клиента!");
        
        Оповестить("СобытиеСозданияЗаказа", СтруктураОповещения, ЭтаФорма);
    КонецЕсли;
КонецПроцедуры

Затем в форме списка документов ПриобретениеТоваровУслуг нам необходимо «поймать» это событие. Для этого используется обработчик ОбработкаОповещения:


&НаКлиенте
Процедура ОбработкаОповещения(ИмяСобытия, Параметр, Источник)
    Если ИмяСобытия = "СобытиеСозданияЗаказа" Тогда
        // Обновим список, чтобы увидеть изменения, если нужно
        Элементы.Список.Обновить();
        // Выведем сообщение пользователю прямо здесь
        ПоказатьОповещениеПользователя("Успешно", , Параметр.Текст);
    КонецЕсли;
КонецПроцедуры

Решение 2: Использование ПоказатьОповещениеПользователя в ПриЗакрытии

Если мы хотим, чтобы в углу экрана появилось симпатичное всплывающее окно (toast-уведомление), которое не зависит от состояния форм, лучше всего использовать метод ПоказатьОповещениеПользователя. Проанализируем пример кода, который можно разместить в расширении или основной форме в процедуре ПриЗакрытии:


&НаКлиенте
Процедура ПриЗакрытии(ЗавершениеРаботы)
    Если НЕ ЗавершениеРаботы Тогда
        // Получаем ссылку на созданный заказ из реквизита формы
        ЗаказСсылка = Объект.СсылкаНаСозданныйЗаказ; 
        
        Если ЗначениеЗаполнено(ЗаказСсылка) Тогда
            ТекстУведомления = Строка(ЗаказСсылка);
            НавигационнаяСсылка = ПолучитьНавигационнуюСсылку(ЗаказСсылка);
            
            ПоказатьОповещениеПользователя(
                "Создан связанный документ", 
                НавигационнаяСсылка, 
                ТекстУведомления, 
                БиблиотекаКартинок.ИнформационноеПисьмо
            );
        КонецЕсли;
    КонецЕсли;
КонецПроцедуры

Выясним причину, по которой этот метод удобен: он позволяет пользователю не просто прочитать текст, но и кликнуть на уведомление, чтобы мгновенно открыть созданный Заказ клиента благодаря использованию НавигационнойСсылки.

Важные архитектурные рекомендации

При реализации подобной логики важно не совершить классическую ошибку новичка: создание и запись новых объектов непосредственно внутри транзакции записи основного документа (например, в модуле объекта в ПередЗаписью или ПриЗаписи). Разберем по шагам, почему это плохо:

  1. Блокировки таблиц БД: Пока выполняется код создания заказа внутри транзакции проведения поступления, таблицы обоих документов заблокированы. В высоконагруженных системах это приведет к очередям и ошибкам «Превышено время ожидания блокировки».
  2. Интерфейсный «затуп»: Весь сеанс пользователя будет заблокирован, пока сервер выполняет тяжелые операции создания подчиненного документа. Пользователь будет видеть «песочные часы» и не сможет даже переключиться на другую вкладку в 1С.
  3. Целостность данных: Если создание заказа вызовет ошибку, проведение основного документа тоже откатится. Иногда это нужно, но чаще это мешает работе, если заказ является вспомогательным.

Правильнее всего инициировать создание связанных объектов в обработчике ПослеЗаписиНаСервере в форме или использовать механизм длительных операций (фоновых заданий).

Применение фоновых заданий для создания документов

Выясним, как сделать работу системы максимально плавной. Вместо того чтобы заставлять пользователя ждать, мы можем запустить фоновое задание. Рассмотрим алгоритм:

  1. В форме документа в ПослеЗаписи вызываем серверный метод, который запускает фоновое задание.
  2. Фоновое задание в отдельном потоке создает Заказ клиента.
  3. Форма документа закрывается, пользователь возвращается в список.
  4. Как только фоновое задание завершается, система через механизм Оповестить или через обработчик ожидания в форме списка уведомляет пользователя о результате.

Проанализируем ситуацию: использование Библиотеки Стандартных Подсистем (БСП) значительно упрощает этот процесс. Метод ДлительныеОперации.ЗапуститьВыполнениеНаСервере позволяет выполнить создание документа в фоне, а функция ПоказатьОповещениеПользователя выведет результат, когда он будет готов, даже если пользователь уже перешел к работе с другим разделом программы.

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

← На главную