What is wrong with this Query ? PostgreSQL - postgresql

I want to create 3 tables and join them with foreign keys. Unfortunately, it doesn't work and I have no idea where is a mistake.
CREATE TABLE Students (
Student_Id SERIAL PRIMARY KEY,
Name VARCHAR (20) NOT NULL,
Surname VARCHAR (30) NOT NULL,
Date_of_Birth DATE NOT NULL,
Phone INT NOT NULL UNIQUE,
Email VARCHAR(225) NOT NULL UNIQUE,
Course_Id INT
FOREIGN KEY (Course_Id) REFERENCES Course (Course_Id)
);
CREATE TABLE Course (
Course_Id SERIAL PRIMARY KEY,
Student_Id INT NOT NULL,
Teacher_Id INT NOT NULL,
Category VARCHAR (30) NOT NULL,
FOREIGN KEY (Student_Id) REFERENCES Students (Student_Id)
);
CREATE TABLE Teachers (
Teacher_Id SERIAL PRIMARY KEY,
Name VARCHAR (20) NOT NULL,
Surname VARCHAR (30) NOT NULL,
Phone INT NOT NULL UNIQUE,
Salary INT NOT NULL,
Course_Id INT NOT NULL,
FOREIGN KEY (Teacher_Id) REFERENCES Course (Teacher_Id)
);
I should create a Foreign Key to join all three tables.
I get this error every time: relation "course" does not exist
I can't find where is the mistake. Please help.

It appears like you are attempting to crate a many-to-many (M:M) between Students and Teachers with Course as the resolution table. You are close, however, your definition sets up bi-directional relationships. This is normally not necessary. Define Students and Teachers without the FK to Course. Then define Course with a FK to each.
create table students (
student_id serial primary key
, name varchar (20) not null
, surname varchar (30) not null
, date_of_birth date not null
, phone int not null unique
, email varchar(225) not null unique
);
create table teachers (
teacher_id serial primary key
, name varchar (20) not null
, surname varchar (30) not null
, phone int not null unique
, salary int not null
);
create table course (
course_id serial primary key
, student_id int not null
, teacher_id int not null
, category varchar (30) not null
, foreign key (student_id) references students (student_id)
, foreign key (teacher_id) references teachers (teacher_id)
, unique (student_id, teacher_id)
);
If you must define bi-directional FK in Students and Teachers then create the tables without the FK then use alter table after Course is defined to add the FK and make them DEFERRABLE INITIALLY DEFERRED. Necessary for eventual Inserts.
alter table teachers add column course_id int references course(course_id) deferrable initially deferred;
alter table students add column course_id int references course(course_id) deferrable initially deferred;

Related

sql error - no unique constraint matching keys

for some reason i am getting there is no unique constraint matching given keys for referenced table "accident_location". I am using postgresql to create the table. what is the error here? as i have set the primary key of ID and address_ID on my accident_location table
CREATE TABLE IF NOT EXISTS Accident(
ID varchar(10) NOT NULL,
Severity INT,
Start_Time varchar(100) NOT NULL,
End_Time varchar(100) NOT NULL,
Description varchar(100),
PRIMARY KEY(ID)
);
CREATE TABLE IF NOT EXISTS Accident_Location(
ID varchar(10),
Address_ID INT,
Start_lat float,
Start_Lng float,
End_Lat float,
End_Lng float,
"Distance(mi)" float,
PRIMARY KEY (ID,Address_ID),
FOREIGN KEY (ID) REFERENCES Accident(ID)
);
CREATE TABLE IF NOT EXISTS Address(
Address_ID INT,
Number INT,
Street varchar(100),
Side varchar(5) ,
City varchar(50) NOT NULL,
County varchar(50) ,
State varchar(10) NOT NULL,
Zipcode varchar(15) NOT NULL,
Country varchar(5) ,
Timezone varchar(30) ,
Airport_code varchar(10),
Location_ID INT NOT NULL,
Weather_ID INT NOT NULL,
PRIMARY KEY (Address_ID),
FOREIGN KEY (Address_ID) REFERENCES Accident_Location(Address_ID)
);
The referenced Address_ID on the Address table should be unique on table Accident_Location.
Change Accident_Location table to
CREATE TABLE IF NOT EXISTS Accident_Location(
ID varchar(10),
Address_ID INT constraint unx_addres_id_location unique,
Start_lat float,
Start_Lng float,
End_Lat float,
End_Lng float,
"Distance(mi)" float,
PRIMARY KEY (ID,Address_ID),
FOREIGN KEY (ID) REFERENCES Accident(ID)
);
Here, I've added a unique constraint on Address_ID
Address_ID INT constraint unx_addres_id_location unique
UPDATED
Since you are referring to Address_ID of Accident_Location table as a foreign key on the Address table, this will force you to make it a unique record. That means any two rows or more should not have the same value of Address_ID. Otherwise, the foreign key Address_ID on the Address table wouldn't know which row you are referring to.
The reason you are not seeing this same error for the Accident table is that by default primary keys are unique.

Query using analytic functions in postgresql

I have the following tables in postgresql and I would like to make a query using analytical functions to obtain the following results: The name of the athlete, the discipline and the country, A column indicating the best time of the discipline. (REGISTER_MEASURE), A column containing the average time by country and discipline, A column containing the number of participations by country and discipline, A column containing the cumulative of the previous column (we will see at the end the number of participants in the discipline), The information must be sorted by discipline, country and athlete. All in a single output.
CREATE TABLE olympic.tb_discipline (
discipline_id INT NOT NULL,
name CHARACTER VARYING(50) NOT NULL,
inventor CHARACTER VARYING(50) NOT NULL,
type CHARACTER VARYING(10) NOT NULL,
object_type CHARACTER VARYING(20) DEFAULT NULL,
CONSTRAINT ck_discipline_type CHECK (type IN ('RUN', 'JUMP', 'THROW')),
CONSTRAINT pk_discipline PRIMARY KEY (discipline_id)
);
CREATE TABLE olympic.tb_athlete (
athlete_id CHARACTER(7) NOT NULL,
name CHARACTER VARYING(50) NOT NULL,
country CHARACTER VARYING(3) NOT NULL,
substitute_id CHARACTER(7) DEFAULT NULL,
CONSTRAINT pk_athlete PRIMARY KEY (athlete_id),
CONSTRAINT fk_athlete_substitute FOREIGN KEY (substitute_id) REFERENCES olympic.tb_athlete (athlete_id)
);
CREATE TABLE olympic.tb_play (
athlete_id CHARACTER(7) NOT NULL,
discipline_id INT NOT NULL,
CONSTRAINT pk_play PRIMARY KEY (athlete_id, discipline_id),
CONSTRAINT fk_play_athlete FOREIGN KEY (athlete_id) REFERENCES olympic.tb_athlete (athlete_id),
CONSTRAINT fk_play_discipline FOREIGN KEY (discipline_id) REFERENCES olympic.tb_discipline (discipline_id)
);
CREATE TABLE olympic.tb_round (
round_number INT NOT NULL,
discipline_id INT NOT NULL,
CONSTRAINT pk_round PRIMARY KEY (discipline_id, round_number),
CONSTRAINT fk_round_discipline FOREIGN KEY (discipline_id) REFERENCES olympic.tb_discipline (discipline_id)
);
CREATE TABLE olympic.tb_register (
athlete_id CHARACTER(7) NOT NULL,
round_number INT NOT NULL,
discipline_id INT NOT NULL,
register_date DATE NOT NULL DEFAULT CURRENT_DATE,
register_position INT DEFAULT NULL,
register_time TIME DEFAULT NULL,
register_measure REAL DEFAULT NULL,
CONSTRAINT pk_register PRIMARY KEY (athlete_id, round_number, discipline_id),
CONSTRAINT fk_register_athlete FOREIGN KEY (athlete_id) REFERENCES olympic.tb_athlete (athlete_id),
CONSTRAINT fk_register_round FOREIGN KEY (discipline_id, round_number) REFERENCES olympic.tb_round (discipline_id, round_number)
);
I have tried to implement the query similar to the following but I am not getting satisfactory results.
SELECT tb_athlete.name, tb_discipline.name
, tb_athlete.country
, MAX(tb_register.register_measure) OVER (PARTITION BY tb_discipline.name)
, AVG(tb_register.register_time) OVER (PARTITION BY tb_discipline.name)
FROM olympic.tb_athlete
JOIN olympic.tb_register USING (athlete_id)
JOIN olympic.tb_discipline USING (discipline_id);
Image sample
Could you help me with a solution. Thank you!

TypeORM: many to many: Get all teams from userID

I have two table: User and Team.
They are in a many-to-many relation.
I would like to get all teams of a specific user.
Seams really simple but I can't find the answer anywhere..
Do you know how can I do ?
On the many-to-many relation must be 3rd table. This table contained user_id and team_id connections.
For example:
CREATE TABLE user (
id serial4 NOT NULL,
first_name varchar(200) NOT NULL,
last_name varchar(200) NULL,
CONSTRAINT user_pk PRIMARY KEY (id)
);
CREATE TABLE team (
id serial4 NOT NULL,
team_name varchar NOT NULL,
team_about text NULL,
CONSTRAINT team_pk PRIMARY KEY (id)
);
CREATE TABLE user_team (
id serial4 NOT NULL,
user_id int4 NOT NULL,
team_id int4 NOT NULL,
CONSTRAINT user_team_pk PRIMARY KEY (id)
);
-- filter and select team by user_id
select t.* from examples.team t
inner join examples.user_team usrt on usrt.team_id = t.id
where usrt.user_id = 2;

Error Code: 1822. Failed to add the foreign key constraint. Missing index for constraint 'questions_ibfk_1' in the referenced table 'category'

cannot add foreign key constraint to table
create table users
(
user_id int auto_increment primary key not null,
username varchar(50) unique null ,
email varchar(50) unique ,
passwords varchar(50) not null,
login_status boolean not null
);
create table category (
category_id int primary key not null,
category_name varchar(50) not null
);
create table answers (
id_answer int auto_increment primary key not null,
answer boolean not null
);
create table questions (
question_id int primary key not null,
category_name varchar(50) not null,
content varchar(50) not null ,
foreign key (category_name) references category (category_name)
);
You get this error because there's no index on category_name in the category table. Change that CREATE statement as follows:
create table category (
category_id int primary key not null,
category_name varchar(50) not null,
KEY category_name_index (category_name)
);
From the docs (8.0 version, but the statement is true for older versions):
MySQL requires indexes on foreign keys and referenced keys so that foreign key checks can be fast and not require a table scan. In the referencing table, there must be an index where the foreign key columns are listed as the first columns in the same order. Such an index is created on the referencing table automatically if it does not exist. This index might be silently dropped later, if you create another index that can be used to enforce the foreign key constraint. index_name, if given, is used as described previously.
Also, you're using a varchar(50) as your foreign key, which is not usually a great idea for a variety of reasons. You probably want to use a numeric value, such as category_id, instead.

'there is no unique constraint matching given keys for referenced table' where i dont want something to be unique

In Postgres I have written the following code:
CREATE TABLE students (
student_id BIGINT PRIMARY KEY,
first_name VARCHAR(15),
surname VARCHAR(35),
enrollment_year INT);
CREATE TABLE teachers (
bsn BIGINT PRIMARY KEY,
first_name VARCHAR(15),
surname VARCHAR(35),
salary REAL,
scale INT,
CONSTRAINT salary CHECK(salary < (25 * scale) AND salary > (20 * scale))
);
CREATE TABLE course (
course_code VARCHAR(10) PRIMARY KEY,
course_name VARCHAR(20) UNIQUE,
study_points INT);
CREATE TABLE study_program (
course_name VARCHAR(20) PRIMARY KEY,
level VARCHAR(15),
duration VARCHAR(10),
FOREIGN KEY(course_name) REFERENCES course(course_name));
CREATE TABLE assignment (
assignment_code VARCHAR(10) UNIQUE,
course_name VARCHAR(20),
PRIMARY KEY(assignment_code, course_name),
FOREIGN KEY(course_name) REFERENCES course(course_name)
);
CREATE TABLE records (
student_id BIGINT,
course_name VARCHAR(20),
PRIMARY KEY(student_id, course_name),
FOREIGN KEY(student_id) REFERENCES students(student_id),
FOREIGN KEY(course_name) REFERENCES course(course_name));
CREATE TABLE make (
student_id BIGINT,
assignment_code VARCHAR(20),
PRIMARY KEY(student_id, assignment_code),
FOREIGN KEY(student_id) REFERENCES students(student_id),
FOREIGN KEY(assignment_code) REFERENCES assignment(assignment_code));
CREATE TABLE prerequisit (
assignment_code VARCHAR(20),
course_name VARCHAR(20),
PRIMARY KEY(assignment_code, course_name),
FOREIGN KEY(assignment_code) REFERENCES assignment(assignment_code),
FOREIGN KEY(course_name) REFERENCES course(course_name)
);
CREATE TABLE records_2 (
assignment_code VARCHAR(20),
course_name VARCHAR(20),
bsn BIGINT,
mandatory BOOLEAN,
year INT,
week INT,
PRIMARY KEY(assignment_code, course_name),
FOREIGN KEY(assignment_code) REFERENCES assignment(assignment_code),
FOREIGN KEY(course_name) REFERENCES course(course_name)
);
CREATE TABLE designes (
course_code VARCHAR(15),
bsn BIGINT,
study_points INT,
course_name VARCHAR(20),
PRIMARY KEY(course_code, bsn),
FOREIGN KEY(course_code) REFERENCES course(course_code),
FOREIGN KEY(bsn) REFERENCES teachers(bsn),
FOREIGN KEY(study_points) REFERENCES course(study_points),
FOREIGN KEY(course_name) REFERENCES course(course_name)
);
CREATE TABLE reviews (
bsn BIGINT PRIMARY KEY,
course_code VARCHAR(15),
study_points INT,
course_name VARCHAR(20),
FOREIGN KEY(bsn) REFERENCES teachers(bsn),
FOREIGN KEY(course_code) REFERENCES course(course_code),
FOREIGN KEY(study_points) REFERENCES course(study_points),
FOREIGN KEY(course_name) REFERENCES course(course_name)
);
The error I get is
ERROR: there is no unique constraint matching given keys for referenced table "course"
This error is fixed by adding the UNIQUE constraint to study points, however I do not want study points to be unique because I need different courses to have the same amount of study points.
Referencing study_points makes no sense whatsoever. In fact referencing three different columns of a single table makes no sense whatsoever.
You only need FOREIGN KEY(course_code) REFERENCES course(course_code) and you don't need the columns course_name and study_points in the reviews table as they are implicitly defined through the foreign key to the course table.
Which means the table should look something like this:
CREATE TABLE reviews
(
bsn BIGINT PRIMARY KEY,
course_code VARCHAR(15),
FOREIGN KEY(bsn) REFERENCES teachers(bsn),
FOREIGN KEY(course_code) REFERENCES course(course_code)
);
Which then begs the question: what is that table supposed to do? You can only have a single row per teacher in there because bsn is the primary key (thus can't be repeated). So that is a one-to-one (or one-to-zero/one) relationship. Which in turn means you could move the column course_code to the teachers table, e.g. as reviewed_course.
However, I guess you meant to create a many-to-many relationship between teachers and course which then should be something like this:
CREATE TABLE reviews
(
bsn BIGINT,
course_code VARCHAR(15),
primary key (bsn, course_code),
FOREIGN KEY(bsn) REFERENCES teachers(bsn),
FOREIGN KEY(course_code) REFERENCES course(course_code)
);
That makes the combination of bsn and course_code unique. Which means each teacher can review each course exactly once, but a teacher can review multiple courses and a single course can be reviewed by multiple teachers.