join up to 3 tables in MySQL - mysql

I have tables are:
student{student_id as primery key,firstName, lastName};
teacher{teacher_id as primery key,firstName, lastName};
course{course_id as primery key,courseName, credits,teacher_id(forein key from teacher table)}
class{class_id as primery key,roomNumber,teacer_id forein_key from teacher,course_id forein key from course}
classStudent{student_id foreign key from student,class_id foreign key from class}
I want to retrive courseName, teacher first and last Name,roomNumber for specific student id.
my database:
CREATE TABLE `student` (
`student_id` int(10) NOT NULL,
`firstName` varchar(20) NOT NULL,
`lastName` varchar(20) NOT NULL,
`phone_number` int(8) NOT NULL,
`Email` varchar(40) NOT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE `teacher` (
`teacher_id` int(10) NOT NULL,
`firstName` varchar(20) NOT NULL,
`lastName` varchar(20) NOT NULL,
`phone_number` int(8) NOT NULL,
`Email` varchar(40) NOT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
CREATE TABLE `course` (
`course_id` varchar(10) NOT NULL,
`Course_Name` varchar(20) NOT NULL,
`Description` varchar(100) NOT NULL,
`credits` int(1) NOT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
ALTER TABLE `class`
ADD PRIMARY KEY (`class_id`),
ADD KEY `classTeacher` (`teacher_id`),
ADD KEY `classCourse` (`course_id`);
ALTER TABLE `classstudent`
ADD PRIMARY KEY (`class_id`,`student_id`),
ADD KEY `studentClass` (`student_id`);
-- Constraints for table `class`
--
ALTER TABLE `class`
ADD CONSTRAINT `classCourse` FOREIGN KEY (`course_id`) REFERENCES `course` (`course_id`) ON UPDATE CASCADE,
ADD CONSTRAINT `classTeacher` FOREIGN KEY (`teacher_id`) REFERENCES `teacher` (`teacher_id`);
--
-- Constraints for table `classstudent`
--
ALTER TABLE `classstudent`
ADD CONSTRAINT `classstudent_ibfk_1` FOREIGN KEY (`class_id`) REFERENCES `class` (`class_id`),
ADD CONSTRAINT `studentClass` FOREIGN KEY (`student_id`) REFERENCES `student` (`student_id`);
ALTER TABLE `classstudent`
ADD PRIMARY KEY (`class_id`,`student_id`),
ADD KEY `studentClass` (`student_id`);
I am also new to stack-overflow so please tell me if thare is any note about my question.

Select course.courseName, teacher.firstName, teacher.lastName, class.roomNumber
from student
inner join classStudent
on student.student_id=classStudent.student_id
inner join class
on classStudent.class_id = class.class_id
Inner join course
On class.course_id = course.course_id
Inner join teacher
On course.teacher_id = teacher.teacher_id
Where student.student_id = ?

Related

Foreign key constraint fails with Insert Into Select in MySQL

I'm quite new to SQL, and I'm trying to upload data to my tables. For this I have special tables where I upload the data from a CSV file, and then, from this table, I am trying to copy the data to the final table.
But now I have a problem with an intermediate table where I have uploaded my data. The table is:
CREATE TABLE `_work_has_person` (
`work_id` int(11) NOT NULL,
`person_id` int(11) NOT NULL,
`primary_contribution_id` int(11) DEFAULT NULL,
PRIMARY KEY (`work_id`,`person_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
I want to copy the data in
CREATE TABLE `work_has_person` (
`work_id` int(11) NOT NULL,
`person_id` int(11) NOT NULL,
`primary_contribution_id` int(11) NOT NULL,
PRIMARY KEY (`work_id`,`person_id`),
KEY `fk_work_has_person_person1_idx` (`person_id`),
KEY `fk_work_has_person_work1_idx` (`work_id`),
KEY `fk_work_has_person_primary_contribution1_idx` (`primary_contribution_id`),
CONSTRAINT `fk_work_has_person_person1` FOREIGN KEY (`person_id`) REFERENCES `person` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION,
CONSTRAINT `fk_work_has_person_primary_contribution1` FOREIGN KEY (`primary_contribution_id`) REFERENCES `primary_contribution` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION,
CONSTRAINT `fk_work_has_person_work1` FOREIGN KEY (`work_id`) REFERENCES `work` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
Which is an intermediate table between:
CREATE TABLE `work` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`title_work` varchar(250) DEFAULT NULL,
`subtitle_work` varchar(250) DEFAULT NULL,
`date_work` varchar(45) DEFAULT NULL,
`unix_date_work` varchar(100) DEFAULT NULL,
`sinopsis` text,
`ref_bne` varchar(100) DEFAULT NULL,
`ref_alt` longtext,
`language_id` int(11) NOT NULL,
PRIMARY KEY (`id`),
KEY `fk_work_language1_idx` (`language_id`),
KEY `title_work` (`title_work`),
CONSTRAINT `fk_work_language1` FOREIGN KEY (`language_id`) REFERENCES `language` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION
) ENGINE=InnoDB AUTO_INCREMENT=24610 DEFAULT CHARSET=utf8;
and
CREATE TABLE `person` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(100) NOT NULL,
`img_person` varchar(250) DEFAULT NULL,
`born_date` varchar(45) DEFAULT NULL,
`unix_born_date` varchar(100) DEFAULT NULL,
`city_born_date` varchar(100) DEFAULT NULL,
`country_born_date` varchar(100) DEFAULT NULL,
`death_date` varchar(45) DEFAULT NULL,
`unix_death_date` varchar(100) DEFAULT NULL,
`city_death_date` varchar(100) DEFAULT NULL,
`country_death_date` varchar(45) DEFAULT NULL,
`biography` longtext,
`ref_bne` varchar(100) DEFAULT NULL,
`ref_alt` longtext,
PRIMARY KEY (`id`),
UNIQUE KEY `name_UNIQUE` (`name`),
KEY `name` (`name`)
) ENGINE=InnoDB AUTO_INCREMENT=9159 DEFAULT CHARSET=utf8;
But everytime I try to run
INSERT INTO work_has_person (work_id, person_id, primary_contribution_id)
SELECT work_id, person_id, primary_contribution_id
FROM _work_has_person;
It says
Cannot add or update a child row: a foreign key constraint fails (`cdu93hfg93r`.
`work_has_person`, CONSTRAINT `fk_work_has_person_person1` FOREIGN KEY (`person_id`)
REFERENCES `person` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION)
I am pretty sure that the tables has the neccesary data, but, ¿is there a way to know which data fails? I have seen Mysql error 1452 - Cannot add or update a child row: a foreign key constraint fails: but don't understand exactly how to use it here.
A.
It is relatively easy to find out what data is causing the conflict: get all person_ids from _work_has_person that are not in the persons table. You can achieve this via an outer join and filtering for person.id is null in the where clause.
select * from `_work_has_person` whp
left join person p on whp.person_id=p.id
where p.id is null
You can actually remove such data from the results being inserted by including the reverse criterion into the select part of your insert query (an inner join):
INSERT INTO work_has_person (work_id, person_id, primary_contribution_id)
SELECT whp.work_id, whp.person_id, whp.primary_contribution_id
FROM _work_has_person whp
INNER join person p on whp.person_id=p.id

Cannot add foreign key constraint even with the same data type

| section | CREATE TABLE `section` (
`CourseNumber` varchar(10) NOT NULL,
`Quarter` varchar(10) NOT NULL,
`RoomNumber` varchar(4) DEFAULT NULL,
`DayTime` varchar(20) DEFAULT NULL,
PRIMARY KEY (`CourseNumber`,`Quarter`),
CONSTRAINT `section_ibfk_1` FOREIGN KEY (`CourseNumber`) REFERENCES `Course` (`CourseNumber`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 |
| enrollment | CREATE TABLE `enrollment` (
`SSN` varchar(9) DEFAULT NULL,
`CourseNumber` varchar(4) DEFAULT NULL,
`Quarter` varchar(10) DEFAULT NULL,
`Grade` varchar(1) DEFAULT NULL,
KEY `SSN` (`SSN`),
KEY `CourseNumber` (`CourseNumber`),
CONSTRAINT `enrollment_ibfk_1` FOREIGN KEY (`SSN`) REFERENCES `Student` (`SSN`),
CONSTRAINT `enrollment_ibfk_2` FOREIGN KEY (`CourseNumber`) REFERENCES `Course` (`CourseNumber`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 |
mysql> alter table enrollment add foreign key(Quarter) references section(Quarter);
ERROR 1215 (HY000): Cannot add foreign key constraint
Column Quarter in both table Enrollment and Section have the datatype VARCHAR(10),so I am not sure what is causing the error.
If tables have data which do not respect foreign key you can not create it.
Try
SET foreign_key_checks = 0;
alter table enrollment add foreign key(Quarter) references section(Quarter);
SET foreign_key_checks = 1;
But i have used this to delete tables, do not know what will happen in this case.
This is a two fold problem...
Column Quarter is not already indexed in the target table enrollment.
Column Quarter is also not indexed in the source table section, although it is a part of the composite PRIMARY KEY along with CourseNumber.
So, if you just want Quarter from section table to be referenced in enrollment table, you'd need to:
ALTER TABLE `section` ADD INDEX( `Quarter`);
ALTER TABLE `enrollment` ADD INDEX( `Quarter`);
And thereafter:
ALTER TABLE enrollment ADD FOREIGN KEY(`Quarter`) REFERENCES section(`Quarter`);
However, if you want (CourseNumber, Quarter) as a composite foreign key, you would need to create a combined index on the two fields in enrollment table:
ALTER TABLE `enrollment` ADD INDEX( `CourseNumber`, `Quarter`);
And follow it up with:
ALTER TABLE `enrollment` ADD FOREIGN KEY( `CourseNumber`, `Quarter` )
REFERENCES section( `CourseNumber`, `Quarter` );
Must be some data preventing the creation as others have said. This worked fine when I ran it:
CREATE TABLE `Course` (
`CourseNumber` varchar(10) NOT NULL,
PRIMARY KEY (`CourseNumber`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
CREATE TABLE `Student` (
`SSN` varchar(9) NOT NULL,
PRIMARY KEY (`SSN`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
CREATE TABLE `section` (
`CourseNumber` varchar(10) NOT NULL,
`Quarter` varchar(10) NOT NULL,
`RoomNumber` varchar(4) DEFAULT NULL,
`DayTime` varchar(20) DEFAULT NULL,
PRIMARY KEY (`CourseNumber`,`Quarter`),
CONSTRAINT `section_ibfk_1` FOREIGN KEY (`CourseNumber`) REFERENCES `Course` (`CourseNumber`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
CREATE TABLE `enrollment` (
`SSN` varchar(9) DEFAULT NULL,
`CourseNumber` varchar(4) DEFAULT NULL,
`Quarter` varchar(10) DEFAULT NULL,
`Grade` varchar(1) DEFAULT NULL,
KEY `SSN` (`SSN`),
KEY `CourseNumber` (`CourseNumber`),
CONSTRAINT `enrollment_ibfk_1` FOREIGN KEY (`SSN`) REFERENCES `Student` (`SSN`),
CONSTRAINT `enrollment_ibfk_2` FOREIGN KEY (`CourseNumber`) REFERENCES `Course` (`CourseNumber`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;

not able to apply foreign key constraint in mysql

I can run the below query and there are no nulls in the user_id column in the result -
select c.*,r.user_id from chat_group_users c left join roleuser r
on c.user_id = r.user_id;
But I cannot apply the foreign key constraint and mysql just says
Error Code: 1215. Cannot add foreign key constraint
The command i wrote -
ALTER TABLE chat_group_users
ADD CONSTRAINT fk_roleuser FOREIGN KEY (user_id) REFERENCES roleuser (user_id)
ON DELETE cascade ON UPDATE cascade;
The table structures -
CREATE TABLE `roleuser` (
`User_ID` int(10) unsigned NOT NULL AUTO_INCREMENT,
`UserNM` varchar(50) NOT NULL,
`UserPS` varchar(150) NOT NULL,
`r_username` varchar(50) DEFAULT NULL,
`UGroup` varchar(5) NOT NULL DEFAULT 'Usar',
`FirstName` varchar(45) NOT NULL,
`LastName` varchar(45) NOT NULL,
PRIMARY KEY (`User_ID`),
UNIQUE KEY `Index_2` (`UserNM`),
) ENGINE=InnoDB AUTO_INCREMENT=50 DEFAULT CHARSET=latin1;
CREATE TABLE `chat_group_users` (
`auto_id` int(11) NOT NULL AUTO_INCREMENT,
`group_id` int(11) DEFAULT NULL,
`user_id` int(10) DEFAULT NULL,
`is_admin` varchar(5) COLLATE utf8mb4_unicode_ci DEFAULT NULL,
PRIMARY KEY (`auto_id`),
UNIQUE KEY `unique_user_group` (`user_id`,`group_id`),
KEY `fc_group_id` (`group_id`),
CONSTRAINT `fc_group_id` FOREIGN KEY (`group_id`)
REFERENCES `chat_group`(`auto_id`)
ON DELETE CASCADE ON UPDATE CASCADE
)ENGINE=InnoDB AUTO_INCREMENT=21 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;
missed the unsigned on the chat_group_users -
`User_ID` int(10) unsigned NOT NULL AUTO_INCREMENT, ...

Lookup table in MySQL

I'm doing my first work in PHP/MySQL & I need help. I have one master table:
CREATE TABLE `m4l_movies` (
`ID` int(11) NOT NULL AUTO_INCREMENT,
`Title` varchar(250) NOT NULL,
`Rating` int(11) NOT NULL,
`Genre` varchar(250) NOT NULL,
`Actors` varchar(250) NOT NULL,
`UserID` int(11) NOT NULL DEFAULT '1',
PRIMARY KEY (`ID`)
) ENGINE=MyISAM AUTO_INCREMENT=115 DEFAULT CHARSET=utf8;
that receives input for a form which has values from a these lookup tables:
CREATE TABLE `m4l_actors` (
`ID` int(11) NOT NULL AUTO_INCREMENT,
`Actor` varchar(255) NOT NULL,
PRIMARY KEY (`ID`)
) ENGINE=InnoDB AUTO_INCREMENT=232 DEFAULT CHARSET=utf8;
CREATE TABLE `m4l_genre` (
`ID` int(11) NOT NULL AUTO_INCREMENT,
`Genre` varchar(255) NOT NULL,
PRIMARY KEY (`ID`)
) ENGINE=InnoDB AUTO_INCREMENT=202 DEFAULT CHARSET=utf8;
CREATE TABLE `m4l_movierating` (
`ID` int(11) NOT NULL AUTO_INCREMENT,
`Movie_Rating` varchar(250) NOT NULL,
PRIMARY KEY (`ID`)
) ENGINE=MyISAM AUTO_INCREMENT=12 DEFAULT CHARSET=utf8;
& I've created a View:
SELECT m4l_movies.ID AS ID,
m4l_movies.Title AS Title,
m4l_movierating.Movie_Rating AS Rating,
m4l_movies.Actors AS Actors,
m4l_movies.Genre AS Genre
FROM m4l_movies
JOIN m4l_movierating ON m4l_movierating.ID = m4l_movies.Rating
INNER JOIN m4l_genre ON m4l_movies.Genre = m4l_genre.ID
INNER JOIN m4l_actors ON m4l_movies.Actors = m4l_actors.ID
ORDER BY m4l_movies.Title
Here is the out put I get:
----------------------------------------------------------------|
ID Title Rating Actor Genre |
10 Summer G (10,15,25) (45,115,123) |
1 About You G-1 (63,163,405) (3,16,51) |
5 Dog Years P (45,65,95) (98,163,357) |
----------------------------------------------------------------|
Firstly this view should return more than 200 records. Secondly, I need to know how to either create a lookup or some other method to convert the NAME & GENRE back to their corresponding text values. Some how the RATING value is doing it right but I can't get NAME or GENRE to do it correctly. I'm sure it has to do with either the way I've joined the tables but I can't figure out where I'm going wrong. Will someone PLEASE help me.
Ok trying to follow along with suggesting made by Phil I've removed actors, genre from movies tale & created movies_genre & movies_actors
DROP TABLE IF EXISTS `m4l_movies`;
CREATE TABLE `m4l_movies` (
`ID` int(11) NOT NULL auto_increment,
`Title` varchar(250) NOT NULL,
`Year` float NOT NULL,
`Review` varchar(250) NOT NULL,
`Rating` int(11) NOT NULL,
`Image` varchar(250) NOT NULL,
`Storyline` longtext NOT NULL,
`Director` varchar(250) NOT NULL,
`UserID` int(11) NOT NULL default '1',
PRIMARY KEY (`ID`)
) ENGINE=MyISAM AUTO_INCREMENT=1 DEFAULT CHARSET=utf8;
CREATE TABLE `m4l_movie_actor` (
movie_id INT(11),
actor_id INT(11),
PRIMARY KEY (movie_id, actor_id),
FOREIGN KEY (movie_id) REFERENCES m4l_movies (ID),
FOREIGN KEY (actor_id) REFERENCES m4l_actors (ID)
);
CREATE TABLE `m4l_movie_genre` (
movie_id INT(11),
genre_id INT(11),
PRIMARY KEY (movie_id, genre_id),
FOREIGN KEY (movie_id) REFERENCES m4l_movies (ID),
FOREIGN KEY (genre_id) REFERENCES m4l_genre (ID)
);
DROP TABLE IF EXISTS m4l_genre;
CREATE TABLE m4l_genre (
ID int(11) NOT NULL auto_increment,
Genre varchar(250) NOT NULL,
PRIMARY KEY (ID)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8;
DROP TABLE IF EXISTS m4l_actors;
CREATE TABLE m4l_actors (
ID int(11) NOT NULL auto_increment,
Actor varchar(255) NOT NULL,
PRIMARY KEY (ID)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8;
but when I try to create the movie_actor OR movie_genre I get
09:29:45
CREATE TABLE `m4l_movie_actor` (movie_id INT(11), actor_id INT(11),
PRIMARY KEY (movie_id, actor_id),
FOREIGN KEY (movie_id) REFERENCES m4l_movies (ID),
FOREIGN KEY (actor_id) REFERENCES m4l_actors (ID) )
Error Code: 1215. Cannot add foreign key constraint
0.000 sec
09:40:56 CREATE TABLE m4l_movie_genre (movie_id INT(11),genre_id INT(11),
PRIMARY KEY (movie_id, genre_id),
FOREIGN KEY (movie_id) REFERENCES m4l_movies (ID),
FOREIGN KEY (genre_id) REFERENCES m4l_genre (ID) )
Error Code: 1215. Cannot add foreign key constraint
0.016 sec
From what I can gather this only occurs when you have data types mismatch, but I THINK I have all INT data types so why am I getting this error?
You appear to have made the classic blunder of storing relational data in an un-relatable way.
You should be using junction tables instead of comma separated values. For example...
CREATE TABLE `m4l_movies` (
`ID` int(11) NOT NULL AUTO_INCREMENT,
`Title` varchar(250) NOT NULL,
`Rating` int(11) NOT NULL,
-- removed Actors and Genre
`UserID` int(11) NOT NULL DEFAULT '1',
PRIMARY KEY (`ID`)
);
CREATE TABLE `m4l_movie_actor` (
movie_id INT(11) NOT NULL,
actor_id INT(11) NOT NULL,
PRIMARY KEY (movie_id, actor_id),
FOREIGN KEY (movie_id) REFERENCES m4l_movies (ID),
FOREIGN KEY (actor_id) REFERENCES m4l_actors (ID)
);
-- repeat for genres
You can then join on the junction table and on to the Actors / Genres tables, eg
SELECT ... m4l_actors.Actor ...
FROM m4l_movies
INNER JOIN m4l_movie_actor ON m4l_movies.ID = m4l_movie_actor.movie_id
INNER JOIN m4l_actors ON m4l_movie_actor.actor_id = m4l_actors.ID
If you want the result in a comma separated list, look into GROUP_CONCAT()

It is not letting me drop a foreign key

I am trying to remove a foreign key from a table but I am getting this error below in mysql:
1025 - Error on rename of './mobile_app/Question' to './mobile_app/#sql2-4517-15515' (errno: 152)
What does this error mean and how can it be fixed?
Below is the code where I am trying to drop the foreign key:
alter table Question drop foreign key FK_Option_Table;
Below is the Question Table details (no rows in this table):
CREATE TABLE `Question` (
`SessionId` varchar(10) NOT NULL DEFAULT '',
`QuestionId` int(5) NOT NULL,
`QuestionContent` varchar(5000) NOT NULL,
`NoofAnswers` int(2) NOT NULL,
`AnswerId` int(10) NOT NULL AUTO_INCREMENT,
`ReplyId` varchar(2) NOT NULL,
`QuestionMarks` int(4) NOT NULL,
`OptionId` varchar(3) NOT NULL,
PRIMARY KEY (`SessionId`,`QuestionId`),
KEY `FK_Option_Table` (`OptionId`),
KEY `FK_IndividualQuestion` (`QuestionId`),
KEY `FK_Reply` (`ReplyId`),
KEY `FK_AnswerId` (`AnswerId`)
) ENGINE=InnoDB AUTO_INCREMENT=76 DEFAULT CHARSET=utf8
Below is the Option_Table details:
CREATE TABLE `Option_Table` (
`OptionId` varchar(3) NOT NULL,
`OptionType` varchar(20) NOT NULL,
PRIMARY KEY (`OptionId`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8
There are 24 rows in this table and below is a sample:
OptionId OptionType
O1 A-C
O2 A-D
O3 A-E
O4 A-F
...
Those are index's not foreign keys you have. I see no foreign keys in your create statements.
Example to create foreign key.
ALTER TABLE `Question`
ADD CONSTRAINT `SessionId`
FOREIGN KEY (`SessionId` )
REFERENCES `Option_Table` (`OptionId` )
ON DELETE NO ACTION
ON UPDATE CASCADE
, ADD INDEX `test_idx` (`SessionId` ASC) ;
ALTER TABLE `Question` DROP FOREIGN KEY `SessionId` ;