Re: Proposed archival read only trigger on rows - prevent history modification - Mailing list pgsql-sql

From Steve Midgley
Subject Re: Proposed archival read only trigger on rows - prevent history modification
Date
Msg-id 20080130043352.3EEAF2E283E@postgresql.org
Whole thread Raw
List pgsql-sql
At 07:50 PM 1/29/2008, pgsql-sql-owner@postgresql.org wrote:
>Date: Mon, 28 Jan 2008 20:16:35 -0800
>From: Bryce Nesbitt <bryce1@obviously.com>
>To: pgsql-sql@postgresql.org
>Subject: Proposed archival read only trigger on rows - prevent history 
>modification
>[snip]
>I'm considering building a protective mechanism, and am seeking 
>feedback
>on the idea.  The approach would be to add a new column named "ro" to
>each table at invoice level and below.  Then have a trigger on
>'ro'==true deny the write, and probably raise a huge stink.  As 
>invoice
>are mailed each month, all the supporting data would be set to "ro" 
>true.
>[snip]

Hi Bryce,

I have a similar situation but a little in reverse. I have many sets of 
*incoming* records, which I want to preserve, though at any one time 
there is only one "live" version of the incoming records. Sometimes I 
have to read and compare versions of the records, live or otherwise. 
The logical records I'm talking about occupy a number of tables that 
are joined together in the database itself.

My solution, which required a little middleware engineering, was to 
create two tables for each table that had multiple "versions" of 
records. So, I have  a "property" table and a "property_versions" table 
that have identical table structures. I have a column common to every 
such versioned set of tables called "import_group_id." For live tables, 
this just tells me which version from the "*_versions" table is 
currently being used for that row. The live tables have primary keys 
just like normal ("id" as a serial int field). The "versions" tables' 
primary keys are different, compound keyed off "id" and 
"import_group_id." This permits normalization but also allows multiple 
versions of the same records.

In your case, I'd say you could archive your data table to a 
"data_versions" table. You might archive periodically and leave the 
records on the live table (but knowing that audit versions are safely 
tucked away and easily accessible/comparable), or you might migrate the 
records off the live table onto the versions table (insert followed by 
a delete in a transaction). If you adopted the latter method, you could 
union the two tables to get a complete set of rows. (Via a view even? 
Not sure if you can create a view on a union but it seems likely you 
can..)

You could also choose (like I did) to store multiple versions of the 
records, if your data are slowly changing rather than completely 
unchanging. However it sounds like your situation is such that you want 
to ensure old records are not modified ever. If you set up triggers 
and/or permission on the "data_versions" table, no one can ever delete 
or modify anything there. This might work perfectly for your purposes. 
Data in the live table can be edited as you like but changes to the 
"data_versions" table is simply not permitted. Inserts are allowed to 
data_versions but nothing else..

I hope this idea is useful. If I haven't explained it well, drop me a 
line and I'll try to clarify. Good luck with the project!

Steve



pgsql-sql by date:

Previous
From: "Premsun Choltanwanich"
Date:
Subject: Re: Slow Query problem
Next
From: "Jaroslav Sivy"
Date:
Subject: Sql ORDER BY and ASC/DESC question