Почему MQT обновляется при цикле фиксации 0? - PullRequest
0 голосов
/ 15 февраля 2020

У нас есть таблица MQT (TESTMQT), которая выбирает данные из таблицы TEST1. У нас также есть индекс по MQT, поэтому наша программа может использовать собственный ввод-вывод по MQT. У нас также есть триггер «Перед обновлением» на MQT, поэтому вместо непосредственного обновления MQT обновляется таблица TEST1 (в случае, если программе объявлено MQT в F-spe c).

Проблема в том, что даже если это триггер скомпилирован с commit = * none и программа SQLRPGLE также скомпилирована с commit = * none, по какой-то причине данные, обновленные в таблице TEST1, обновляются в цикле фиксации 5, но MQT обновляется в цикле фиксации 0 (я вижу это в журнале) , Я ожидал, что, поскольку программа была скомпилирована с Commit = * none, все транзакции НЕ будут выполняться при фиксации.

Не уверен, что это имеет значение, но эта программа, которая обновляет таблицу / mqt, вызывается из программы CL, которая запускает управление фиксацией с помощью scope (job) и lcklvl (* chg)

STRCMTCTL LCKLVL (* CHG ) CMTSCOPE (* JOB)

Итак, программа CL запускает обязательство по заданию и вызывает программу SQLRPGLE, которая компилируется с commit = * none. После завершения программы CL фиксирует изменения программы и завершает управление фиксацией.

В мониторе производительности я вижу, что перед запуском триггера уровень изоляции изменяется на UNCOMMITED READ с помощью SET TRANSACTION, но я не делаю этого явно в код. Я читал в IBM RedBook, что если триггер был создан с уровнем изоляции, отличным от вызывающего, уровень изоляции будет изменен, чтобы соответствовать уровню изоляции вызывающего. Я думал, что в моем случае Caller - это SQLRPGLE, который был скомпилирован с commit = * none, так как обновление в TEST1 выполняется при коммите? Из-за уровня изоляции uncommited чтения из SET TRANSACTION? Как проверить уровень изоляции вызывающего абонента?

Код MQT:

CREATE TABLE TESTLIB.TESTMQT ( TESTCODE, TESTDESC ) AS
    (SELECT DECIMAL(CODE, 5), DESC
    FROM TESTLIB.TESTTABLE)
DATA INITIALLY IMMEDIATE  
REFRESH DEFERRED 
ENABLE QUERY OPTIMIZATION
MAINTAINED BY USER
RCDFMT TESTMQT ;    

CREATE UNIQUE INDEX TESTLIB.TESTIDX
    ON TESTLIB.TESTMQT (TESTCODE);

Перед кодом триггера:

CREATE OR REPLACE TRIGGER TESTLIB.TESTTRGUP
NO CASCADE BEFORE Update On TESTLIB.TESTMQT
REFERENCING OLD As vOld
            NEW As vNew
For Each Row Mode DB2ROW
SET OPTION COMMIT=*NONE
BEGIN ATOMIC
    UPDATE TESTLIB.TESTTABLE
    SET
        CODE = vNew.TESTCODE,
        DESC = vNew.TESTDESC
    WHERE 
        CODE = vOld.TESTCODE;
END;
...