1、Fault injection to test PostgreSQL codeAsim R P apraveenpivotal.io Pune,IndiaAgenda What is lacking in current testing frameworks?What is fault injection?Proposal to inject faults Tests to demonstrate proposed faultinjector patchTesting frameworks in PostgreSQL pg_regress(src/test/regress)A test is
2、written as a.sql file Expected output is saved as an answer file(.out)pg_regress runs a.sql file,compares the output with the answer isolation(src/test/isolation)tests concurrent transactions .spec file-SQL commands within each transaction and how to interleave themisolation:test that select waits f
3、or altersession“s1”setup BEGIN ISOLATION LEVEL READ COMMITTED;step“alter1”ALTER TABLE test ADD RENAME TO test2;step“commit1”COMMIT;session“s2”setup SET default_transaction_isolation=read committed;step“select2”SELECT*from test;permutation“alter1”“s2”“commit1”Testing frameworks in PostgreSQL TAP-test
4、s written in perl(Test:More)Orchestrate a cluster-master and one or more standby initdb,start/stop cluster,etc.src/test/perl/README src/test/modules(not run in CI)modular testing of a specific component,e.g.planner src/test/modules/READMEWhat is lacking in PostgreSQL tests?Test that a backend is kil
5、led after writing commit record but before updating the transaction status in pg_clog Is synchronous replication really synchronous?Was a cached plan reused?Anything comes to your mind?Fault injection Unconference discussion at PGcon 2019 in Ottawa Already being used in Greenplum Patch proposed on p
6、gsql-hackers:https:/www.postgresql.org/message-id/flat/CANXE4TdxdESX1jKw48xet-5GvBFVSq%3D4cgNeioTQff372KO45A%Fault point(./configure CPPFLAGS=-DFAULT_INJECTOR)Fault point-macro definitionSet a fault using its name CREATE EXTENSION faultinjector;Enable the“heap_insert”fault when a tuple is inserted i
7、nto“mytable”SELECT inject_fault(heap_insert,error,mytable,);Wait until the fault is triggered(blocking call)SELECT wait_until_triggered_fault(heap_insert,1);Check the status SELECT inject_fault(heap_insert,status);Reset the fault SELECT inject_fault(heap_insert,reset);More on inject_faultinject_faul
8、t(,trigger only after the fault point is reached as many number of times,stop after triggerring as many number of times(fault state completed)seconds to sleep in a sleep fault)inject_fault_remote()Same as inject_fault()Additional args:hostname and port number New libpq message to inject faults Usefu
9、l for testing standby servers in a clusterFault types error:elog(ERORR)leads to transaction abort skip:do nothing-indicates that the fault point was reached,also used for custom action suspend reset statusFault states injected but not triggered-SELECT inject_fault();completed-triggered maximum numbe
10、r of times,will no longer trigger triggered-reached during execution at least onceFaults offer fine grained control Enable complex testing scenarios Was a specific flag in shared memory set,and when?Was a branch in a function taken?Can be used in regress,isolation as well as TAP testsDemonstrative t
11、est:speculative insertCREATE TABLE test(key TEXT,data TEXT);CREATE UNIQUE INDEX ON test(key);T1:INSERT INTO test values(k1,inserted T1)ON CONFLICT DO UPDATE SET data=test.data|conflict update T1;T2:INSERT INTO test values(k1,inserted T2)ON CONFLICT DO UPDATE SET data=test.data|conflict update T2;Dem
12、onstrative test:speculative insertConflicts detected after a tuple is inserted into heap but before inserting into index are handled properly T1 goes first and inserts the tuple into heap Before T1 updates the index,T2 inserts into both,heap and the index.T2 sees no conflicts because T1 is still in
13、progress.T1 moves ahead.T1 should detect a conflict and abort.Demonstrative test:speculative insert Find it in the faultinjector patch:src/test/isolation/specs/insert-conflict-with-faults.specDemonstrative test:synchronous replicationEnsure that commits on master block until a synchronous standby ac
14、knowledges the commit Master writes a commit record The backend process on master starts waiting for standby to flush WAL upto the commit LSN Standby goes down before the WAL receiver writes WAL upto the commit LSNDemonstrative test:synchronous replication Find it in the faultinjector patch,its a TAP test:src/test/recovery/t/007_sync_rep.plTHANKS