このようなテーブル構造を想定すると:
use test;
create table song(
song_id integer,
rating_avg double,
rating_sum integer,
rating_count integer);
create table rating(
song_id integer,
user_id integer,
rating integer);
次のトリガーを定義します。
delimiter $$
create trigger bi_song before insert on test.song
for each row
begin
set NEW.rating_sum = 0;
set NEW.rating_count = 0;
set NEW.rating_avg = NULL;
end
$$
create trigger ai_rating after insert on test.rating
for each row
begin
update song set
rating_sum = rating_sum + NEW.rating,
rating_count = rating_count + 1,
rating_avg = rating_sum / rating_count
where song_id = NEW.song_id;
end
$$
delimiter ;
そして、次のように機能するはずです:
mysql> insert into song(song_id) values (1);
Query OK, 1 row affected (0.06 sec)
mysql> select * from song;
+---------+------------+------------+--------------+
| song_id | rating_avg | rating_sum | rating_count |
+---------+------------+------------+--------------+
| 1 | NULL | 0 | 0 |
+---------+------------+------------+--------------+
1 row in set (0.00 sec)
mysql> insert into rating(song_id, user_id, rating) values (1, 1000, 5);
Query OK, 1 row affected (0.05 sec)
mysql> select * from song;
+---------+------------+------------+--------------+
| song_id | rating_avg | rating_sum | rating_count |
+---------+------------+------------+--------------+
| 1 | 5 | 5 | 1 |
+---------+------------+------------+--------------+
1 row in set (0.00 sec)
mysql> insert into rating(song_id, user_id, rating) values (1, 1001, 7);
Query OK, 1 row affected (0.05 sec)
mysql> select * from song;
+---------+------------+------------+--------------+
| song_id | rating_avg | rating_sum | rating_count |
+---------+------------+------------+--------------+
| 1 | 6 | 12 | 2 |
+---------+------------+------------+--------------+
1 row in set (0.00 sec)
これは、トリガーの操作方法を説明するために非常に単純化されています。実際のアプリケーションでは、より多くの列、インデックスなどがあります。