I'm trying to add a foreign key constraint on my schema devair from field user_id of table bluePrints to the PK id of table users but I get an error:
ERROR 1215: Cannot add foreign key constraint
Here are my table definitions:
users:
CREATE TABLE `users` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`name` varchar(255) COLLATE utf8_unicode_ci NOT NULL,
`email` varchar(255) COLLATE utf8_unicode_ci NOT NULL,
`password` varchar(60) COLLATE utf8_unicode_ci NOT NULL,
`remember_token` varchar(100) COLLATE utf8_unicode_ci DEFAULT NULL,
`created_at` timestamp NULL DEFAULT NULL,
`updated_at` timestamp NULL DEFAULT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `users_email_unique` (`email`)
) ENGINE=InnoDB AUTO_INCREMENT=19 DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci;
bluePrints:
CREATE TABLE `bluePrints` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`bluePrintName` varchar(255) COLLATE utf8_unicode_ci NOT NULL,
`description` varchar(255) COLLATE utf8_unicode_ci NOT NULL,
`user_id` int(10) NOT NULL,
`created_at` timestamp NULL DEFAULT NULL,
`updated_at` timestamp NULL DEFAULT NULL,
PRIMARY KEY (`id`),
KEY `uid` (`user_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci;
And the offending alter table statement:
ALTER TABLE `devair`.`bluePrints`
ADD CONSTRAINT `bp_u`
FOREIGN KEY (user_id)
REFERENCES `devair`.`users` (id)
ON DELETE CASCADE
ON UPDATE CASCADE;
The simple answer would be that you need to do this:
ALTER TABLE table1 ADD CONSTRAINT fk_bp_id FOREIGN KEY (columnFromTable1) REFERENCES table2(columnReferencedFromTable2);
The problem is the 'unsigned' in the bluePrints table. Once it's unsigned, then it works.
Now i have to figure out how to get laravel to use unsigned.
Related
I have this Database schema
exercise_quiz table
CREATE TABLE `exercise_quiz` (
`exercise_id` int(10) unsigned NOT NULL,
`quiz_id` int(10) unsigned NOT NULL,
`user_id` int(10) unsigned NOT NULL,
`answer` varchar(191) COLLATE utf8mb4_unicode_ci NOT NULL,
`created_at` timestamp NULL DEFAULT NULL,
`updated_at` timestamp NULL DEFAULT NULL,
PRIMARY KEY (`exercise_id`,`quiz_id`,`user_id`),
KEY `exercise_quiz_user_id_foreign` (`user_id`),
KEY `exercise_quiz_quiz_id_foreign` (`quiz_id`),
CONSTRAINT `exercise_quiz_exercise_id_foreign` FOREIGN KEY (`exercise_id`) REFERENCES `exercises` (`id`) ON DELETE CASCADE,
CONSTRAINT `exercise_quiz_quiz_id_foreign` FOREIGN KEY (`quiz_id`) REFERENCES `quizzes` (`id`) ON DELETE CASCADE,
CONSTRAINT `exercise_quiz_user_id_foreign` FOREIGN KEY (`user_id`) REFERENCES `users` (`id`) ON DELETE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;
exercises table
CREATE TABLE `exercises` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`title` varchar(191) COLLATE utf8mb4_unicode_ci DEFAULT NULL,
`body` text COLLATE utf8mb4_unicode_ci NOT NULL,
`created_at` timestamp NULL DEFAULT NULL,
`updated_at` timestamp NULL DEFAULT NULL,
`course_id` int(10) unsigned NOT NULL,
`score` int(11) DEFAULT NULL,
PRIMARY KEY (`id`),
KEY `exercises_course_id_foreign` (`course_id`),
CONSTRAINT `exercises_course_id_foreign` FOREIGN KEY (`course_id`) REFERENCES `courses` (`id`) ON DELETE CASCADE
) ENGINE=InnoDB AUTO_INCREMENT=145 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;
quizzes table
CREATE TABLE `quizzes` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`question` varchar(191) COLLATE utf8mb4_unicode_ci NOT NULL,
`created_at` timestamp NULL DEFAULT NULL,
`updated_at` timestamp NULL DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;
Example of data in exercise_quiz
How can I retrieve this, either with raw SQL or with Eloquent, in such a way as I’d have one single row for each exercise_id with one column with the average answer for each quiz_id ? something like
exercise_id --- avg_quiz_1 ---- avg_quiz_2 ---- avg_quiz_3 ...
I'm struggling around to create a foreign key with the following query:
alter table `users` add constraint `users_sales_partner_id_foreign` foreign key (`sales_partner_id`) references `structures` (`sales_partner_id`) on update cascade
InnoDB log says, it can't match this index:
2017-02-27 10:25:47 Error in foreign key constraint of
table website_backend/users: foreign key
(sales_partner_id) references structures (sales_partner_id) on update cascade:
Cannot find an index in the referenced table where the referenced
columns appear as the first columns, or column types in the table and
the referenced table do not match for constraint.
I have already checked typos and data type incompatibility, but everything seems to be alright:
CREATE TABLE `users` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`profile_id` int(10) unsigned NOT NULL,
`sales_partner_id` int(11) NOT NULL,
`email` varchar(191) COLLATE utf8mb4_unicode_ci NOT NULL,
`password` varchar(191) COLLATE utf8mb4_unicode_ci NOT NULL,
`state` enum('pending','confirmed','active','deactivated') COLLATE utf8mb4_unicode_ci NOT NULL,
`created_at` timestamp NULL DEFAULT NULL,
`updated_at` timestamp NULL DEFAULT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `users_profile_id_unique` (`profile_id`),
UNIQUE KEY `users_sales_partner_id_unique` (`sales_partner_id`),
UNIQUE KEY `users_email_unique` (`email`),
CONSTRAINT `users_profile_id_foreign` FOREIGN KEY (`profile_id`) REFERENCES `profiles` (`id`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci
CREATE TABLE `structures` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`sales_partner_id` int(11) NOT NULL,
`sales_partner_structure` int(11) DEFAULT NULL,
`active` tinyint(1) NOT NULL,
`blocked` tinyint(1) NOT NULL,
`created_at` timestamp NULL DEFAULT NULL,
`updated_at` timestamp NULL DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci
I can't get my problem, does somebody have a clue? Thanks in advance!
Thanks to Paul Spiegel for his reminding that I can only set FKs to the indexed fields. After another review I noticed that my referenced field was not indexed, that solved my problem.
I have created a database "webportal". and this is my "user" table script
DROP TABLE IF EXISTS `user`;
CREATE TABLE `user` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`username` varchar(255) DEFAULT NULL,
`password` varchar(255) DEFAULT NULL,
`firstName` varchar(255) DEFAULT NULL,
`lastName` varchar(255) DEFAULT NULL,
`dateRegistered` DATE DEFAULT NULL,
`skypeID` int(11) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=utf8;
and this one is "catalog" table script.
DROP TABLE IF EXISTS `catalog`;
create table catalog(
`id` int(11) NOT NULL AUTO_INCREMENT,
`user_id` int(11) NOT NULL,
`link` VARCHAR(100) NOT NULL,
`comment` VARCHAR(100) NOT NULL,
`inserDate` DATE DEFAULT NULL,
`content` longblob NOT NULL,
PRIMARY KEY (`id`),
CONSTRAINT `fk_catalog` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
and when I try to execute the second script in the command line, I get this error...
ERROR 1215 (HY000): Cannot add foreign key constraint.
What is wrong with this code?
It seems you are using a old version of MySQL, you can add a INDEX clause to foreign key field to fix the problem:
DROP TABLE IF EXISTS `catalog`;
create table `catalog`(
`id` int(11) NOT NULL AUTO_INCREMENT,
`user_id` int(11) NOT NULL,
`link` VARCHAR(100) NOT NULL,
`comment` VARCHAR(100) NOT NULL,
`inserDate` DATE DEFAULT NULL,
`content` longblob NOT NULL,
PRIMARY KEY (`id`),
INDEX (`user_id`),
CONSTRAINT `fk_catalog` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
I have two tables on distinct schemas
db1.invoice
CREATE TABLE IF NOT EXISTS db1.`invoice` (
`invoice_id` int(11) NOT NULL AUTO_INCREMENT,
`qsales_sale_id` int(11) DEFAULT NULL,
`invoice_id_from_dosage_id` int(11) NOT NULL,
`number` int(11) DEFAULT NULL,
`enterprise_name` varchar(100) DEFAULT NULL,
`subsidiary_name` varchar(100) DEFAULT NULL,
`subsidiary_address` varchar(200) DEFAULT NULL,
`subsidiary_phone` varchar(40) DEFAULT NULL,
`client_name` varchar(200) DEFAULT NULL,
`nit` bigint(20) DEFAULT NULL,
`was_paid` tinyint(1) DEFAULT NULL,
PRIMARY KEY (`invoice_id`),
KEY `fk_invoice_qsales_sale1_idx` (`qsales_sale_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=457 ;
bd2.qsale_sale
CREATE TABLE IF NOT EXISTS db2.qsales_sale (
`qsales_sale_id` int(11) NOT NULL AUTO_INCREMENT,
`qsales_order_type_id` int(11) NOT NULL,
`client_id` int(11) NOT NULL,
`total_cost` decimal(10,2) DEFAULT NULL,
`currency` varchar(45) DEFAULT NULL,
`created_at` datetime DEFAULT NULL,
`has_discount` tinyint(1) DEFAULT NULL,
`created_by` int(11) NOT NULL,
`is_wholesaler` tinyint(1) NOT NULL DEFAULT '0',
`payment_type` varchar(65) DEFAULT NULL,
PRIMARY KEY (`qsales_sale_id`),
KEY `fk_qsales_sale_qsales_order_type1_idx` (`qsales_order_type_id`),
KEY `fk_qsales_sale_client1_idx` (`client_id`),
KEY `fk_qsales_sale_employee1_idx` (`created_by`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=51 ;
then i want to add a foreign key
I try:
1.
alter table bd1.invoice
add foreign key fk_invoice_qsales_sale1(qsales_sale_id)
references db2.qsales_sale (qsales_sale_id)
on delete cascade
on update cascade;
ALTER TABLE db1.invoice
ADD CONSTRAINT fk_invoice_qsales_sale1 FOREIGN KEY (qsales_sale_id)
REFERENCES db2.qsales_sale (qsales_sale_id) ON DELETE NO ACTION ON UPDATE NO ACTION;
But i have this error:
Error Code: 1452. Cannot add or update a child row: a foreign key constraint fails (`qfix`.`#sql-a28_5`, CONSTRAINT `#sql-a28_5_ibfk_1` FOREIGN KEY (`qsales_sale_id`) REFERENCES `qsales`.`qsales_sale` (`qsales_sale_id`) ON DELETE CASCADE ON UPDATE CASCADE)
0.625 sec
Not sure what else to check/do. I made sure the foreign key data type matches (char(36)) and I ensured the foreign key statement uses the correct syntax
Running this script i get error 1215
USE addm;
CREATE TABLE `addm`.`notificationResource` (
`notificationId` CHAR(36) NOT NULL ,
`resourceId` CHAR(36) NOT NULL ,
PRIMARY KEY (`notificationId`, `resourceId`) ,
INDEX `fk_notificationResource_notification_idx` (`notificationId` ASC) ,
INDEX `fk_notificationResource_resource_idx` (`resourceId` ASC) ,
CONSTRAINT `fk_notificationResource_notification`
FOREIGN KEY (`notificationId` )
REFERENCES `addm`.`notification` (`id` )
ON DELETE NO ACTION
ON UPDATE NO ACTION,
CONSTRAINT `fk_notificationResource_resource`
FOREIGN KEY (`resourceId` )
REFERENCES `addm`.`resource` (`resourceId` )
ON DELETE NO ACTION
ON UPDATE NO ACTION);
commit;
Parent Tables:
CREATE TABLE `resource` (
`resourceId` char(36) NOT NULL,
`resourceName` varchar(255) DEFAULT NULL,
`resourceData` longblob,
PRIMARY KEY (`resourceId`),
UNIQUE KEY `resourceName_UNIQUE` (`resourceName`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8$$
CREATE TABLE `notification` (
`notificationType` varchar(5) CHARACTER SET latin1 NOT NULL,
`id` char(36) CHARACTER SET latin1 NOT NULL,
`aborted` bit(1) DEFAULT NULL,
`attempts` int(11) DEFAULT NULL,
`content` longblob,
`recordDate` datetime DEFAULT NULL,
`sent` bit(1) DEFAULT NULL,
`sentDate` datetime DEFAULT NULL,
`subject` varchar(255) CHARACTER SET latin1 DEFAULT NULL,
`fromUser_id` bigint(20) DEFAULT NULL,
`toUser_id` bigint(20) DEFAULT NULL,
`attachmentName` varchar(100) CHARACTER SET latin1 DEFAULT NULL,
`attachmentData` longblob,
`category` varchar(255) CHARACTER SET latin1 DEFAULT NULL,
`read` tinyint(1) DEFAULT '0',
`locked` tinyint(1) DEFAULT '0',
PRIMARY KEY (`id`),
KEY `FK2D45DD0B7F734EAD` (`toUser_id`),
KEY `FK2D45DD0BE62E629E` (`fromUser_id`),
CONSTRAINT `FK2D45DD0B7F734EAD` FOREIGN KEY (`toUser_id`) REFERENCES `user` (`id`),
CONSTRAINT `FK2D45DD0BE62E629E` FOREIGN KEY (`fromUser_id`) REFERENCES `user` (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8$$
I think column CHARACTER SET is different. id char(36) CHARACTER SET latin1 NOT NULL
change CHARACTER SET