Weak Entity postgresql - postgresql

I want to create a table with primary key email,nro being nro a sequential number for each email ex:
user1#e.com, 1
user1#e.com, 2
user2#e.com, 1
create table proposta_de_correcao(
email varchar(255) not null,
nro serial not null,
unique(nro,email),
PRIMARY KEY(nro, email),
FOREIGN KEY (email) REFERENCES Utilizador(email),
);
But I get the following error:
ERROR: there is no unique constraint matching given keys for referenced table "proposta_de_correcao"
I have already tried:
unique(nro,email)
contraint keys unique(nro,email)

Two things here, to help with your problem:
Why nro is serial if is not a sequential field in your database? serial type is used when you want that the field be incremented automatically (as in single integer primary keys). Maybe is better that you put an int type here.
You have in your table no unique constraints. If you create a fiddle, you can see that code runs fine:
CREATE TABLE proposta_de_correcao(
email VARCHAR(255) not null,
nro SERIAL not null,
UNIQUE(nro, email),
PRIMARY KEY(nro, email)
-- FOREIGN KEY (email) REFERENCES Utilizador(email)
);
INSERT INTO proposta_de_correcao VALUES ('user1#e.com', 1);
INSERT INTO proposta_de_correcao VALUES ('user1#e.com', 2);
INSERT INTO proposta_de_correcao VALUES ('user2#e.com', 1);
So, I can conclude that when you want to add the constraint, your database already have duplicated data in those two columns. Try to create in a test database the data mentioned above and you will see that runs perfectly.
I just removed the foreign key constraint to allow to run the code as we don't have the referenced table in example and we can consider that the referenced table don't have influence on the problem cited on answer.
Here's the fiddle.

Related

Citus: How can I add self referencing table in distributed tables list

I'm trying to run create_distributed_table for tables which i need to shard and almost all of the tables have self relation ( parent child )
but when I run SELECT create_distributed_table('table-name','id');
it throws error cannot create foreign key constraint
simple steps to reproduce
CREATE TABLE TEST (
ID TEXT NOT NULL,
NAME CHARACTER VARYING(255) NOT NULL,
PARENT_ID TEXT
);
ALTER TABLE TEST ADD CONSTRAINT TEST_PK PRIMARY KEY (ID);
ALTER TABLE TEST ADD CONSTRAINT TEST_PARENT_FK FOREIGN KEY (PARENT_ID) REFERENCES TEST (ID);
ERROR
citus=> SELECT create_distributed_table('test','id');
ERROR: cannot create foreign key constraint
DETAIL: Foreign keys are supported in two cases, either in between two colocated tables including partition column in the same ordinal in the both tables or from distributed to reference tables
For the time being, it is not possible to shard a table on PostgreSQL without dropping the self referencing foreign key constraints, or altering them to include a separate and new distribution column.
Citus places records into shards based on the hash values of the distribution column values. It is most likely the case that the hashes of parent and child id values are different and hence the records should be stored in different shards, and possibly on different worker nodes. PostgreSQL does not have a mechanism to create foreign key constraints that reference records on different PostgreSQL clusters.
Consider adding a new column tenant_id and adding this column to the primary key and foreign key constraints.
CREATE TABLE TEST (
tenant_id INT NOT NULL,
id TEXT NOT NULL,
name CHARACTER VARYING(255) NOT NULL,
parent_id TEXT NOT NULL,
FOREIGN KEY (tenant_id, parent_id) REFERENCES test(tenant_id, id),
PRIMARY KEY (tenant_id, id)
);
SELECT create_distributed_table('test','tenant_id');
Note that parent and child should always be in the same tenant for this to work.

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.

How do I create a check to make sure a value exists in another table?

Right now I have two tables, one that contains a compound primary key and another that that references one of the values of the primary key but is a one-to-many relationship between Product and Mapping. The following is an idea of the setup:
CREATE TABLE dev."Product"
(
"Id" serial NOT NULL,
"ShortCode" character(6),
CONSTRAINT "ProductPK" PRIMARY KEY ("Id")
)
CREATE TABLE dev."Mapping"
(
"LookupId" integer NOT NULL,
"ShortCode" character(6) NOT NULL,
CONSTRAINT "MappingPK" PRIMARY KEY ("LookupId", "ShortCode")
)
Since the ShortCode is displayed to the user as a six character string I don't want to have a another table to have a proper foreign key reference but trying to create one with the current design is not allowed by PostgreSQL. As such, how can I create a check so that the short code in the Mapping table is checked to make sure it exists?
Depending on the fine print of your requirements and your version of Postgres I would suggest a TRIGGER or a NOT VALID CHECK constraint.
We have just discussed the matter in depth in this related question on dba.SE:
Disable all constraints and table checks while restoring a dump
If I understand you correctly, you need a UNIQUE constraint on "Product"."ShortCode". Surely it should be declared NOT NULL, too.
CREATE TABLE dev."Product"
(
"Id" serial NOT NULL,
"ShortCode" character(6) NOT NULL UNIQUE,
CONSTRAINT "ProductPK" PRIMARY KEY ("Id")
);
CREATE TABLE dev."Mapping"
(
"LookupId" integer NOT NULL,
"ShortCode" character(6) NOT NULL REFERENCES dev."Product" ("ShortCode"),
CONSTRAINT "MappingPK" PRIMARY KEY ("LookupId", "ShortCode")
);
Your original "Product" table will allow this INSERT statement to succeed, but it shouldn't.
insert into dev."Product" ("ShortCode") values
(NULL), (NULL), ('ABC'), ('ABC'), ('ABC');
Data like that is just about useless.
select * from dev."Product"
id ShortCode
--
1
2
3 ABC
4 ABC
5 ABC

Unique Field - no unique constraint matching given keys

I have three tables in a postgresql database, namely tec_configurations, tep_cores and tep2tec_bindings. The table tec2tep_bindings references to the primary key fields of the first two tables. The related create statements per table are listed in below sql snippets 2,3 and 4. I get the error indicated in the 1st snippet below. Could you please tell me how I can fix this error? The 'id' field in table TEC_CONFIGURATIONS is already unique since it is a primary key. So, I don't see a reason to get this error message.
SNIPPET 1 (Error message):
ERROR: there is no unique constraint matching given keys for referenced table
"tec_configurations"
SNIPPET 2 (TABLE tec_configurations):
CREATE TABLE IF NOT EXISTS TEC_CONFIGURATIONS (
ID SERIAL PRIMARY KEY,
TEC_ID INT NOT NULL,
HANDLER_MAC TEXT NOT NULL,
PRIMARY_MAC TEXT,
SECONDARY_MAC TEXT,
TERTIARY_MAC TEXT,
EXPECTED_FLOWS INT DEFAULT 0,
VERSION INT DEFAULT 0,
UUID TEXT DEFAULT NULL );
SNIPPET 3 (TABLE tep_cores):
CREATE TABLE IF NOT EXISTS TEP_CORES (
ID SERIAL PRIMARY KEY,
MAC TEXT,
UUID TEXT,
CORE_NO INT DEFAULT 0);
SNIPPET 4 (TABLE tec2tep_bindings)
CREATE TABLE IF NOT EXISTS TEC2TEP_BINDINGS (
ID SERIAL PRIMARY KEY,
TEC_ID_FK INT NOT NULL REFERENCES TEC_CONFIGURATIONS(ID),
TEP_CORE_ID_FK INT NOT NULL REFERENCES TEP_CORES(ID),
REPLICA_RANK INT DEFAULT 0);
Wild guess, since you're issuing create table if not exists rather than create table: one of the tables exists without the needed unique key (e.g. from lack of a primary key).
(If correct, I'd add this note. Some Postgres core devs were hostile to the idea of adding if exists and if not exists constructs, objecting thus: "What is supposed to happen when you create table if not exists, silently "succeed", and the existing table has a schema different from the one you were hoping for?")

postgresql unique constraint not unique enough

I am creating tables to handle the security question/selected question/given answer section of our database and getting this error:
there is no unique constraint matching given keys for referenced table "m_security_questions"
Not sure how I fix this?
(Since schema won't build b/c of error, I couldn't add SQL Fiddle)
CREATE TABLE security_question --defines questions
(
id SERIAL PRIMARY KEY NOT NULL,
question character varying(1024) NOT NULL,
is_custom boolean DEFAULT FALSE NOT NULL
);
INSERT INTO security_question
(question,is_custom)
VALUES
('do you know the answer?',FALSE),
('Write your own question',TRUE);
CREATE TABLE m_security_questions
( --defines question a member chooses & allows free form question
-- id SERIAL NOT NULL,
-- I know adding id like this and making keeping same pk solves it
-- but isn't storing the extra sequence not needed?
member integer --REFERENCES member(m_no)
-- commented out reference for so only
NOT NULL,
question integer REFERENCES security_question(id) NOT NULL,
m_note text,
PRIMARY KEY(member,question)
);
-- here I add unique constraint but doesn't the primary already mean I have a unique index?
ALTER TABLE m_security_questions ADD CONSTRAINT m_security_questions_unique_member_question UNIQUE (member,question);
INSERT INTO m_security_questions
(member,question,m_note)
VALUES
(2,1,NULL),
(2,2,'How many marbles in this jar?');
CREATE TABLE m_security_answer --defines members given answer
( -- I want member & question here to line up w/ same from m_security_questions
member integer REFERENCES m_security_questions(member),
question integer REFERENCES m_security_questions(question) NOT NULL,
answer character varying(255) NOT NULL,
PRIMARY KEY (member,question)
);
-- here is where I get the error:
-- there is no unique constraint matching given keys for referenced table "m_security_questions"
INSERT INTO m_security_answer
(member,question,answer)
VALUES
(2,1,'yes'),
(2,2,'431');
The primary key definitely defines a unique constraint. But the unique constraint is on (member,question). Your have two FOREIGN KEY constraints that references just (member) and (question) separately.
I'm pretty sure what you want is:
CREATE TABLE m_security_answer --defines members given answer
(
member integer,
question integer NOT NULL,
answer character varying(255) NOT NULL,
PRIMARY KEY (member,question),
FOREIGN KEY (member, question) REFERENCES m_security_questions(member, question)
);