插入后PostgreSQL强制X量的外键行

时间:2014-03-13 07:02:17

标签: sql postgresql

如果我有以下表格:

CREATE TABLE projects
(
    id SERIAL PRIMARY KEY,
    name VARCHAR(25) NOT NULL,
);
INSERT INTO projects (name) VALUES ('Portfolio Website'), ('Client Website');

CREATE TABLE developers
(
    id SERIAL PRIMARY KEY,
    name VARCHAR(25) NOT NULL,
);
INSERT INTO developers (name) VALUES ('Kevin'), ('Mark'), ('Simon');

CREATE TABLE languages
(
    id SERIAL PRIMARY KEY,
    name VARCHAR(25) NOT NULL,
);
INSERT INTO languages (name) VALUES ('HTML'), ('PHP'), ('ASP.NET'), ('Java');

CREATE TABLE developer_languages
(
    id SERIAL PRIMARY KEY,
    developer INTEGER REFERENCES developers(id),
    language INTEGER REFERENCES languages(id)
);
INSERT INTO developer_languages (developer, language) VALUES (1,1), (1,2), (2,1), (2,3), (3,4);

CREATE TABLE project_developers
(
    id SERIAL PRIMARY KEY,
    project INTEGER REFERENCES projects(id),
    developer INTEGER REFERENCES developers(id)
);

要求是每个项目都有一个HTML开发人员和一个Java开发人员。有没有办法创建一个强制执行此规则的规则?

我知道我可以在项目表中有一个'html_dev'和'java_dev'列,但如果你想让项目中的每个开发人员都存储在这两列和project_developers表中,那么这就是一个额外的数据源。

我希望我的问题有道理吗?我甚至不确定从哪里开始寻找所以我虽然有人可能能指出我正确的方向,谢谢!

1 个答案:

答案 0 :(得分:0)

您尝试做的事情并不容易解决,并且约束触发器不是解决方案,因为您无法创建约束来匹配您的问题。一种解决方案如下,虽然它有点人为:

  1. 从项目表中删除INSERT权限。
  2. 创建一个函数insert_new_project(nm text,html_dev integer,java_dev integer),它在project_developers中插入新项目和两个插入。检查开发人员是否确实具备所需的语言技能。
  3. 删除project_developers的UPDATE权限。在project_developers上创建一个BEFORE DELETE触发器,以检查如果从项目中删除Java或HTML开发人员,则至少还有一个此类开发人员。 (因此,如果您要删除开发人员,请先插入替换。)
  4. 此过程可确保新项目具有两种风格的开发人员,并且当开发人员从项目中删除时,每种风格中至少有一种仍然存在。使用SELECT insert_new_project('New project', 1, 3);插入新项目。