【发布时间】:2011-08-22 16:18:34
【问题描述】:
我正在尝试构建我的第一个涉及继承的 Postgres 数据库模式。我知道PostgreSQL foreign key not existing, issue of inheritance? 中讨论的外键问题。然而,这个问题的答案并没有真正给出解决方案的例子,所以我想出了自己的(灵感来自http://people.planetpostgresql.org/dfetter/index.php?/archives/51-Partitioning-Is-Such-Sweet-Sorrow.html):
CREATE TABLE a (
id SERIAL PRIMARY KEY INITIALLY DEFERRED,
foo TEXT
);
CREATE TABLE b (
PRIMARY KEY(id),
a_number REAL
) inherits(a);
CREATE TABLE c (
PRIMARY KEY(id),
a_number INTEGER
) inherits(a);
-- SELECT * FROM ONLY a; will always return an empty record.
CREATE TABLE x (
a_id INTEGER NOT NULL,
bar TEXT
);
CREATE TABLE xb (
FOREIGN KEY( a_id ) REFERENCES b INITIALLY DEFERRED
) inherits(x);
CREATE TABLE xc (
FOREIGN KEY( a_id ) REFERENCES c INITIALLY DEFERRED
) inherits(x);
为了执行有效的INSERT INTO x,我定义了以下触发器:
CREATE FUNCTION marshal_x()
RETURNS TRIGGER
LANGUAGE plpgsql
AS $$
DECLARE
ref_table varchar;
BEGIN
SELECT INTO ref_table p.relname FROM a, pg_class p WHERE a.id = NEW.a_id AND a.tableoid = p.oid;
IF ref_table = 'b'
THEN INSERT INTO xb ( a_id, bar ) VALUES ( NEW.a_id, NEW.bar );
ELSIF ref_table = 'c'
THEN INSERT INTO xc ( a_id, bar ) VALUES ( NEW.a_id, NEW.bar );
END IF;
RETURN NULL;
END;
$$;
CREATE TRIGGER insert_x_trg
BEFORE INSERT ON x
FOR EACH ROW
EXECUTE PROCEDURE marshal_x();
编辑:有没有人看到这个定义有问题,这对我未经训练的眼睛来说并不明显?
假设表 c 为空。会表现的
SELECT * FROM a JOIN x ON a.id= x.a_id;
同
SELECT * FROM b JOIN x ON b.id= x.a_id;
?非常感谢。
伊萨姆
【问题讨论】: