3

テストテーブルを使用しましょう:

CREATE TABLE labs.date_test
(
  pkey int NOT NULL,
  val integer,
  date timestamp without time zone,
  CONSTRAINT date_test_pkey PRIMARY KEY (pkey)
);

以下のように定義されたトリガー関数があります。テーブルの指定した列に日付を挿入する機能です。その引数は、主キー、日付フィールドの名前、および挿入される日付です。

CREATE OR REPLACE FUNCTION tf_set_date()
  RETURNS trigger AS
$BODY$
DECLARE
    table_name text;
    pkey_col text := TG_ARGV[0];
    date_col text := TG_ARGV[1];
    date_val text := TG_ARGV[2];
BEGIN
    table_name := format('%I.%I', TG_TABLE_SCHEMA, TG_TABLE_NAME);
    IF TG_NARGS != 3 THEN
        RAISE 'Wrong number of args for tf_set_date()'
        USING HINT='Check triggers for table ' || table_name;
    END IF;
    EXECUTE format('UPDATE %s SET %I = %s' ||
            ' WHERE %I = ($1::text::%s).%I', 
            table_name, date_col, date_val,
            pkey_col, table_name, pkey_col )
    USING NEW;
    RAISE NOTICE '%', NEW;
    RETURN NEW;
END;
$BODY$
LANGUAGE plpgsql VOLATILE;

実際のトリガー定義は次のとおりです。

CREATE TRIGGER t_set_ready_date
  BEFORE UPDATE OF val
  ON labs.date_test
  FOR EACH ROW
  EXECUTE PROCEDURE tf_set_date('pkey', 'date', 'localtimestamp(0)');

今私が言う:INSERT INTO TABLEdate_test(pkey) values(1);`

次に、次のように更新を実行します。

UPDATE labs.date_test SET val = 1 WHERE pkey = 1;

期待どおりに日付が挿入されるようになりました。しかし、valフィールドはまだNULLです。思ったほどではありません1(というか、私が期待したとおりです)。

私は何を間違っていますか?トリガーの RAISE NOTICE は、NEW がまだ期待どおりであることを示しています。はトリガーUPDATEで許可されていませんか? postgres トリガーに関するBEFORE UPDATE1 つのコメントは、BEFORE UPDATE トリガーに UPDATE ステートメントがある場合、元の UPDATE が上書きされることを示しているようです。誰かが私を助けることができますか?

編集

トリガーを呼び出したのと同じテーブルを更新しようとしています。それも、トリガーを呼び出した UPDATE ステートメントによって変更される同じ行です。Postgresql 9.2 を実行しています

4

2 に答える 2