Изменение данных клиентом
Всякий раз, когда клиент создаёт, удаляет или изменяет записи в своей локальной копии рабочего набора данных, он должен убедиться, что изменения, вносимые в набор данных, помечаются как обновления в таблице BEFORE. Набор изменений, который подготавливает клиент должен содержать все записи из таблицы BEFORE и все обновлённые записи таблицы AFTER. Сервер использует эти записи для применения изменений к базе данных.
Для того, чтобы изменения в рабочем наборе данных были отмечены в таблице BEFORE, мы должны установить атрибут TRACKING-CHANGES для конкретной временной таблицы в рабочем наборе. Это логический атрибут, который по умолчанию для каждой временной таблицы имеет значение FALSE, т.е. отслеживание изменений выключено. Для того чтобы включить отслеживание изменений мы должны установить ему значение TRUE. Синтаксис изменения состояния атрибута TRACKING-CHANGES следующий:
TEMP-TABLE table-name:TRACKING-CHANGES = TRUE | FALSE.
После завершения изменений во временной таблице атрибут TRACKING-CHANGES должен быть снова переведён в состоянии FALSE.
В следующем примере кода мы собираемся добавить новую запись в таблицу ttOrderLine. Но перед этим мы включаем отслеживание изменений, установив TRACKING-CHANGES в состояние TRUE. Затем мы создаём запись и присваиваем значения её полям. После чего возвращаем атрибут TRACKING-CHANGES в исходное состояние.
TEMP-TABLE ttOrderLine:TRACKING-CHANGES = TRUE. CREATE ttOrderLine. /* присваиваем значения полям новой записи */ TEMP-TABLE ttOrderLine:TRACKING-CHANGES = FALSE.
Для подготовки набора изменений к отправке на сервер мы должны:
- Создать динамический набор изменений.
- Добавить информацию о схеме из рабочего набора в динамический набор изменений.
- Поместить записи таблиц BEFORE и AFTER в набор изменений.
Динамический набор данных создаётся путём назначения объекта набора данных переменной типа HANDLE.
Пример:
DEFINE VARIABLE hChangeDataSet AS HANDLE NO-UNDO. CREATE DATASET hChangeDataSet.
После этого мы копируем схему из рабочего набора в динамический. Для этого используется следующий синтаксис:
change-dataset-handle:CREATE-LIKE(working-dataset-handle).
В следующем примере схема набора данных dsOrderOrderLine копируется в динамический набор изменений:
DEFINE VARIABLE hChangeDataSet AS HANDLE NO-UNDO. CREATE DATASET hChangeDataSet. hChangeDataSet:CREATE-LIKE(DATASET dsOrderOrderLine:HANDLE).
Как только набор изменений будет инициализирован добавлением информацией о схеме, мы копируем таблицу BEFORE и все связанные записи из таблицы AFTER используя метод GET-CHANGES. При этом необходимо убедиться в том, что атрибут TRACKING-CHAGES установлен в состояние FALSE для всех временных таблицы из рабочего набора данных перед вызовом метода GET-CHANGES.
Синтаксис вызова метода GET-CHANGES:
change-dataset-handle:GET-CHANGES (working-dataset-handle)
В следующем примере выполняется извлечение изменений из набора данных dsOrderOrderLine. Обратите внимание, что связанный через hChangeDataSet набор данных получит только изменённые строки:
hChangeDataSet:GET-CHANGES(DATASET dsOrderOrderLine:HANDLE).
Теперь, когда набор изменений подготовлен, следующим шагом будет вызов серверной внутренней процедуры для обновления набора данных. Процедура обновления, работающая на стороне сервера, принимает набор изменений в качестве параметра.
Следующий синтаксис используется для вызова серверной внутренней процедуры с использованием хэндла внешней процедуры:
RUN update-proc-name IN proc-handle (INPUT-OUTPUT DATASET-HANDLE change-dataset-handle).
Обратите внимание, параметр должен иметь тип INPUT-OUTPUT, так как серверный код должен вернуть обновлённый набор изменений обратно клиенту, и атрибут DATASET-HANDLE, так как набор данных между клиентом и сервером передаётся по значению.
Пример вызова процедуры обновления на клиенте:
RUN update_dsOrderOrderLine IN hProc (INPUT-OUTPUT DATASET-HANDLE hChangeDataSet).