ERROR: there is no unique constraint matching given keys for referenced table "mail_message" Odoo Postgres [duplicate] - postgresql

Trying to create this example table structure in Postgres 9.1:
CREATE TABLE foo (
name VARCHAR(256) PRIMARY KEY
);
CREATE TABLE bar (
pkey SERIAL PRIMARY KEY,
foo_fk VARCHAR(256) NOT NULL REFERENCES foo(name),
name VARCHAR(256) NOT NULL,
UNIQUE (foo_fk,name)
);
CREATE TABLE baz(
pkey SERIAL PRIMARY KEY,
bar_fk VARCHAR(256) NOT NULL REFERENCES bar(name),
name VARCHAR(256)
);
Running the above code produces an error, which does not make sense to me:
NOTICE: CREATE TABLE / PRIMARY KEY will create implicit index "foo_pkey" for table "foo"
NOTICE: CREATE TABLE will create implicit sequence "bar_pkey_seq" for serial column "bar.pkey"
NOTICE: CREATE TABLE / PRIMARY KEY will create implicit index "bar_pkey" for table "bar"
NOTICE: CREATE TABLE / UNIQUE will create implicit index "bar_foo_fk_name_key" for table "bar"
NOTICE: CREATE TABLE will create implicit sequence "baz_pkey_seq" for serial column "baz.pkey"
NOTICE: CREATE TABLE / PRIMARY KEY will create implicit index "baz_pkey" for table "baz"
ERROR: there is no unique constraint matching given keys for referenced table "bar"
********** Error **********
ERROR: there is no unique constraint matching given keys for referenced table "bar"
SQL state: 42830
Can anyone explain why this error arises?

It's because the name column on the bar table does not have the UNIQUE constraint.
So imagine you have 2 rows on the bar table that contain the name 'ams' and you insert a row on baz with 'ams' on bar_fk, which row on bar would it be referring since there are two rows matching?

In postgresql all foreign keys must reference a unique key in the parent table, so in your bar table you must have a unique (name) index.
See also http://www.postgresql.org/docs/9.1/static/ddl-constraints.html#DDL-CONSTRAINTS-FK and specifically:
Finally, we should mention that a foreign key must reference columns
that either are a primary key or form a unique constraint.
Emphasis mine.

You should have name column as a unique constraint. here is a 3 lines of code to change your issues
First find out the primary key constraints by typing this code
\d table_name
you are shown like this at bottom "some_constraint" PRIMARY KEY, btree (column)
Drop the constraint:
ALTER TABLE table_name DROP CONSTRAINT some_constraint
Add a new primary key column with existing one:
ALTER TABLE table_name ADD CONSTRAINT some_constraint PRIMARY KEY(COLUMN_NAME1,COLUMN_NAME2);
That's All.

when you do UNIQUE as a table level constraint as you have done then what your defining is a bit like a composite primary key see ddl constraints, here is an extract
This specifies that the combination of values in the indicated columns is unique across the whole table, though any one of the columns need not be (and ordinarily isn't) unique.
this means that either field could possibly have a non unique value provided the combination is unique and this does not match your foreign key constraint.
most likely you want the constraint to be at column level. so rather then define them as table level constraints, 'append' UNIQUE to the end of the column definition like name VARCHAR(60) NOT NULL UNIQUE or specify indivdual table level constraints for each field.

Related

PostgreSQL declarative partition - unique constraint on partitioned table must include all partitioning columns [duplicate]

This question already has an answer here:
ERROR: unique constraint on partitioned table must include all partitioning columns
(1 answer)
Closed last month.
I'm trying to create a partitioned table which refers to itself, creating a doubly-linked list.
CREATE TABLE test2 (
id serial NOT NULL,
category integer NOT NULL,
time timestamp(6) NOT NULL,
prev_event integer,
next_event integer
) PARTITION BY HASH (category);
Once I add primary key I get the following error.
alter table test2 add primary key (id);
ERROR: unique constraint on partitioned table must include all partitioning columns
DETAIL: PRIMARY KEY constraint on table "test2" lacks column "category" which is part of the partition key.
Why does the unique constrain require all partitioned columns to be included?
EDIT: Now I understand why this is needed: https://www.postgresql.org/docs/current/ddl-partitioning.html#DDL-PARTITIONING-DECLARATIVE-LIMITATIONS
Once I add PK with both columns it works.
alter table test2 add primary key (id, category);
But then adding the FK to itself doesn't work.
alter table test2 add foreign key (prev_event) references test2 (id) on update cascade on delete cascade;
ERROR: there is no unique constraint matching given keys for referenced table "test2"
Since PK is not just id but id-category I can't create FK pointing to id.
Is there any way to deal with this or am I missing something?
I would like to avoid using inheritance partitioning if possible.
EDIT2: It seems this is a known problem. https://www.reddit.com/r/PostgreSQL/comments/di5mbr/postgresql_12_foreign_keys_and_partitioned_tables/f3tsoop/
Seems that there is no straightforward solution. PostgreSQL simply doesn't support this as of v14. One solution is to use triggers to enforce 'foreign key' behavior. Other is to use multi-column foreign keys. Both are far from optimal.

there is no unique constraint matching given keys for referenced table "employees" [duplicate]

Trying to create this example table structure in Postgres 9.1:
CREATE TABLE foo (
name VARCHAR(256) PRIMARY KEY
);
CREATE TABLE bar (
pkey SERIAL PRIMARY KEY,
foo_fk VARCHAR(256) NOT NULL REFERENCES foo(name),
name VARCHAR(256) NOT NULL,
UNIQUE (foo_fk,name)
);
CREATE TABLE baz(
pkey SERIAL PRIMARY KEY,
bar_fk VARCHAR(256) NOT NULL REFERENCES bar(name),
name VARCHAR(256)
);
Running the above code produces an error, which does not make sense to me:
NOTICE: CREATE TABLE / PRIMARY KEY will create implicit index "foo_pkey" for table "foo"
NOTICE: CREATE TABLE will create implicit sequence "bar_pkey_seq" for serial column "bar.pkey"
NOTICE: CREATE TABLE / PRIMARY KEY will create implicit index "bar_pkey" for table "bar"
NOTICE: CREATE TABLE / UNIQUE will create implicit index "bar_foo_fk_name_key" for table "bar"
NOTICE: CREATE TABLE will create implicit sequence "baz_pkey_seq" for serial column "baz.pkey"
NOTICE: CREATE TABLE / PRIMARY KEY will create implicit index "baz_pkey" for table "baz"
ERROR: there is no unique constraint matching given keys for referenced table "bar"
********** Error **********
ERROR: there is no unique constraint matching given keys for referenced table "bar"
SQL state: 42830
Can anyone explain why this error arises?
It's because the name column on the bar table does not have the UNIQUE constraint.
So imagine you have 2 rows on the bar table that contain the name 'ams' and you insert a row on baz with 'ams' on bar_fk, which row on bar would it be referring since there are two rows matching?
In postgresql all foreign keys must reference a unique key in the parent table, so in your bar table you must have a unique (name) index.
See also http://www.postgresql.org/docs/9.1/static/ddl-constraints.html#DDL-CONSTRAINTS-FK and specifically:
Finally, we should mention that a foreign key must reference columns
that either are a primary key or form a unique constraint.
Emphasis mine.
You should have name column as a unique constraint. here is a 3 lines of code to change your issues
First find out the primary key constraints by typing this code
\d table_name
you are shown like this at bottom "some_constraint" PRIMARY KEY, btree (column)
Drop the constraint:
ALTER TABLE table_name DROP CONSTRAINT some_constraint
Add a new primary key column with existing one:
ALTER TABLE table_name ADD CONSTRAINT some_constraint PRIMARY KEY(COLUMN_NAME1,COLUMN_NAME2);
That's All.
when you do UNIQUE as a table level constraint as you have done then what your defining is a bit like a composite primary key see ddl constraints, here is an extract
This specifies that the combination of values in the indicated columns is unique across the whole table, though any one of the columns need not be (and ordinarily isn't) unique.
this means that either field could possibly have a non unique value provided the combination is unique and this does not match your foreign key constraint.
most likely you want the constraint to be at column level. so rather then define them as table level constraints, 'append' UNIQUE to the end of the column definition like name VARCHAR(60) NOT NULL UNIQUE or specify indivdual table level constraints for each field.

Alter the table by adding constraint and using index in postgresql getting an error syntax error at or near "("IDX_emp_PK

CREATE INDEX IDX_emp_PK ON
EMP(ID);
ALTER TABLE EMP ADD
CONSTRAINT PK_emp PRIMARY KEY (ID)
USING INDEX IDX_emp_PK;
There are two errors in your script:
First: you can't use a non-unique index for a primary key constraint, so you need
CREATE UNIQUE INDEX idx_emp_pk ON emp(id);
When you add a primary or unique constraint based on an index, you can't specify columns (as they are already defined in the index):
ALTER TABLE emp ADD
CONSTRAINT pk_emp PRIMARY KEY
USING INDEX idx_emp_pk;

PostgreSQL/PGAdmin4 ERROR: there is no unique constraint matching given keys for referenced table

PostgreSQL/PGAdmin4 ERROR: there is no unique constraint matching given keys for referenced table
This is the ‘schema’ I’m trying to code into PGAdmin4/Postgresql:
http://i.imgur.com/xPEu8Sh.jpg
I was able to convert all tables, except “QUALIFICATIONS”.
I tried to process the following query:
create table REGISTRATION(
StudentID int,
SectionNo int,
Semester varchar(16),
foreign key(StudentID) references Student(StudentID),
foreign key (SectionNo, Semester) references Section(SectionNo, Semester),
primary key(studentID, SectionNo, Semester)
);
I received the following message:
ERROR: there is no unique constraint matching given keys for referenced table "section"
These are the foreign and primary I have in the table SECTION
PKEY: i.imgur.com/BcUNKug.jpg
FKEY: i.imgur.com/D8B8hRW.jpg
Code of SECTION table:
CREATE TABLE class_scheduling_01.section
(
sectionno integer NOT NULL,
semester character varying(16) COLLATE pg_catalog."default" NOT NULL,
courseid character varying(16) COLLATE pg_catalog."default" NOT NULL,
CONSTRAINT section_pkey PRIMARY KEY (sectionno, semester, courseid),
CONSTRAINT section_sectionno_key UNIQUE (sectionno),
CONSTRAINT section_courseid_fkey FOREIGN KEY (courseid)
REFERENCES class_scheduling_01.course (courseid) MATCH SIMPLE
ON UPDATE NO ACTION
ON DELETE NO ACTION
)
I additionally ran the command: ALTER TABLE section ADD UNIQUE (sectionno);
Since none of the attributes seemed to be repeating itself.
Despite all this I’m getting:
ERROR: there is no unique constraint matching given keys for referenced table "section" Query returned successfully in 642 msec.
Edit: I've gone back to the COURSE table and made courseID a unique constraint. I still get the same message. SECTION table has a composite primary key made up of 3 columns. As seen in the first picture linked, out of all the values, only SECTION.sectionno is the only column with unique/non-repeating values.
2nd edit: I decided to create the table "REGISTRATION" one step at a time, and make the foreign keys last with alter table command.
I was able to make the columns StudentID andd SectionNo foreign keys to their respective columns. When I tried to make REGISTRATION.semester a foreign key to SECTION.semester I got the error message again.
alter table REGISTRATION add foreign key (semester) references section(semester);
As seen in the image I linked Semester value, is repeated; despite this, am I still required to make it unique? Or do I make a unique command assigning all 3 columns (of SECTION) together as unique, instead of just 1? If so, how?
This
foreign key (SectionNo, Semester) references Section(SectionNo, Semester),
requires that there be a unique constraint on the pair of columns SectionNo and Semester.
CREATE TABLE class_scheduling_01.section
(
sectionno integer NOT NULL,
semester character varying(16) COLLATE pg_catalog."default" NOT NULL,
courseid character varying(16) COLLATE pg_catalog."default" NOT NULL,
CONSTRAINT section_pkey PRIMARY KEY (sectionno, semester, courseid),
CONSTRAINT section_sectionno_key UNIQUE (sectionno),
CONSTRAINT section_courseid_fkey FOREIGN KEY (courseid)
REFERENCES class_scheduling_01.course (courseid) MATCH SIMPLE
ON UPDATE NO ACTION
ON DELETE NO ACTION,
-- Unique constraint on the pair
CONSTRAINT your_constraint_name UNIQUE (SectionNo, Semester)
);
That change should let these SQL statements succeed. I didn't check to see whether that's a good idea.
SQL is case insensitive.
I understand what you mean, but this is a bad way to think about it.
PostgreSQL folds unquoted identifiers to lowercase. So PostgreSQL would treat the identifiers SQL, Sql, and sql as if they were all sql. A quoted or delimited identifier, like "Select" always refers to either a table or a column; it's never interpreted as a keyword. Quoted identifiers are case-sensitive. You can't successfully refer to the table "Select" as select.

Postgres foreign keys / schema issue

If I create a new schema on the current database (management), why does it complain about cross-database references?
management=# create schema mgschema;
CREATE SCHEMA
management=# alter table clients add column task_id int null references mgschema.tasks.id;
ERROR: cross-database references are not implemented: "mgschema.tasks.id"
alter table clients add column task_id int null references mgschema.tasks.id;
The REFERENCES syntax in not correct, you should use:
REFERENCES reftable [ ( refcolumn ) ]
A simple references only expects a table name. The foreign key will then automatically point to the primary key of that table, e.g.
alter table clients add column task_id int null references mgschema.tasks;
Another alternative is to to specify the table and columns, but not with a single identifier:
alter table clients add column task_id int null references mgschema.tasks (id);
The second format is needed if the target table has multiple unique constraints.