Как программно перечитать данные открытого документа в интерфейсе Такси 1С

Программист 1С v8.3 (Управляемые формы) IT и автоматизация бизнеса
← На главную

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

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

Особенности архитектуры управляемых форм

Проанализируем ключевые причины, из-за которых возникают сложности при попытке обновить данные формы:

  1. Разделение контекстов исполнения: Серверный код работает исключительно с объектами базы данных (например, ДокументОбъект). Сервер ничего не знает об открытых на клиенте окнах и не имеет к ним прямых ссылок. Серверный модуль не может вызвать метод клиентской формы.
  2. Различие типов данных: На клиенте отображаются не сами объекты базы данных, а их проекция — тип ДанныеФормыСтруктура (реквизит Объект).
  3. Риск потери несохраненных данных: Принудительный вызов метода Прочитать() сбрасывает введенные пользователем, но еще не сохраненные изменения, если свойство Модифицированность установлено в значение Истина.

Способ 1. Вызов метода Прочитать() из клиентского контекста

Рассмотрим вариант, когда вызов происходит из общего модуля с признаком Клиент. В этом случае мы имеем доступ к клиентскому контексту и объекту формы.

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

Посмотрим на пример кода в клиентском общем модуле:


// Вызов выполняется в клиентском общем модуле
Процедура ОбновитьДанныеФормыДокумента(ФормаДокумента) Экспорт
    
    // Перечитываем данные объекта из базы данных в форму
    ФормаДокумента.Прочитать();
    
КонецПроцедуры

Способ 2. Глобальное оповещение об изменении объекта

Разберем наиболее универсальный подход, когда объект модифицируется и записывается в базу данных. В 1С предусмотрен специальный механизм оповещения, который самостоятельно информирует все открытые формы и динамические списки о том, что данные конкретного объекта изменились.

Для этого в клиентском контексте вызывается процедура ОповеститьОбИзменении() с передачей ссылки на объект:


// Вызов на клиенте после изменения и записи объекта
СсылкаНаДокумент = ...; // Ссылка на измененный документ
ОповеститьОбИзменении(СсылкаНаДокумент);

Платформа автоматически обновит данные в связанных открытых формах данного документа, не требуя поиска конкретного окна.

Способ 3. Использование пары Оповестить() и ОбработкаОповещения

Если необходимо передать произвольный сигнал или дополнительный контекст из клиентского модуля в открытую форму, используем механизм пользовательских оповещений.

Шаг 1. Из общего клиентского модуля отправляем событие с помощью процедуры Оповестить():


Оповестить("ОбновитьДанныеДокумента", Новый Структура("Ссылка", СсылкаНаДокумент), ЭтотОбъект);

Шаг 2. В самой форме документа описываем предопределенный обработчик ОбработкаОповещения:


&НаКлиенте
Процедура ОбработкаОповещения(ИмяСобытия, Параметр, Источник)
    
    Если ИмяСобытия = "ОбновитьДанныеДокумента" И Параметр.Ссылка = Объект.Ссылка Тогда
        ЭтаФорма.Прочитать();
    КонецЕсли;
    
КонецПроцедуры

Способ 4. Передача данных формы на сервер и обратно

Посмотрим на ситуацию, когда обработка выполняется на сервере формы. В таком контексте не требуется перечитывать весь документ из базы с помощью метода Прочитать(), если мы модифицируем данные формы на сервере.

В серверном контексте формы используется трансформация между объектом базы данных и данными формы с помощью функций ЗначениеВРеквизитФормы() и РеквизитФормыВЗначение():


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

Способ 5. Обновление визуального отображения

Если реквизиты формы уже были изменены программно, но интерфейсные элементы на экране еще не успели перерисоваться, применяют метод ОбновитьОтображениеДанных() на клиенте:


&НаКлиенте
Процедура ПослеИзмененияРеквизитов()
    
    // Обновляем визуальное отображение элементов формы
    ЭтаФорма.ОбновитьОтображениеДанных();
    
КонецПроцедуры

Таким образом, выбор метода зависит от того, в каком контексте (клиент или сервер) выполняется ваш код и требуется ли полная перечитка объекта из СУБД или лишь обновление визуальных элементов формы.

← На главную