代码之家  ›  专栏  ›  技术社区  ›  anjanb

用于联接父子审核表的Postgres SQL

  •  0
  • anjanb  · 技术社区  · 14 年前

    我们用的是 "1 audit table for each monitored Table" 设计;但是,在我们的例子中 emp(PARENT) 表有子表 emp_address emp_audit emp_addr_audit tables

    postgresauditsql:如何连接父表和子表以进行报告。

    /* Employee table */    
    create table emp (
     emp_id integer primary key,
     empnum  integer,
     empname 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),
     emp_id integer,
     empnum  integer,
     empname varchar(50),
     updatetime timestamp,
     txid bigint
    );
    
    /* Audit table for emp_addr table */    
    create table emp_addr_audit (
     operation   character(1),
     addr_id integer,
     emp_id integer,
     line1 varchar(30),
     updatetime timestamp,
     txid bigint
    );
    

    我们使用hibernate(java)进行持久化,hibernate只更新那些在更新操作中修改了列的表。考虑到这一点,我可能会在emp_addr峎audit表中有多行(比如说5行)对应emp_audit表中的1行。反之亦然。

    empname,第1行,操作(插入/删除/更新),更新时间

    让我们考虑两个场景来了解需要什么:

    1. emp 属性被创建。然后在单独的事务中,在 emp_addr 环境管理审计 表和1行 emp_addr_audit
    2. 两者兼而有之 电磁脉冲 雇员地址 属性在单个事务中创建。这将确保 和1排 雇员地址审计 . 现在,报表将只有1行(因为两个表行都是在一个事务中创建的)。

    脚本
    事务#1:我在emp和emp_addr中都插入一行。这将在emp_audit和emp_addr_audit中各生成一行
    事务#2:我更新上面的emp'属性。这将在emp_audit中生成一个UPDATE行。
    事务#3:我更新上面emp_addr的属性。这将导致emp_addr_audit中出现一个更新行。

    我尝试了下面的SQL#1,它返回了3行(如预期);

    SELECT emp.*, addr.*
     FROM  emp_audit emp 
     FULL OUTER JOIN emp_addr_audit addr USING(emp_id, txid);
    

    但是,当我添加 where
    SQL#2

    SELECT emp.*, addr.*
     FROM  emp_audit emp 
            FULL OUTER JOIN emp_addr_audit addr USING(emp_id, txid);
    WHERE  emp.empnum = 20;
    

    SQL会做什么 仍然是 能为这3个事务获取3行,这样我仍然可以基于empnum过滤掉?

    1 回复  |  直到 14 年前
        1
  •  1
  •   morja    14 年前

    完全联接将从两个表中创建一个表,并用空值填充空(不匹配)行。当只选择具有emp.empnum公司=20它当然不会返回中有NULL的最后一行emp.empnum公司.

    也许你只能在emp_id上加入,然后按txid分组。但这不会那么容易。您可能需要始终更新两个表。或者使用一些更高级的逻辑(比如:选择一个emp_id的所有事务,其中一方是空的,直到下一整行为止,并用最后一个整行填充缺失的部分)。