Mysql 外部复合键中的复合键

Mysql composite key out of a foreign composite key

我正在尝试在 Mysql WorkBench 中的两个表之间建立多对多关系,并且这两个表中的一个具有复合主键(部分来自 2外键)。当我尝试生成 SQL 时出现此错误:

ERROR: Error 1215: Cannot add foreign key constraint

SQL代码:

    -- -----------------------------------------------------
    -- Table `A_D_schema`.`Resources_has_OwnerGroups`
    -- -----------------------------------------------------
    CREATE TABLE IF NOT EXISTS `A_D_schema`.`Resources_has_OwnerGroups` (
      `Resources_id` INT NOT NULL,
      `OwnerGroups_id` INT NOT NULL,
      `OwnerGroups_Instances_has_Customers_Instances_idInstances` INT NOT NULL,
      `OwnerGroups_Instances_has_Customers_Customers_idCustomers` INT NOT NULL,
      PRIMARY KEY (`Resources_id`, `OwnerGroups_id`, `OwnerGroups_Instances_has_Customers_Instances_idInstances`, `OwnerGroups_Instances_has_Customers_Customers_idCustomers`),
      INDEX `fk_Resources_has_OwnerGroups_OwnerGroups1_idx` (`OwnerGroups_id` ASC, `OwnerGroups_Instances_has_Customers_Instances_idInstances` ASC, `OwnerGroups_Instances_has_Customers_Customers_idCustomers` ASC),
      INDEX `fk_Resources_has_OwnerGroups_Resources1_idx` (`Resources_id` ASC),
      CONSTRAINT `fk_Resources_has_OwnerGroups_Resources1`
        FOREIGN KEY (`Resources_id`)
        REFERENCES `A_D_schema`.`Resources` (`id`)
        ON DELETE NO ACTION
        ON UPDATE NO ACTION,
      CONSTRAINT `fk_Resources_has_OwnerGroups_OwnerGroups1`
        FOREIGN KEY (`OwnerGroups_id` , `OwnerGroups_Instances_has_Customers_Instances_idInstances` , `OwnerGroups_Instances_has_Customers_Customers_idCustomers`)
        REFERENCES `A_D_schema`.`OwnerGroups` (`id` , `Instances_has_Customers_Instances_idInstances` , `Instances_has_Customers_Customers_idCustomers`)
        ON DELETE NO ACTION
        ON UPDATE NO ACTION)
    ENGINE = InnoDB

SHOW ENGINE INNODB STATUS 我可以看到这条消息:

Cannot resolve column name close to:
)
    ON DELETE NO ACTION
    ON UPDATE NO ACTION,
  CONSTRAINT `fk_Resources_has_OwnerGroups_OwnerGroups1`
    FOREIGN KEY (`OwnerGroups_id` , `OwnerGroups_Instances_has_Customers_Instances_idInstances` , `OwnerGroups_Instances_has_Customers_Customers_idCustomers`)
    REFERENCES `A_D_schema`.`OwnerGroups` (`id` , `Instances_has_Customers_Instances_idInstances` , `Instances_has_Customers_Customers_idCustomers`)
    ON DELETE NO ACTION
    ON UPDATE NO ACTION)
ENGINE = InnoDB

SHOW CREATE TABLE ResourcesSHOW CREATE TABLE OwnerGroups :

CREATE TABLE `Resources` (
  `idResources` int(11) NOT NULL AUTO_INCREMENT,
  `email` varchar(45) DEFAULT NULL,
  `role` int(11) DEFAULT NULL COMMENT 'role : 1 disptcher \n0 admin',
  PRIMARY KEY (`idResources`),
  UNIQUE KEY `idresources_UNIQUE` (`idResources`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;

CREATE TABLE `OwnerGroups` (
  `idOwnerGroups` int(11) NOT NULL AUTO_INCREMENT,
  `name` varchar(45) DEFAULT NULL,
  `group` int(11) DEFAULT NULL,
  PRIMARY KEY (`idOwnerGroups`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
  CONSTRAINT `fk_Resources_has_OwnerGroups_Resources1`
    FOREIGN KEY (`Resources_id`)
    REFERENCES `A_D_schema`.`Resources` (`id`)

您的资源 table 没有列 id。它的主键是idResources.

  CONSTRAINT `fk_Resources_has_OwnerGroups_OwnerGroups1`
    FOREIGN KEY (`OwnerGroups_id` , `OwnerGroups_Instances_has_Customers_Instances_idInstances` , `OwnerGroups_Instances_has_Customers_Customers_idCustomers`)
    REFERENCES `A_D_schema`.`OwnerGroups` (`id` , `Instances_has_Customers_Instances_idInstances` , `Instances_has_Customers_Customers_idCustomers`)

您的 OwnerGroups table 没有列 id。它的主键是idOwnerGroups。它根本没有您引用的其他两列。


一般来说,当你声明一个外键时,首先你在子项中命名列 table:

CREATE TABLE Child (
  childCol1 INT,
  childCol2 INT,
...
FOREIGN KEY (childCol1, childCol2) ...

然后您引用父级中的列 table:

... REFERENCES Parent (parentCol1, parentCol2)
);

您必须使用父 table 中存在的列名称。

您在父 table 中引用的列必须一起成为该 table 的主键或唯一键。换句话说,给定上面的例子,它不会对这个 Parent table:

CREATE TABLE Parent (
  parentCol1 INT,
  parentCol2 INT,
  PRIMARY KEY (parentCol1)
);

因为PRIMARY KEY不包含parentCol2.


对于您的情况,以下应该有效:

CREATE TABLE IF NOT EXISTS `A_D_schema`.`Resources_has_OwnerGroups` (
  `Resources_id` INT NOT NULL,
  `OwnerGroups_id` INT NOT NULL,
  `OwnerGroups_Instances_has_Customers_Instances_idInstances` INT NOT NULL,
  `OwnerGroups_Instances_has_Customers_Customers_idCustomers` INT NOT NULL,
  PRIMARY KEY (`Resources_id`, `OwnerGroups_id`, `OwnerGroups_Instances_has_Customers_Instances_idInstances`, `OwnerGroups_Instances_has_Customers_Customers_idCustomers`),
  CONSTRAINT `fk_Resources_has_OwnerGroups_Resources1`
    FOREIGN KEY (`Resources_id`)
    REFERENCES `A_D_schema`.`Resources` (`idResources`)
    ON DELETE NO ACTION
    ON UPDATE NO ACTION,
  CONSTRAINT `fk_Resources_has_OwnerGroups_OwnerGroups1`
    FOREIGN KEY (`OwnerGroups_id`)
    REFERENCES `A_D_schema`.`OwnerGroups` (`idOwnerGroups`)
    ON DELETE NO ACTION
    ON UPDATE NO ACTION
) ENGINE = InnoDB

我删除了几个多余的 INDEX 定义。你不需要索引你的PRIMARY KEY,它已经是table的聚集索引了。您不需要索引您在外键声明中使用的列,MySQL 将在需要时自动索引该列(尽管如果该列已经存在索引,FK 约束将使用该索引) .

我不确定我是否理解您的其他两列 OwnerGroups_Instances_has_Customers_Instances_idInstancesOwnerGroups_Instances_has_Customers_Customers_idCustomers 的意思。通常在 many-to-many table 中,您只需要足够的列来引用相应父 table 的主键。


回复您的评论:

您应该不时尝试刷新架构视图。在 "SCHEMAS".

的右侧有一个带有一对弯曲箭头的按钮