Abychom tento požadavek splnili, měli bychom přijít s nějakým druhem filtrů, jako jsou TRIGGERs/RULEs na Slave Node, aby se zabránilo přenášení příkazů DELETE a UPDATE. Protože máme co do činění s Slony-I, nemá takový vestavěný mechanismus pro filtrování DML při jejich přehrávání na podřízeném uzlu, i když shromáždil všechny události z hlavního uzlu. (AFAIK Mysql, Oracle, SQL Server podporují filtry ).
Aby to bylo přímočaré, tradiční způsob Slony-I zachovává jedinečnost řádků napříč všemi uzly a jeho základní koncept tabulek musí mít primární klíče. V takovém návrhu architektury je těžké vyloučit příkazy DELETE/UPDATE, vezměte si příklad sloupce primárního klíče „orderid“ tabulky „orders“ má první příkaz INSERT s hodnotou 100 a byl replikován jako první formulář na filtrovaném Slave Node. Později byl proveden příkaz DELETE pro „orderid=100“ a odstraněný řádek, nyní, pokud se jakýkoli příkaz INSERT nebo UPDATE pokusí použít „orderid=100“, uzel Slave zasáhne duplicitní klíč a replikaci jednoduše přeruší.
ERROR: duplicate key value violates unique constraint "reptest_pkey"
DETAIL: Key (id)=(2) already exists.
CONTEXT: SQL statement "INSERT INTO "public"."reptest" ("id", "name") VALUES ($1, $2);"
.....
or
....
CONTEXT: SQL statement "UPDATE ONLY "public"."reptest" SET "id" = $1 WHERE "id" = $2;"
2014-11-17 23:18:53 PST ERROR remoteWorkerThread_1: SYNC aborted
Prováděcí pravidlo tedy nepředstavuje problém, ale když je zavedeno, je třeba být extrémně opatrný. Ve skutečnosti je však použití těchto filtrů na slave uzlu Slony-I velmi křehké, zvláště aplikace/vývojář by to měl mít vždy na paměti, jakékoli duplicitní zadání řádku příkazem INSERT NEBO UPDATE by mohlo replikaci přerušit.
Protože pravidla DML nejsou možná sama se Slony-I, můžeme použít PostgreSQL CREATE RULE…ON DELETE/ON UPDATE NEDĚLEJTE MÍSTO NIC a aplikujte toto PRAVIDLO na tabulku pomocí ALTER TABLE…ENABLE REPLICA RULE pro zrušení příkazu DELETE/UPDATE. Používání této možnosti vyžaduje hodně disciplíny, takže můžete zajistit, aby vaše aplikace a zaměstnanci skutečně dodržovali tato pravidla.
Chcete-li pokračovat v krocích, měli byste mít slony nastavení, v případě, že budete potřebovat nastavení, můžete se podívat na můj minulý příspěvek zde.
Kroky na Slave Node (Master DB:postgres, Slave DB:demo, Port:5432):
1. Zastavte démony slon
2. Vytvořte pravidlo ON DELETE a ON UPDATE NEDĚLEJTE NIC
demo=# CREATE RULE void_delete AS ON DELETE TO reptest DO INSTEAD NOTHING;
CREATE RULE
demo=# CREATE RULE void_update AS ON UPDATE TO reptest DO INSTEAD NOTHING;
CREATE RULE
3. Aplikujte PRAVIDLO na stůl
demo=# ALTER TABLE reptest ENABLE REPLICA RULE void_delete;
ALTER TABLE
demo=# ALTER TABLE reptest ENABLE REPLICA RULE void_update ;
ALTER TABLE
4. Spusťte démony Slon
Nyní si níže můžete všimnout, že UPDATE/DELETE nemá žádný vliv na Slave Node:
postgres=# delete from reptest where id =2;
DELETE 1
postgres=# update reptest set id=2 where id=1;
UPDATE 1
--On Master
postgres=# select * from reptest ;
id | name
----+------------
2 | A
(1 row)
--On Slave
demo=# select * from reptest ;
id | name
----+------------
1 | A
2 | C
(2 rows)
Pokud je příkaz INSERT proveden s hodnotou 1, přeruší replikaci. Pozor…!!
Pamatujte, že existují další způsoby, jak splnit tento požadavek, jako jsou dblinks, Triggers jako BEFORE DELETE...vracejí hodnotu NULL z funkce, ale věřím, že nejúčinnějším způsobem by bylo použití RULE/ENABLE REPLICA RULE, když pracujete s replikací Slony.
Nyní jste možná četli mnoho blogů o nové funkci slotů Logical Decoding Replication v PostgreSQL 9.4, doufáme, že v budoucnu bude zahrnovat koncept filtrování DML na Slave.
Děkujeme za návštěvu.