These patches should fix check constraints not inheriting
when added by alter table add constraint. The first file patches backend/commands/command.c and the latter is a patch to the alter table regression test. Stephan Szabo
This commit is contained in:
parent
3f5563d131
commit
7160c86ec2
@ -8,7 +8,7 @@
|
|||||||
*
|
*
|
||||||
*
|
*
|
||||||
* IDENTIFICATION
|
* IDENTIFICATION
|
||||||
* $Header: /cvsroot/pgsql/src/backend/commands/Attic/command.c,v 1.130 2001/05/30 12:57:36 momjian Exp $
|
* $Header: /cvsroot/pgsql/src/backend/commands/Attic/command.c,v 1.131 2001/05/30 13:00:03 momjian Exp $
|
||||||
*
|
*
|
||||||
* NOTES
|
* NOTES
|
||||||
* The PerformAddAttribute() code, like most of the relation
|
* The PerformAddAttribute() code, like most of the relation
|
||||||
@ -1215,6 +1215,7 @@ AlterTableAddConstraint(char *relationName,
|
|||||||
Relation rel;
|
Relation rel;
|
||||||
Node *expr;
|
Node *expr;
|
||||||
char *name;
|
char *name;
|
||||||
|
Oid myrelid;
|
||||||
|
|
||||||
if (constr->name)
|
if (constr->name)
|
||||||
name = constr->name;
|
name = constr->name;
|
||||||
@ -1224,6 +1225,7 @@ AlterTableAddConstraint(char *relationName,
|
|||||||
constlist = makeList1(constr);
|
constlist = makeList1(constr);
|
||||||
|
|
||||||
rel = heap_openr(relationName, AccessExclusiveLock);
|
rel = heap_openr(relationName, AccessExclusiveLock);
|
||||||
|
myrelid = RelationGetRelid(rel);
|
||||||
|
|
||||||
/* make sure it is not a view */
|
/* make sure it is not a view */
|
||||||
if (rel->rd_rel->relkind == RELKIND_VIEW)
|
if (rel->rd_rel->relkind == RELKIND_VIEW)
|
||||||
@ -1318,6 +1320,35 @@ AlterTableAddConstraint(char *relationName,
|
|||||||
*/
|
*/
|
||||||
AddRelationRawConstraints(rel, NIL, constlist);
|
AddRelationRawConstraints(rel, NIL, constlist);
|
||||||
heap_close(rel, NoLock);
|
heap_close(rel, NoLock);
|
||||||
|
|
||||||
|
if (inh) {
|
||||||
|
List *child,
|
||||||
|
*children;
|
||||||
|
|
||||||
|
/* this routine is actually in the planner */
|
||||||
|
children = find_all_inheritors(myrelid);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* find_all_inheritors does the recursive search of the
|
||||||
|
* inheritance hierarchy, so all we have to do is process all
|
||||||
|
* of the relids in the list that it returns.
|
||||||
|
*/
|
||||||
|
foreach(child, children)
|
||||||
|
{
|
||||||
|
Oid childrelid = lfirsti(child);
|
||||||
|
char *childrelname;
|
||||||
|
|
||||||
|
if (childrelid == myrelid)
|
||||||
|
continue;
|
||||||
|
rel = heap_open(childrelid, AccessExclusiveLock);
|
||||||
|
childrelname = pstrdup(RelationGetRelationName(rel));
|
||||||
|
heap_close(rel, AccessExclusiveLock);
|
||||||
|
|
||||||
|
AlterTableAddConstraint(childrelname, false, newConstraint);
|
||||||
|
|
||||||
|
pfree(childrelname);
|
||||||
|
}
|
||||||
|
}
|
||||||
pfree(constlist);
|
pfree(constlist);
|
||||||
|
|
||||||
break;
|
break;
|
||||||
|
@ -375,3 +375,76 @@ NOTICE: ALTER TABLE ... ADD CONSTRAINT will create implicit trigger(s) for FORE
|
|||||||
ERROR: Unable to identify an operator '=' for types 'text' and 'int4'
|
ERROR: Unable to identify an operator '=' for types 'text' and 'int4'
|
||||||
You will have to retype this query using an explicit cast
|
You will have to retype this query using an explicit cast
|
||||||
-- temp tables should go away by themselves, need not drop them.
|
-- temp tables should go away by themselves, need not drop them.
|
||||||
|
-- test check constraint adding
|
||||||
|
create table atacc1 ( test int );
|
||||||
|
-- add a check constraint
|
||||||
|
alter table atacc1 add constraint atacc_test1 check (test>3);
|
||||||
|
-- should fail
|
||||||
|
insert into atacc1 (test) values (2);
|
||||||
|
ERROR: ExecAppend: rejected due to CHECK constraint atacc_test1
|
||||||
|
-- should succeed
|
||||||
|
insert into atacc1 (test) values (4);
|
||||||
|
drop table atacc1;
|
||||||
|
-- let's do one where the check fails when added
|
||||||
|
create table atacc1 ( test int );
|
||||||
|
-- insert a soon to be failing row
|
||||||
|
insert into atacc1 (test) values (2);
|
||||||
|
-- add a check constraint (fails)
|
||||||
|
alter table atacc1 add constraint atacc_test1 check (test>3);
|
||||||
|
ERROR: AlterTableAddConstraint: rejected due to CHECK constraint atacc_test1
|
||||||
|
insert into atacc1 (test) values (4);
|
||||||
|
drop table atacc1;
|
||||||
|
-- let's do one where the check fails because the column doesn't exist
|
||||||
|
create table atacc1 ( test int );
|
||||||
|
-- add a check constraint (fails)
|
||||||
|
alter table atacc1 add constraint atacc_test1 check (test1>3);
|
||||||
|
ERROR: Attribute 'test1' not found
|
||||||
|
drop table atacc1;
|
||||||
|
-- something a little more complicated
|
||||||
|
create table atacc1 ( test int, test2 int, test3 int);
|
||||||
|
-- add a check constraint (fails)
|
||||||
|
alter table atacc1 add constraint atacc_test1 check (test+test2<test3*4);
|
||||||
|
-- should fail
|
||||||
|
insert into atacc1 (test,test2,test3) values (4,4,2);
|
||||||
|
ERROR: ExecAppend: rejected due to CHECK constraint atacc_test1
|
||||||
|
-- should succeed
|
||||||
|
insert into atacc1 (test,test2,test3) values (4,4,5);
|
||||||
|
drop table atacc1;
|
||||||
|
-- lets do some naming tests
|
||||||
|
create table atacc1 (test int check (test>3), test2 int);
|
||||||
|
alter table atacc1 add check (test2>test);
|
||||||
|
-- should fail for $2
|
||||||
|
insert into atacc1 (test2, test) values (3, 4);
|
||||||
|
ERROR: ExecAppend: rejected due to CHECK constraint $2
|
||||||
|
drop table atacc1;
|
||||||
|
-- inheritance related tests
|
||||||
|
create table atacc1 (test int);
|
||||||
|
create table atacc2 (test2 int);
|
||||||
|
create table atacc3 (test3 int) inherits (atacc1, atacc2);
|
||||||
|
alter table atacc2 add constraint foo check (test2>0);
|
||||||
|
-- fail and then succeed on atacc2
|
||||||
|
insert into atacc2 (test2) values (-3);
|
||||||
|
ERROR: ExecAppend: rejected due to CHECK constraint foo
|
||||||
|
insert into atacc2 (test2) values (3);
|
||||||
|
-- fail and then succeed on atacc3
|
||||||
|
insert into atacc3 (test2) values (-3);
|
||||||
|
ERROR: ExecAppend: rejected due to CHECK constraint foo
|
||||||
|
insert into atacc3 (test2) values (3);
|
||||||
|
drop table atacc3;
|
||||||
|
drop table atacc2;
|
||||||
|
drop table atacc1;
|
||||||
|
-- let's try only to add only to the parent
|
||||||
|
create table atacc1 (test int);
|
||||||
|
create table atacc2 (test2 int);
|
||||||
|
create table atacc3 (test3 int) inherits (atacc1, atacc2);
|
||||||
|
alter table only atacc2 add constraint foo check (test2>0);
|
||||||
|
-- fail and then succeed on atacc2
|
||||||
|
insert into atacc2 (test2) values (-3);
|
||||||
|
ERROR: ExecAppend: rejected due to CHECK constraint foo
|
||||||
|
insert into atacc2 (test2) values (3);
|
||||||
|
-- both succeed on atacc3
|
||||||
|
insert into atacc3 (test2) values (-3);
|
||||||
|
insert into atacc3 (test2) values (3);
|
||||||
|
drop table atacc3;
|
||||||
|
drop table atacc2;
|
||||||
|
drop table atacc1;
|
||||||
|
@ -254,3 +254,78 @@ ALTER TABLE FKTABLE ADD FOREIGN KEY(ftest2, ftest1)
|
|||||||
references pktable(ptest1, ptest2);
|
references pktable(ptest1, ptest2);
|
||||||
|
|
||||||
-- temp tables should go away by themselves, need not drop them.
|
-- temp tables should go away by themselves, need not drop them.
|
||||||
|
|
||||||
|
-- test check constraint adding
|
||||||
|
|
||||||
|
create table atacc1 ( test int );
|
||||||
|
-- add a check constraint
|
||||||
|
alter table atacc1 add constraint atacc_test1 check (test>3);
|
||||||
|
-- should fail
|
||||||
|
insert into atacc1 (test) values (2);
|
||||||
|
-- should succeed
|
||||||
|
insert into atacc1 (test) values (4);
|
||||||
|
drop table atacc1;
|
||||||
|
|
||||||
|
-- let's do one where the check fails when added
|
||||||
|
create table atacc1 ( test int );
|
||||||
|
-- insert a soon to be failing row
|
||||||
|
insert into atacc1 (test) values (2);
|
||||||
|
-- add a check constraint (fails)
|
||||||
|
alter table atacc1 add constraint atacc_test1 check (test>3);
|
||||||
|
insert into atacc1 (test) values (4);
|
||||||
|
drop table atacc1;
|
||||||
|
|
||||||
|
-- let's do one where the check fails because the column doesn't exist
|
||||||
|
create table atacc1 ( test int );
|
||||||
|
-- add a check constraint (fails)
|
||||||
|
alter table atacc1 add constraint atacc_test1 check (test1>3);
|
||||||
|
drop table atacc1;
|
||||||
|
|
||||||
|
-- something a little more complicated
|
||||||
|
create table atacc1 ( test int, test2 int, test3 int);
|
||||||
|
-- add a check constraint (fails)
|
||||||
|
alter table atacc1 add constraint atacc_test1 check (test+test2<test3*4);
|
||||||
|
-- should fail
|
||||||
|
insert into atacc1 (test,test2,test3) values (4,4,2);
|
||||||
|
-- should succeed
|
||||||
|
insert into atacc1 (test,test2,test3) values (4,4,5);
|
||||||
|
drop table atacc1;
|
||||||
|
|
||||||
|
-- lets do some naming tests
|
||||||
|
create table atacc1 (test int check (test>3), test2 int);
|
||||||
|
alter table atacc1 add check (test2>test);
|
||||||
|
-- should fail for $2
|
||||||
|
insert into atacc1 (test2, test) values (3, 4);
|
||||||
|
drop table atacc1;
|
||||||
|
|
||||||
|
-- inheritance related tests
|
||||||
|
create table atacc1 (test int);
|
||||||
|
create table atacc2 (test2 int);
|
||||||
|
create table atacc3 (test3 int) inherits (atacc1, atacc2);
|
||||||
|
alter table atacc2 add constraint foo check (test2>0);
|
||||||
|
-- fail and then succeed on atacc2
|
||||||
|
insert into atacc2 (test2) values (-3);
|
||||||
|
insert into atacc2 (test2) values (3);
|
||||||
|
-- fail and then succeed on atacc3
|
||||||
|
insert into atacc3 (test2) values (-3);
|
||||||
|
insert into atacc3 (test2) values (3);
|
||||||
|
drop table atacc3;
|
||||||
|
drop table atacc2;
|
||||||
|
drop table atacc1;
|
||||||
|
|
||||||
|
-- let's try only to add only to the parent
|
||||||
|
|
||||||
|
create table atacc1 (test int);
|
||||||
|
create table atacc2 (test2 int);
|
||||||
|
create table atacc3 (test3 int) inherits (atacc1, atacc2);
|
||||||
|
alter table only atacc2 add constraint foo check (test2>0);
|
||||||
|
-- fail and then succeed on atacc2
|
||||||
|
insert into atacc2 (test2) values (-3);
|
||||||
|
insert into atacc2 (test2) values (3);
|
||||||
|
-- both succeed on atacc3
|
||||||
|
insert into atacc3 (test2) values (-3);
|
||||||
|
insert into atacc3 (test2) values (3);
|
||||||
|
drop table atacc3;
|
||||||
|
drop table atacc2;
|
||||||
|
drop table atacc1;
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user