バージョンごとのドキュメント一覧

42.6. PL/Tclのトリガ関数 #

<title>Trigger Functions in PL/Tcl</title>

Trigger functions can be written in PL/Tcl. <productname>PostgreSQL</productname> requires that a function that is to be called as a trigger must be declared as a function with no arguments and a return type of <literal>trigger</literal>. トリガ関数をPL/Tclで作成することができます。 PostgreSQLでは、トリガとして呼び出される関数は、trigger型の戻り値を返す引数のない関数として宣言する必要があります。

The information from the trigger manager is passed to the function body in the following variables: トリガマネージャからの情報は、以下の変数内に格納されて関数本体に渡されます。

$TG_name

The name of the trigger from the <command>CREATE TRIGGER</command> statement. CREATE TRIGGER文によるトリガ名。

$TG_relid

The object ID of the table that caused the trigger function to be invoked. そのトリガ関数の呼び出しを発生させたテーブルのオブジェクトID。

$TG_table_name

The name of the table that caused the trigger function to be invoked. そのトリガ関数の呼び出しを発生させたテーブルの名前。

$TG_table_schema

The schema of the table that caused the trigger function to be invoked. そのトリガプロシージャ呼び出しが発生したテーブルのスキーマ。

$TG_relatts

A Tcl list of the table column names, prefixed with an empty list element. So looking up a column name in the list with <application>Tcl</application>'s <function>lsearch</function> command returns the element's number starting with 1 for the first column, the same way the columns are customarily numbered in <productname>PostgreSQL</productname>. (Empty list elements also appear in the positions of columns that have been dropped, so that the attribute numbering is correct for columns to their right.) 先頭に空のリスト要素を持つ、テーブルの列名のTclリスト。 Tcllsearchコマンドを使用して、そのリストから列名を検索することで、最初の列を1とした要素番号が返されます。 これは、PostgreSQLでの通常の列の番号付けと同じです。 (また空のリスト要素は、右側の列の属性番号を正しくするために、削除された列の位置に現れます。)

$TG_when

The string <literal>BEFORE</literal>, <literal>AFTER</literal>, or <literal>INSTEAD OF</literal>, depending on the type of trigger event. トリガイベントの種類に応じた、BEFOREAFTERまたはINSTEAD OFという文字列。

$TG_level

The string <literal>ROW</literal> or <literal>STATEMENT</literal> depending on the type of trigger event. トリガイベントの種類に応じた、ROWまたはSTATEMENTという文字列。

$TG_op

The string <literal>INSERT</literal>, <literal>UPDATE</literal>, <literal>DELETE</literal>, or <literal>TRUNCATE</literal> depending on the type of trigger event. トリガイベントの種類に応じた、INSERTUPDATEDELETE、またはTRUNCATEの文字列。

$NEW

An associative array containing the values of the new table row for <command>INSERT</command> or <command>UPDATE</command> actions, or empty for <command>DELETE</command>. The array is indexed by column name. Columns that are null will not appear in the array. This is not set for statement-level triggers. INSERT/UPDATE動作の場合は新しいテーブル行の値を、DELETE動作の場合は空を持つ連想配列。 配列のインデックスは列名です。 NULLの列はこの配列内には現れません。 文レベルのトリガに対しては設定されません。

$OLD

An associative array containing the values of the old table row for <command>UPDATE</command> or <command>DELETE</command> actions, or empty for <command>INSERT</command>. The array is indexed by column name. Columns that are null will not appear in the array. This is not set for statement-level triggers. UPDATE/DELETE動作の場合は古いテーブル行の値を、INSERT動作の場合は空を持つ連想配列。 配列のインデックスは列名です。 NULLの列はこの配列内には現れません。 文レベルのトリガに対しては設定されません。

$args

A Tcl list of the arguments to the function as given in the <command>CREATE TRIGGER</command> statement. These arguments are also accessible as <literal>$1</literal> ... <literal>$<replaceable>n</replaceable></literal> in the function body. CREATE TRIGGER文で指定された、関数への引数のTclリスト。 この引数は、関数本体から$1 ... $nとしてもアクセスすることができます。

The return value from a trigger function can be one of the strings <literal>OK</literal> or <literal>SKIP</literal>, or a list of column name/value pairs. If the return value is <literal>OK</literal>, the operation (<command>INSERT</command>/<command>UPDATE</command>/<command>DELETE</command>) that fired the trigger will proceed normally. <literal>SKIP</literal> tells the trigger manager to silently suppress the operation for this row. If a list is returned, it tells PL/Tcl to return a modified row to the trigger manager; the contents of the modified row are specified by the column names and values in the list. Any columns not mentioned in the list are set to null. Returning a modified row is only meaningful for row-level <literal>BEFORE</literal> <command>INSERT</command> or <command>UPDATE</command> triggers, for which the modified row will be inserted instead of the one given in <varname>$NEW</varname>; or for row-level <literal>INSTEAD OF</literal> <command>INSERT</command> or <command>UPDATE</command> triggers where the returned row is used as the source data for <command>INSERT RETURNING</command> or <command>UPDATE RETURNING</command> clauses. In row-level <literal>BEFORE</literal> <command>DELETE</command> or <literal>INSTEAD OF</literal> <command>DELETE</command> triggers, returning a modified row has the same effect as returning <literal>OK</literal>, that is the operation proceeds. The trigger return value is ignored for all other types of triggers. トリガ関数からの戻り値は、OKという文字列、SKIPという文字列、列名/値の組のリスト、の内の1つを取ることができます。 戻り値がOKの場合、トリガを発行した操作(INSERT/UPDATE/DELETE)は正常に処理されます。 SKIPはトリガマネージャにこの行に対する操作を何も出力せずに中止するように通知します。 リストが返された場合は、PL/Tclに対し、変更した行をトリガマネージャに返すことを通知します。変更行の内容はリスト内の列名と値により指定されます。 リストで言及されなかった列は全てNULLが置かれます。 変更された行を返すことは、$NEW内で与えられる行ではなく変更された行が挿入される、行レベルのBEFORE INSERTまたはUPDATEトリガ、または、返される行がINSERT RETURNINGおよびUPDATE RETURNING句の元データとして使われる、行レベルのINSTEAD OF INSERTまたはUPDATEトリガでのみ有意です。 行レベルのBEFORE DELETEまたはINSTEAD OF DELETEトリガでは、変更された行が返されることがOKが返されるのと同じ効果を持ち、その操作は処理されます。 この他の種類のトリガでは戻り値は無視されます。

ヒント

The result list can be made from an array representation of the modified tuple with the <literal>array get</literal> Tcl command. 結果リストはarray get Tclコマンドによる変更されたタプルの配列表現から作ることができます。

Here's a little example trigger function that forces an integer value in a table to keep track of the number of updates that are performed on the row. For new rows inserted, the value is initialized to 0 and then incremented on every update operation. ここで、テーブル内の整数値としてその行に対する更新数を記録させる、小さめのトリガプロシージャの例を示します。 新規の行が挿入された場合は、その値はゼロに初期化され、その後の各更新操作時に1が加算されます。

CREATE FUNCTION trigfunc_modcount() RETURNS trigger AS $$
    switch $TG_op {
        INSERT {
            set NEW($1) 0
        }
        UPDATE {
            set NEW($1) $OLD($1)
            incr NEW($1)
        }
        default {
            return OK
        }
    }
    return [array get NEW]
$$ LANGUAGE pltcl;

CREATE TABLE mytab (num integer, description text, modcnt integer);

CREATE TRIGGER trig_mytab_modcount BEFORE INSERT OR UPDATE ON mytab
    FOR EACH ROW EXECUTE FUNCTION trigfunc_modcount('modcnt');

Notice that the trigger function itself does not know the column name; that's supplied from the trigger arguments. This lets the trigger function be reused with different tables. トリガ関数自身は列名を認識していない点に注目してください。 これはトリガの引数として与えられます。 これにより、このトリガ関数を別のテーブルで再利用することができます。