-3

`私は、従業員がいつ働き始めたかを表すstartdate列(s_date)を持つテーブル(workers)を持っています。そこで、1 年 (365 日) 未満の勤務であれば、例外を与えるというトリガーを作成したいと考えています。しかし、コードに何か問題があります。ヘルプ_?

CREATE OR REPLACE FUNCTION control_func() RETURNS TRIGGER AS '
declare 
int1 integer;
tt  Date;
begin 
select now()::date into tt;
select s_date from workers; 
if(tt-s_date<365) then
RAISE EXCEPTION ''A message'';
end if;
RETURN NULL;
END;
' LANGUAGE  'plpgsql';
4

2 に答える 2

4

いくつかの問題があります。まず第一に、関数本体を引用するために単一引用符を使用しないでください。これは大きな混乱を招くだけです。代わりにドル引用符を使用してください。

create or replace function f() returns trigger as $$
    ...
$$ language plpgsql;

次に、これは何も役に立ちません:

select s_date from workers;

s_dateからすべての値を取得してからworkers、それらをすべて破棄しようとします。トリガーの現在の行を確認したいのですが、それは次の場所にありますNEW

NEW
データ型RECORD; INSERT/UPDATE行レベル トリガーでの操作の新しいデータベース行を保持する変数。この変数はNULL、ステートメント レベルのトリガーとDELETE操作用です。

したがってnew.s_date、興味のある日付を確認するために見ることができます。

select now()::date into tt;
if tt - new.s_date < 365 then
    raise exception 'A message';
end if;

これはおそらく行レベルのbefore insert or updateトリガーであるため、return null;ここでは不要です。細かいマニュアルから:

操作の前に起動される行レベルのトリガーには、次の選択肢があります。

  • NULL現在の行の操作をスキップして戻ることができます。これは、トリガーを呼び出した行レベルの操作 (特定のテーブル行の挿入、変更、または削除) を実行しないようにエグゼキューターに指示します。
  • 行レベルINSERTおよびUPDATEトリガーの場合のみ、返された行が挿入される行になるか、更新される行を置き換えます。これにより、トリガー関数は、挿入または更新される行を変更できます。

したがって、return null;「新しいレコードが有効な場合は、この INSERT または UPDATE をスキップする」という意味であり、それはあなたが望むものではありません。あなたがしたいreturn new;

未使用の変数もあります。そして、あなたcurrent_dateの代わりに使うことができますtt

関数は次のようになります。

create or replace function control_func() returns trigger as $$
begin
    if current_date - new.s_date < 365 then
        raise exception 'A message'; 
    end if;
    return new;
end;
$$ language plpgsql;
于 2013-01-03T22:11:11.897 に答える
0

編集: 初期構文はdatediff. ただし、これは MYSQL 構文です。したがって、上記の詳細で正しい答えの方が適切です。;-)

これをコードに入力して、別の変数を追加して保存しs_dateますss

If Datediff(days, tt, ss) < 365 then

于 2013-01-03T21:28:38.577 に答える