Oracle Forms. Программное выполнение последнего запроса в блоке


Модификация.


Назначение

Часто при работе с Oracle Forms требуется реализовать возможность программного выполнения последнего запроса пользователя.
Например, вы стоите на некоторой записи в блоке и нажимаете на кнопку, которая вызывает процедуру(часто хранимую), модифицирующую текущую запись. После того как процедура отработала и запись была успешно модифицирована требуется обновить содержимое блока в форме для отображения сделанных изменений.

Выполнить последний запрос в блоке интерактивно - довольно просто, достаточно последовательно нажать на клавиши:

   ENTER_QUERY (<F7>) ENTER_QUERY (<F7>) EXECUTE_QUERY (<F8>)

Однако попытка последовательно выполнить соответствующие встроенные процедуры:

   ENTER_QUERY; 
   ENTER_QUERY; 
   EXECUTE_QUERY;
не приводит к желаемому. Форма после первой ENTER_QUERY переходит в режим ввода запроса и так в нем и остается.

Пакет P_QUERY предназначен для решения данной проблемы.

Предварительные действия

Для подготовки к использованию требуется наличие в форме пакета P_QUERY (Program Units, Attached libraries) и четыре вида триггеров.

Также, требуется расставить по нужным местам (триггерам) четыре процедуры этого пакета:

  1. P_QUERY.Init_New_Block - в одном месте
  2. P_QUERY.Finalize - в одном месте
  3. P_QUERY.Prepare_Last_Query - один раз на каждый блок, в котором требуется перевыполнять запрос
  4. P_QUERY.Find_Row - один раз на каждый блок, в котором требуется перевыполнять запрос

Где разместить эти процедуры.

Триггеры уровня формы:

1.PRE-FORM:
В этом триггере для каждого блока, в котором хотим перевыполнять запрос,
нужно вызвать процедуру:

P_QUERY.Init_New_Block ('<block_name>', '<primary_key_column>');

, где
<block_name> - имя блока, например 'EMP'
<primary_key_column> - название столбца первичного ключа, например 'EMPNO'
Это вовсе не значит, что этот столбец нужно объявить первичным ключом в блоке
формы.

2. POST-FORM
P_QUERY.Finalize;

Триггеры уровня блока. Для каждого определенного в PRE-FORM блока нужно создать два триггера:

3. PRE-QUERY
P_QUERY.Prepare_Last_Query;

4. POST-QUERY
P_QUERY.Find_Row;

Важное замечание.
Предполагается что только в элементы следующих типов можно вводить условия запроса: 'CHECKBOX', 'DISPLAY ITEM', 'LIST', 'RADIO GROUP', 'TEXT ITEM' Более того, для того чтобы элементы этих типов обрабатывались, необходимо чтобы их свойство 'Column Name' было ЗАПОЛНЕНО.

Подготовка закончена.

Использование

Теперь в любом месте где нужно программно выполнить последний запрос вызываем:

P_QUERY.Exec_Last_Query;

Запрос будет перевыполнен в текущем блоке. Если нужно это сделать для другого блока, то требуется предварительно перейти в него.

Помимо программного выполнения последнего запроса, процедура Exec_Last_Query выполнит позиционирование в тоже поле, той же записи, где находился курсор перед вызовом.

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

P_QUERY.Exec_And_Goto ('<значение PK новой записи>');

Запрос будет перевыполнен и курсор перейдет на запись с указанным значением первичного ключа.

Для того чтобы проверить правильность позиционирования, можно воспользоваться функцией P_QUERY.Last_Query_Success. Эта функция вернет TRUE в случае если искомая запись была найдена и FALSE в противном случае.

Прочие публичные подпрограммы пакета P_QUERY были созданы для отладочных целей и не должны использоваться.

Принцип работы и недостатки текущей реализации

Принцип работы основывается на использовании триггера PRE-QUERY. В этом триггере находится процедура (Prepare_Last_Query), которая по умолчанию запоминает значения всех полей блока, в которые разрешено вводить условия запроса.

Т.к. триггер PRE-QUERY срабатывает непосредственно перед выполнением запроса, а значения полей блока полученные в нем и есть те критерии поиска, вводимые пользователем в режиме ENTER_QUERY, то запомнив их, мы имеем всю необходимую информацию для того, чтобы в дальнейшем перевыполнить этот же запрос.

Для этого нужно в процедуре перевыполняющей запрос (Exec_Last_Query), перед вызовом EXECUTE_QUERY установить специальный флаг для Prepare_Last_Query, чтобы последняя вместо запоминания значений полей, наоборот, восстановила ранее запомненные критерии поиска в соответствующие поля блока.

Использование данной утилиты предполагает, что если требуется программно установить некие критерии поиска, то это делается не установкой свойста DEFAULT_WHERE для блока, а также - через триггер PRE-QUERY. Вызов процедуры Prepare_Last_Query в этом случае должен быть последним в триггере.

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

Недостатки текущей реализации

Собственно код и тестовая форма

Тестовая форма F_QUERY содержит один блок данных построенный по представлению USER_OBJECTS и демонстрирует возможности утилиты. В этой же форме находится собственно пакет P_QUERY.

Пишите


15 Июля 2002 года.

Hosted by www.Geocities.ws

1