概念
至少有几种方法可以解决这个问题。我想到的第一个:
通过覆盖INSERT 语句中的输入值,为每行执行的触发器内的category_id 列分配一个值。
动作
这里是 SQL Fiddle 查看实际代码
对于一个简单的测试,我正在创建article 表保存类别及其id,每个category 应该是唯一的。我省略了约束创建 - 这与提出要点无关。
create table article ( id serial, category varchar, category_id int )
使用generate_series() 函数为两个不同的类别插入一些值,以实现自动增量。
insert into article(category, category_id)
select 'stackoverflow', i from generate_series(1,1) i
union all
select 'stackexchange', i from generate_series(1,3) i
创建一个触发函数,它将选择MAX(category_id) 并将其值增加1 以获得category,我们插入一行,然后覆盖该值,然后继续使用实际的INSERT 到表(BEFORE INSERT 触发器负责处理)。
CREATE OR REPLACE FUNCTION category_increment()
RETURNS trigger
LANGUAGE plpgsql
AS
$$
DECLARE
v_category_inc int := 0;
BEGIN
SELECT MAX(category_id) + 1 INTO v_category_inc FROM article WHERE category = NEW.category;
IF v_category_inc is null THEN
NEW.category_id := 1;
ELSE
NEW.category_id := v_category_inc;
END IF;
RETURN NEW;
END;
$$
使用函数作为触发器。
CREATE TRIGGER trg_category_increment
BEFORE INSERT ON article
FOR EACH ROW EXECUTE PROCEDURE category_increment()
为已存在的类别和不存在的类别插入更多值(触发后设备)。
INSERT INTO article(category) VALUES
('stackoverflow'),
('stackexchange'),
('nonexisting');
查询用于选择数据:
select category, category_id From article order by 1,2
初始插入结果:
category category_id
stackexchange 1
stackexchange 2
stackexchange 3
stackoverflow 1
最终插入后的结果:
category category_id
nonexisting 1
stackexchange 1
stackexchange 2
stackexchange 3
stackexchange 4
stackoverflow 1
stackoverflow 2