外键约束的格式不正确,但外键列和引用键列相同
foreign key constraint is incorrectly formed, but both foreign and reference key column are identical
我正在做一个从 MySQL Workbench 到 MariaDB 数据库的“逆向工程”。当我执行逆向工程时,我在数据透视 table 上收到“外键约束形成不正确”的错误,即使参考键和外键都具有相同的属性和特性。
我有 3 个 tables,其中 2 个是独立的 tables,它们使用 pivot table 具有多对多关系。 table 是 users
table、certificates
table 和 users_has_certificates
枢轴 table。 users
和 certificates
tables 都使用具有相同类型的 id
,即 BIGINT(20), NOT NULL, UNSIGNED,
和 AUTO_INCREMENT
。但是,生成枢轴 table.
时出现约束错误形成错误
运行SHOW ENGINE INNODB STATUS
时,专门显示这个错误。
LATEST FOREIGN KEY ERROR
------------------------
2021-03-15 21:09:31 0x5a8 Error in foreign key constraint of table `database_this`.`if`:
FOREIGN KEY (`certificate_id`)
REFERENCES `database_this`.`certificates` (`id`)
ON DELETE NO ACTION
ON UPDATE NO ACTION)
ENGINE = InnoDB
DEFAULT CHARACTER SET = utf8mb4
COLLATE = utf8mb4_unicode_ci:
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.
Note that the internal storage type of ENUM and SET changed in
tables created with >= InnoDB-4.1.12, and such columns in old tables
cannot be referenced by such columns in new tables.
Please refer to https://mariadb.com/kb/en/library/foreign-keys/
for correct foreign key definition.
Create table `database_this`.`if` with foreign key constraint failed.
Field type or character set for column 'certificate_id' does not
mach referenced column 'id' near '
FOREIGN KEY (`certificate_id`)
REFERENCES `database_this`.`certificates` (`id`)
ON DELETE NO ACTION
ON UPDATE NO ACTION)
ENGINE = InnoDB
DEFAULT CHARACTER SET = utf8mb4
COLLATE = utf8mb4_unicode_ci'.
这是生成每个 table 的 SQL 代码。
users
table:
CREATE TABLE IF NOT EXISTS `database_this`.`users` (
`id` BIGINT(20) UNSIGNED NOT NULL AUTO_INCREMENT,
`name` VARCHAR(255) NOT NULL,
`email` VARCHAR(255) NOT NULL,
`password` VARCHAR(255) NOT NULL,
`created_at` TIMESTAMP NULL DEFAULT NULL,
`updated_at` TIMESTAMP NULL DEFAULT NULL,
PRIMARY KEY (`id`),
UNIQUE INDEX `users_name_unique` (`name` ASC),
UNIQUE INDEX `users_email_unique` (`email` ASC))
ENGINE = InnoDB
AUTO_INCREMENT = 2
DEFAULT CHARACTER SET = utf8mb4
COLLATE = utf8mb4_unicode_ci;
certificates
table:
CREATE TABLE IF NOT EXISTS `database_this`.`certificates` (
`id` BIGINT(20) UNSIGNED NOT NULL AUTO_INCREMENT,
`name` VARCHAR(255) NOT NULL,
`desc` TEXT NULL DEFAULT NULL,
`certifiable_type` VARCHAR(255) NOT NULL,
`certifiable_id` BIGINT(20) UNSIGNED NOT NULL,
`created_at` TIMESTAMP NULL DEFAULT CURRENT_TIMESTAMP(),
`updated_at` TIMESTAMP NULL DEFAULT CURRENT_TIMESTAMP(),
`deleted_at` TIMESTAMP NULL DEFAULT NULL,
PRIMARY KEY (`id`))
ENGINE = InnoDB
DEFAULT CHARACTER SET = utf8mb4;
users_has_certificates
table:
CREATE TABLE IF NOT EXISTS `database_this`.`users_has_certificates` (
`user_id` BIGINT(20) UNSIGNED NOT NULL,
`certificate_id` BIGINT(20) UNSIGNED NOT NULL,
`expired_date` DATE NULL,
INDEX `fk_users_has_certificates_certificates1_idx` (`certificate_id` ASC),
INDEX `fk_users_has_certificates_users1_idx` (`user_id` ASC),
CONSTRAINT `fk_users_has_certificates_users1`
FOREIGN KEY (`user_id`)
REFERENCES `database_this`.`users` (`id`)
ON DELETE NO ACTION
ON UPDATE NO ACTION,
CONSTRAINT `fk_users_has_certificates_certificates1`
FOREIGN KEY (`certificate_id`)
REFERENCES `database_this`.`certificates` (`id`)
ON DELETE NO ACTION
ON UPDATE NO ACTION)
ENGINE = InnoDB
DEFAULT CHARACTER SET = utf8mb4
COLLATE = utf8mb4_unicode_ci;
显然,MySQL Workbench 不喜欢在原始数据库中已经存在类似表的情况下对某些表进行逆向工程。解决方案是删除数据库中的所有表,使数据库为空,然后对该数据库执行逆向工程。我会将此标记为已解决。
我正在做一个从 MySQL Workbench 到 MariaDB 数据库的“逆向工程”。当我执行逆向工程时,我在数据透视 table 上收到“外键约束形成不正确”的错误,即使参考键和外键都具有相同的属性和特性。
我有 3 个 tables,其中 2 个是独立的 tables,它们使用 pivot table 具有多对多关系。 table 是 users
table、certificates
table 和 users_has_certificates
枢轴 table。 users
和 certificates
tables 都使用具有相同类型的 id
,即 BIGINT(20), NOT NULL, UNSIGNED,
和 AUTO_INCREMENT
。但是,生成枢轴 table.
运行SHOW ENGINE INNODB STATUS
时,专门显示这个错误。
LATEST FOREIGN KEY ERROR
------------------------
2021-03-15 21:09:31 0x5a8 Error in foreign key constraint of table `database_this`.`if`:
FOREIGN KEY (`certificate_id`)
REFERENCES `database_this`.`certificates` (`id`)
ON DELETE NO ACTION
ON UPDATE NO ACTION)
ENGINE = InnoDB
DEFAULT CHARACTER SET = utf8mb4
COLLATE = utf8mb4_unicode_ci:
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.
Note that the internal storage type of ENUM and SET changed in
tables created with >= InnoDB-4.1.12, and such columns in old tables
cannot be referenced by such columns in new tables.
Please refer to https://mariadb.com/kb/en/library/foreign-keys/
for correct foreign key definition.
Create table `database_this`.`if` with foreign key constraint failed.
Field type or character set for column 'certificate_id' does not
mach referenced column 'id' near '
FOREIGN KEY (`certificate_id`)
REFERENCES `database_this`.`certificates` (`id`)
ON DELETE NO ACTION
ON UPDATE NO ACTION)
ENGINE = InnoDB
DEFAULT CHARACTER SET = utf8mb4
COLLATE = utf8mb4_unicode_ci'.
这是生成每个 table 的 SQL 代码。
users
table:
CREATE TABLE IF NOT EXISTS `database_this`.`users` (
`id` BIGINT(20) UNSIGNED NOT NULL AUTO_INCREMENT,
`name` VARCHAR(255) NOT NULL,
`email` VARCHAR(255) NOT NULL,
`password` VARCHAR(255) NOT NULL,
`created_at` TIMESTAMP NULL DEFAULT NULL,
`updated_at` TIMESTAMP NULL DEFAULT NULL,
PRIMARY KEY (`id`),
UNIQUE INDEX `users_name_unique` (`name` ASC),
UNIQUE INDEX `users_email_unique` (`email` ASC))
ENGINE = InnoDB
AUTO_INCREMENT = 2
DEFAULT CHARACTER SET = utf8mb4
COLLATE = utf8mb4_unicode_ci;
certificates
table:
CREATE TABLE IF NOT EXISTS `database_this`.`certificates` (
`id` BIGINT(20) UNSIGNED NOT NULL AUTO_INCREMENT,
`name` VARCHAR(255) NOT NULL,
`desc` TEXT NULL DEFAULT NULL,
`certifiable_type` VARCHAR(255) NOT NULL,
`certifiable_id` BIGINT(20) UNSIGNED NOT NULL,
`created_at` TIMESTAMP NULL DEFAULT CURRENT_TIMESTAMP(),
`updated_at` TIMESTAMP NULL DEFAULT CURRENT_TIMESTAMP(),
`deleted_at` TIMESTAMP NULL DEFAULT NULL,
PRIMARY KEY (`id`))
ENGINE = InnoDB
DEFAULT CHARACTER SET = utf8mb4;
users_has_certificates
table:
CREATE TABLE IF NOT EXISTS `database_this`.`users_has_certificates` (
`user_id` BIGINT(20) UNSIGNED NOT NULL,
`certificate_id` BIGINT(20) UNSIGNED NOT NULL,
`expired_date` DATE NULL,
INDEX `fk_users_has_certificates_certificates1_idx` (`certificate_id` ASC),
INDEX `fk_users_has_certificates_users1_idx` (`user_id` ASC),
CONSTRAINT `fk_users_has_certificates_users1`
FOREIGN KEY (`user_id`)
REFERENCES `database_this`.`users` (`id`)
ON DELETE NO ACTION
ON UPDATE NO ACTION,
CONSTRAINT `fk_users_has_certificates_certificates1`
FOREIGN KEY (`certificate_id`)
REFERENCES `database_this`.`certificates` (`id`)
ON DELETE NO ACTION
ON UPDATE NO ACTION)
ENGINE = InnoDB
DEFAULT CHARACTER SET = utf8mb4
COLLATE = utf8mb4_unicode_ci;
显然,MySQL Workbench 不喜欢在原始数据库中已经存在类似表的情况下对某些表进行逆向工程。解决方案是删除数据库中的所有表,使数据库为空,然后对该数据库执行逆向工程。我会将此标记为已解决。