londiste.local_remove_table: dynamically detect triggers to be dropped.
authorMarko Kreen <markokr@gmail.com>
Mon, 10 May 2010 12:25:56 +0000 (15:25 +0300)
committerMarko Kreen <markokr@gmail.com>
Mon, 10 May 2010 21:15:29 +0000 (00:15 +0300)
sql/londiste/expected/londiste_provider.out
sql/londiste/functions/londiste.local_remove_table.sql
sql/londiste/sql/londiste_provider.sql

index fb162245394cd22ae295c7683c9eea88c5678aa8..e7c21fbb4c90d4b843ce0d2a39f8bfd128a74455 100644 (file)
@@ -41,6 +41,12 @@ select * from londiste.local_add_table('aset', 'public.testdata');
       200 | Table added: public.testdata
 (1 row)
 
+select tgname from pg_trigger where tgrelid = 'public.testdata'::regclass;
+     tgname     
+----------------
+ _londiste_aset
+(1 row)
+
 insert into testdata (txt) values ('test-data');
 select * from londiste.get_table_list('aset');
    table_name    | local | merge_state | custom_snapshot | table_attrs | dropped_ddl | copy_role 
@@ -68,6 +74,11 @@ select * from londiste.local_remove_table('aset', 'public.testdata');
       400 | Table not found: public.testdata
 (1 row)
 
+select tgname from pg_trigger where tgrelid = 'public.testdata'::regclass;
+ tgname 
+--------
+(0 rows)
+
 select * from londiste.get_table_list('aset');
  table_name | local | merge_state | custom_snapshot | table_attrs | dropped_ddl | copy_role 
 ------------+-------+-------------+-----------------+-------------+-------------+-----------
index d4f4aea2995dd2fe9761992a42b8becf87db2411..d70dceda7160ef94d2ff6a7503c5e3ac53fdd6a0 100644 (file)
@@ -20,6 +20,7 @@ declare
     fq_table_name   text;
     logtrg_name     text;
     tbl             record;
+    b_queue_name    bytea;
 begin
     fq_table_name := londiste.make_fqname(i_table_name);
 
@@ -33,10 +34,22 @@ begin
     end if;
 
     if tbl.local then
-        -- drop trigger if exists
-        logtrg_name := i_queue_name || '_logtrigger';
-        execute 'drop trigger if exists ' || quote_ident(logtrg_name)
-                || ' on ' || londiste.quote_fqname(fq_table_name);
+        -- cast to bytea
+        b_queue_name := replace(i_queue_name, E'\\', E'\\\\')::bytea;
+
+        -- drop all replication triggers that target our queue.
+        -- by checking trigger func and queue name there is not
+        -- dependency on naming standard or side-storage.
+        for logtrg_name in
+            select tgname from pg_catalog.pg_trigger
+             where tgrelid = londiste.find_table_oid(fq_table_name)
+               and tgfoid in ('pgq.sqltriga'::regproc::oid, 'pgq.logutriga'::regproc::oid)
+               and substring(tgargs for (position(E'\\000'::bytea in tgargs) - 1)) = b_queue_name
+        loop
+            execute 'drop trigger ' || quote_ident(logtrg_name)
+                    || ' on ' || londiste.quote_fqname(fq_table_name);
+        end loop;
+
         -- reset data
         update londiste.table_info
             set local = false,
index 196023ef7e0f823e24fb9f872faba570479f8a63..6530737985b4a82cbde7efc7d1ac78818406cd1c 100644 (file)
@@ -21,11 +21,13 @@ select * from pgq_node.create_node('aset', 'root', 'rnode', 'londiste_root', nul
 
 select * from londiste.local_add_table('aset', 'public.testdata_nopk');
 select * from londiste.local_add_table('aset', 'public.testdata');
+select tgname from pg_trigger where tgrelid = 'public.testdata'::regclass;
 insert into testdata (txt) values ('test-data');
 select * from londiste.get_table_list('aset');
 select * from londiste.local_show_missing('aset');
 select * from londiste.local_remove_table('aset', 'public.testdata');
 select * from londiste.local_remove_table('aset', 'public.testdata');
+select tgname from pg_trigger where tgrelid = 'public.testdata'::regclass;
 select * from londiste.get_table_list('aset');
 
 select ev_id, ev_type, ev_data, ev_extra1 from pgq.event_template;