audit log with context per task instead of just transaction
This commit is contained in:
@ -0,0 +1,12 @@
|
||||
--liquibase formatted sql
|
||||
|
||||
|
||||
-- ============================================================================
|
||||
-- NUMERIC-HASH-FUNCTIONS
|
||||
--changeset hash:1 endDelimiter:--//
|
||||
-- ----------------------------------------------------------------------------
|
||||
|
||||
create function bigIntHash(text) returns bigint as $$
|
||||
select ('x'||substr(md5($1),1,16))::bit(64)::bigint;
|
||||
$$ language sql;
|
||||
--//
|
@ -23,7 +23,8 @@ do $$
|
||||
*/
|
||||
create table tx_context
|
||||
(
|
||||
txId bigint primary key not null,
|
||||
contextId bigint primary key not null,
|
||||
txId bigint not null,
|
||||
txTimestamp timestamp not null,
|
||||
currentUser varchar(63) not null, -- not the uuid, because users can be deleted
|
||||
assumedRoles varchar not null, -- not the uuids, because roles can be deleted
|
||||
@ -42,7 +43,7 @@ create index on tx_context using brin (txTimestamp);
|
||||
*/
|
||||
create table tx_journal
|
||||
(
|
||||
txId bigint not null references tx_context (txId),
|
||||
contextId bigint not null references tx_context (contextId),
|
||||
targetTable text not null,
|
||||
targetUuid uuid not null, -- Assumes that all audited tables have a uuid column.
|
||||
targetOp operation not null,
|
||||
@ -61,28 +62,33 @@ create index on tx_journal (targetTable, targetUuid);
|
||||
create or replace function tx_journal_trigger()
|
||||
returns trigger
|
||||
language plpgsql as $$
|
||||
declare
|
||||
curTask text;
|
||||
curContextId bigint;
|
||||
begin
|
||||
curTask := currentTask();
|
||||
curContextId := txid_current()+bigIntHash(curTask);
|
||||
|
||||
insert
|
||||
into tx_context
|
||||
values (txid_current(), now(),
|
||||
currentUser(), assumedRoles(), currentTask(), currentRequest())
|
||||
into tx_context (contextId, txId, txTimestamp, currentUser, assumedRoles, currentTask, currentRequest)
|
||||
values (curContextId, txid_current(), now(),
|
||||
currentUser(), assumedRoles(), curTask, currentRequest())
|
||||
on conflict do nothing;
|
||||
|
||||
case tg_op
|
||||
when 'INSERT' then insert
|
||||
into tx_journal
|
||||
values (txid_current(),
|
||||
values (curContextId,
|
||||
tg_table_name, new.uuid, tg_op::operation,
|
||||
to_jsonb(new));
|
||||
when 'UPDATE' then insert
|
||||
into tx_journal
|
||||
values (txid_current(),
|
||||
values (curContextId,
|
||||
tg_table_name, old.uuid, tg_op::operation,
|
||||
jsonb_changes_delta(to_jsonb(old), to_jsonb(new)));
|
||||
when 'DELETE' then insert
|
||||
into tx_journal
|
||||
values (txid_current(),
|
||||
values (curContextId,
|
||||
tg_table_name, old.uuid, 'DELETE'::operation,
|
||||
null::jsonb);
|
||||
else raise exception 'Trigger op % not supported for %.', tg_op, tg_table_name;
|
||||
|
@ -14,7 +14,7 @@ declare
|
||||
currentTask varchar;
|
||||
emailAddr varchar;
|
||||
begin
|
||||
currentTask = 'creating RBAC test contact ' || contLabel;
|
||||
currentTask = 'creating contact test-data ' || contLabel;
|
||||
execute format('set local hsadminng.currentTask to %L', currentTask);
|
||||
|
||||
emailAddr = 'contact-admin@' || cleanIdentifier(contLabel) || '.example.com';
|
||||
|
@ -21,7 +21,7 @@ declare
|
||||
emailAddr varchar;
|
||||
begin
|
||||
fullName := concat_ws(', ', newTradeName, newFamilyName, newGivenName);
|
||||
currentTask = 'creating RBAC test person ' || fullName;
|
||||
currentTask = 'creating person test-data ' || fullName;
|
||||
emailAddr = 'person-' || left(cleanIdentifier(fullName), 32) || '@example.com';
|
||||
call defineContext(currentTask);
|
||||
perform createRbacUser(emailAddr);
|
||||
|
@ -17,7 +17,7 @@ declare
|
||||
relatedContact hs_office_contact;
|
||||
begin
|
||||
idName := cleanIdentifier( personTradeName|| '-' || contactLabel);
|
||||
currentTask := 'creating RBAC test partner ' || idName;
|
||||
currentTask := 'creating partner test-data ' || idName;
|
||||
call defineContext(currentTask, null, 'superuser-alex@hostsharing.net', 'global#global.admin');
|
||||
execute format('set local hsadminng.currentTask to %L', currentTask);
|
||||
|
||||
|
@ -23,7 +23,7 @@ declare
|
||||
|
||||
begin
|
||||
idName := cleanIdentifier( anchorPersonTradeName || '-' || holderPersonFamilyName);
|
||||
currentTask := 'creating RBAC test relationship ' || idName;
|
||||
currentTask := 'creating relationship test-data ' || idName;
|
||||
call defineContext(currentTask, null, 'superuser-alex@hostsharing.net', 'global#global.admin');
|
||||
execute format('set local hsadminng.currentTask to %L', currentTask);
|
||||
|
||||
|
@ -14,7 +14,7 @@ declare
|
||||
currentTask varchar;
|
||||
emailAddr varchar;
|
||||
begin
|
||||
currentTask = 'creating RBAC test bankaccount ' || givenHolder;
|
||||
currentTask = 'creating bankaccount test-data ' || givenHolder;
|
||||
execute format('set local hsadminng.currentTask to %L', currentTask);
|
||||
|
||||
emailAddr = 'bankaccount-admin@' || cleanIdentifier(givenHolder) || '.example.com';
|
||||
|
@ -19,7 +19,7 @@ declare
|
||||
newDebitorNumber numeric(6);
|
||||
begin
|
||||
idName := cleanIdentifier( partnerTradeName|| '-' || billingContactLabel);
|
||||
currentTask := 'creating RBAC test debitor ' || idName;
|
||||
currentTask := 'creating debitor test-data ' || idName;
|
||||
call defineContext(currentTask, null, 'superuser-alex@hostsharing.net', 'global#global.admin');
|
||||
execute format('set local hsadminng.currentTask to %L', currentTask);
|
||||
|
||||
|
@ -9,6 +9,8 @@ databaseChangeLog:
|
||||
file: db/changelog/004-jsonb-changes-delta.sql
|
||||
- include:
|
||||
file: db/changelog/005-uuid-ossp-extension.sql
|
||||
- include:
|
||||
file: db/changelog/006-numeric-hash-functions.sql
|
||||
- include:
|
||||
file: db/changelog/010-context.sql
|
||||
- include:
|
||||
|
Reference in New Issue
Block a user