Question

We want to keep the editing history of some table and restore them if necessary. For example, we have following tables. We want to audit the emp table when insert /delete action performed. Besides these, when update on version field happens, we also need to save a copy of related emp_addr records to emp_addr_audit. When users want to roll back to a specif version of one emp, we need to restore the record from emp_audit and emp_addr_audit.

I am thinking to use a trigger to do audit work and a procedure to do restore work. I know the key part is how to maintain the integrity of parent-child tables in audit and restore work. I need some advices. Thanks.

 create table emp (
 emp_id integer primary key,
 version varchar(50)
);

/* Address table */    
create table emp_addr (
 addr_id integer primary key,
 emp_id integer, -- references table emp
 line1 varchar(30),

);

/* Audit table for emp table */    
create table emp_audit (
 operation   character(1),
 updatetime timestamp,
 emp_id integer,
 version varchar(50)

);

/* Audit table for emp_addr table */    
create table emp_addr_audit (
 operation   character(1),
 addr_id integer,
 emp_id integer,
 line1 varchar(30),
);
Était-ce utile?

La solution

I'd recommend adding id field as a primary key to audit tables, since you need to reference to the emp table when rolling back to it and you also need that emp to reference corresponding version of emp_addr. So audit table DDLs should look like this:

/* Audit table for emp table */    
create table emp_audit (
    id bigserial,
    operation   character(1),
    updatetime timestamp,
    emp_id integer,
    version varchar(50),
    CONSTRAINT audit_emp_id PRIMARY KEY (id)
);

/* Audit table for emp_addr table */    
create table emp_addr_audit (
    id bigserial,
    operation   character(1),
    addr_id integer,
    emp_id integer,
    line1 varchar(30),
    CONSTRAINT fk_  audit_emp_id FOREIGN KEY emp_audit_id
       REFERENCES emp_audit (id) MATCH SIMPLE ON UPDATE CASCADE ON DELETE CASCADE;
);

Next you will need to create a trigger, to store changes. Note, that you will have to monitor changes in both tables and create references to the corresponding stored records.

CREATE TRIGGER t_audit_emp_IUD
    AFTER INSERT OR UPDATE OR DELETE -- probably u want only update. Not sure
    ON emp
    FOR EACH ROW
    EXECUTE PROCEDURE emp_modified();

CREATE TRIGGER t_audit_emp_addr_IUD
    AFTER INSERT OR UPDATE OR DELETE 
    ON emp_addr
    FOR EACH ROW
    EXECUTE PROCEDURE emp_addr_modified();

And finally define the functions. Note, that functions should be stored in database before triggers, since triggers reference to the functions.

Rollback function should take emp_audit.id as an input and restore the state according to the audit table. It would be a good idea to save state before rolling back to prevent possible data loss.

If this doesn't answer your question, please clarify which part do you actually need help with.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top