SQLiteでトリガー
項目について、新規追加した際にその作成日と、更新した際に更新日を自動設定しようと、トリガーを使いたいのだがよくわからん。
次のような、作成(登録)日のregistと更新日のmodifiedの要素を持つテーブルを作成し、
CREATE TABLE info (id INTEGER PRIMARY KEY, name TEXT, regist DATETIME, modified DATETIME);
さらに、次の項目追加時のトリガーを作成する(保存時にエラーになる問題のため一時的にSE_T, WHER_E, FRO_M, INT_Oなどと表記してます。了承下さいm(__)m)。
CREATE TRIGGER info_trig_regist AFTER INSERT ON info BEGIN UPDATE info SE_T regist=datetime('now', 'localtime') WHER_E id=NEW.id; END;
追加時に NEW.id を持つエントリの regist 項目を更新するようにしていて、とりあえずはこれで動作する
sqlite> INSERT INT_O info (name) VALUES ('Taro'); sqlite> SELECT * FRO_M info; 1|Taro|2009-12-11 15:16:28|
のだが、更新時のトリガーをさらに次のように設定するとおかしなことになってしまう。
CREATE TRIGGER info_trig_modified AFTER UPDATE ON info BEGIN UPDATE info SE_T modified=datetime('now', 'localtime') WHER_E id=OLD.id; END;
確かに、これで更新時の更新日付は自動設定される、
sqlite> UPDATE info SE_T name='Jiro' WHER_E id=1; sqlite> SELECT * FRO_M info; 1|Jiro|2009-12-11 15:16:28|2009-12-11 15:17:36
が、新規追加時のトリガー中で更新を行っているため、エントリ追加時に更新トリガーも起動され、作成日だけでなく更新日も設定されてしまう。
sqlite> INSERT INT_O info (name) VALUES ('Yoko'); sqlite> SELECT * FRO_M info; 1|Jiro|2009-12-11 15:16:28|2009-12-11 15:17:36 2|Yoko|2009-12-11 15:18:18|2009-12-11 15:18:18
もう少しトリガーを研究というか、工夫しないといけないようだ(続く)。
リンク
次の方は WHEN を使って new.id=0 のエントリを、まず削除して、それから new のデータを持つエントリをトリガー中で INSERT しているが、そちらならいいのかな?
その他もろもろ。
- CREATE TRIGGER – SQLite が認識する SQL - Third impact
- SQLiteのトリガとか – オープンソースなアウトラインプロセッサを一から作る日記
- Cubix | トリガーのサンプル(SQLite)
- SQLite Tutorial: Common Commands and Triggers LG #109
- トリガーの作成 – SQLite入門
- 新規作成 CREATE : PHPとSQLite rakutoネット
次の例では、同じテーブルについて INSERT トリガーで日付を UPDATE してるんで、その際には UPDATE トリガーも呼ばれちゃってるんじゃないかなー。