A completely different way to do this using deferred constraints:
CREATE TABLE Category( category_id INT PRIMARY KEY, team_category_id INT, individual_category_id INT, ... ); CREATE TABLE Individual_category( individual_category_id INT PRIMARY KEY, category_id INT NOT NULL, ..., ); CREATE TABLE Team_category( team_category_id INT PRIMARY KEY, category_id INT NOT NULL, ..., );
Make sure Category
is TeamCategory xor IndividualCategory:
alter table Category add constraint category_type_check check ( (team_category_id is null and individual_category_id is not null) or (team_category_id is not null and individual_category_id is null) );
Create deferred integrity constraints so that you can insert a category and a command / individual_category within the same transaction; otherwise, you could not insert a category in front of TeamCategory / IndividualCategory and vice versa. Trap-22.
alter table category add constraint category_team_fk foreign key (team_category_id) references team_category (team_category_id) deferrable initially deferred; alter table category add constraint category_individual_fk foreign key (individual_category_id) references individual_category (individual_category_id) deferrable initially deferred; alter table individual_category add constraint individual_category_fk foreign_key (category_id) references category (category_id) deferrable initially deferred; alter table team_category add constraint team_category_fk foreign_key (category_id) references category (category_id) deferrable initially deferred;
source share