8.3では更新可能カーソルが使えるようになった。従来、PostgreSQLのカーソルは「更新不可能」だったのである。
次の例を見ていただきたい。
BEGIN;
DECLARE c CURSOR FOR SELECT * FROM T1;
FETCH 2 FROM c;
i | j
---+-----
1 | foo
2 | bar
(2 rows)
この状態で1行削除する。
DELETE FROM t1 WHERE i = 1;
しかし、カーソルを使って確認すると、削除されていないように見える。これがPostgreSQLのカーソルが「更新不可能」と言われる理由である。
MOVE BACKWARD ALL IN c;
FETCH ALL FROM c;
i | j
---+-----
1 | foo
2 | bar
(2 rows)
もちろん、実際には削除されており、SELECT文で確認できる。
SELECT * FROM t1;
i | j
---+-----
1 | foo
(1 row)
これに対して8.3では、FOR UPDATEをカーソル宣言に付与することにより、カーソルを更新可能にできる。
BEGIN;
DECLARE c CURSOR FOR SELECT * FROM T1 FOR UPDATE;
FETCH 2 FROM c;
i | j
---+-----
1 | foo
2 | bar
(2 rows)
ここで1行削除してみる。ちなみに、「WHERE CURRENT OF」は8.3で導入された構文で、カーソルが指す現在行を指定する。
DELETE FROM t1 WHERE CURRENT OF c;
カーソルからも削除されていることが確認できる。
MOVE BACKWARD ALL IN c;
FETCH ALL FROM c;
i | j
---+-----
1 | foo
(1 rows)
更新可能カーソルが使えるようになったことにより、カーソルの扱いに関しては商用DBからの移行が格段に楽になったと言える。