Apakah ada cara yang baik untuk menjalankan pemicu untuk setiap record dalam tabel postgres?

22

Saya memiliki sistem di mana saya tidak dapat mengontrol desain beberapa tabel (direplikasi melalui Slony-I), dan jadi saya memiliki serangkaian apa yang kami sebut sebagai 'tabel bayangan', di mana saya mengekstrak beberapa informasi dari tabel yang direplikasi , dan simpan dalam bentuk olahan yang saya butuhkan, sambil menghapus catatan yang ingin saya abaikan.

Saat ini, setelah membuat replika baru, saya menjalankan pembaruan dan menetapkan nilai kembali ke dirinya sendiri (misalnya, UPDATE tablename SET field=field) untuk memaksa pemicu untuk berjalan, tetapi beberapa tabel adalah jutaan catatan, dan terus bertambah, dan dapat memakan waktu 30 menit . (dan kemudian ada vaccuum juga).

Apakah ada cara yang lebih baik untuk memicunya, atau beberapa cara untuk menulis suatu fungsi sehingga akan bekerja dengan input yang disalurkan atau NEWtergantung pada konteks panggilan? Saya enggan untuk menjaga dua fungsi yang berbeda, karena saya telah melihat terlalu banyak waktu di mana yang satu diperbarui, dan bukan yang lain.

Joe
sumber
Saya tahu bagaimana menjalankan pemicu ... Saya bertanya apakah ada cara yang baik .
Joe

Jawaban:

19

Itu bisa dilakukan, menggunakan templat berikut:

CREATE TABLE tablename ( ... );

/* for direct invocation */
CREATE FUNCTION propagate_data(newrow tablename) RETURNS void
LANGUAGE plpgsql
AS $$
BEGIN
    INSERT INTO other_table VALUES (newrow.a, newrow.b, ...);
END:
$$;

/* trigger function wrapper */
CREATE FUNCTION propagate_data_trg() RETURNS trigger
LANGUAGE plpgsql
AS $$
BEGIN
    PERFORM propagate_data(NEW);
END;
$$;

CREATE TRIGGER propagate_data AFTER INSERT ON tablename FOR EACH ROW
    EXECUTE PROCEDURE propagate_data_trg();
Peter Eisentraut
sumber
Doh ... Saya memikirkannya dari belakang (mencoba membuat fungsi pemicu bisa dipanggil dengan prosedur, bukan visa-sebaliknya).
Joe
1
Ketika saya benar-benar melakukannya, saya menyadari bahwa 'baris' adalah kata yang dilindungi undang-undang, jadi saya mengoreksi contohnya sehingga orang lain tidak akan menghabiskan waktu untuk debugging.
Joe
1
Saya seharusnya mengikuti tahun yang lalu. Butuh beberapa saat sebelum saya berhasil membuat semuanya berfungsi di sistem saya ... dan metode ini berhasil, tetapi kinerjanya sangat buruk. (itu pergi dari 30 menit menjadi lebih dari satu hari untuk menyelesaikan).
Joe