无法添加外键约束创建表MySQL

时间:2018-05-07 04:38:07

标签: mysql sql minecraft

方法createTable()正在运行,我一直在创建其他简单的表而没有问题。

我正在使用MySQL服务器8.0

这是对表的测试,然后我将创建一个脚本来创建它们。我一直有这个错误:

  

无法创建表,SQLException:无法添加外键约束

但我不知道出了什么问题。

    if(!database.checkTable("maps")){
        String maps = "CREATE TABLE maps (" 
                + "name VARCHAR(32) NOT NULL,"
                + "mapType VARCHAR(32) NOT NULL,"
                + "world VARCHAR(32) NOT NULL,"
                + "referenceId INT(32) NOT NULL,"
                + "regionId INT(32) NOT NULL,"
                + "testmode BIT(1) NOT NULL,"
                + "edition BIT(1) NOT NULL,"
                + "finished BIT(1) NOT NULL,"
                + "PRIMARY KEY (name, referenceId, regionId))"
                + "ENGINE = InnoDB "
                + "DEFAULT CHARACTER SET = utf8;";
        database.createTable(maps);
    }
    if(!database.checkTable("regions")){
        String regions = "CREATE TABLE regions ("
                + "id INT(32) NOT NULL AUTO_INCREMENT," 
                + "minLocationId INT(32) NOT NULL,"
                + "maxLocationId INT(32) NOT NULL,"
                + "PRIMARY KEY (id, minLocationId, maxLocationId),"
                + "CONSTRAINT `regionMapFk`"
                + "FOREIGN KEY (id)"
                + "REFERENCES maps (regionId)"
                + "ON DELETE CASCADE "
                + "ON UPDATE CASCADE)"
                + "ENGINE = InnoDB "
                + "DEFAULT CHARACTER SET = utf8;";
        database.createTable(regions);
    }
    if(!database.checkTable("locations")){
        String locations = "CREATE TABLE locations ("   
                + "id INT(16) NOT NULL AUTO_INCREMENT, "
                + "x INT(16) NOT NULL, "
                + "y INT(16) NOT NULL, "
                + "z INT(16) NOT NULL, "
                + "PRIMARY KEY(id),"
                + "CONSTRAINT `minLocationRegionFk`"
                + "FOREIGN KEY (id)"
                + "REFERENCES regions (minLocationId)"
                + "ON DELETE CASCADE "
                + "ON UPDATE CASCADE,"
                + "CONSTRAINT `maxLocationRegionFk`"
                + "FOREIGN KEY (id)"
                + "REFERENCES regions (maxLocationId)"
                + "ON DELETE CASCADE "
                + "ON UPDATE CASCADE,"
                + "CONSTRAINT `locationMapFk`"
                + "FOREIGN KEY (id)"
                + "REFERENCES maps (referenceId)"
                + "ON DELETE CASCADE "
                + "ON UPDATE CASCADE)"
                + "ENGINE = InnoDB "
                + "DEFAULT CHARACTER SET = utf8;";
        database.createTable(locations);
    }
  

[23:51:36 WARN]:java.sql.SQLException:无法添加外键   约束[23:51:36警告]:at   com.mysql.jdbc.SQLError.createSQLException(SQLError.java:1073)   [23:51:36警告]:at   com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3593)[23:51:36   警告]:at   com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3525)[23:51:36   警告]:在com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:1986)   [23:51:36警告]:at   com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:2140)[23:51:36   警告]:at   com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2620)   [23:51:36警告]:at   com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2570)   [23:51:36警告]:at   com.mysql.jdbc.StatementImpl.execute(StatementImpl.java:779)[23:51:36   警告]:at   com.mysql.jdbc.StatementImpl.execute(StatementImpl.java:622)[23:51:36   警告]:在power.database.MySQL.createTable(MySQL.java:104)   [23:51:36警告]:at   power.managers.DatabaseManager.createTables(DatabaseManager.java:81)   [23:51:36警告]:at   power.managers.DatabaseManager.startDatabase(DatabaseManager.java:40)   [23:51:36警告]:at   power.managers.DatabaseManager。(DatabaseManager.java:30)   [23:51:36警告]:at   power.logic.ClanBattles.onEnable(ClanBattles.java:44)[23:51:36警告]:   在org.bukkit.plugin.java.JavaPlugin.setEnabled(JavaPlugin.java:321)   [23:51:36警告]:at   org.bukkit.plugin.java.JavaPluginLoader.enablePlugin(JavaPluginLoader.java:340)   [23:51:36警告]:at   org.bukkit.plugin.SimplePluginManager.enablePlugin(SimplePluginManager.java:405)   [23:51:36警告]:at   org.bukkit.craftbukkit.v1_8_R3.CraftServer.loadPlugin(CraftServer.java:357)   [23:51:36警告]:at   org.bukkit.craftbukkit.v1_8_R3.CraftServer.enablePlugins(CraftServer.java:317)   [23:51:36警告]:at   org.bukkit.craftbukkit.v1_8_R3.CraftServer.reload(CraftServer.java:741)   [23:51:36警告]:org.bukkit.Bukkit.reload(Bukkit.java:535)   [23:51:36警告]:at   org.bukkit.command.defaults.ReloadCommand.execute(ReloadCommand.java:25)   [23:51:36警告]:at   org.bukkit.command.SimpleCommandMap.dispatch(SimpleCommandMap.java:141)   [23:51:36警告]:at   org.bukkit.craftbukkit.v1_8_R3.CraftServer.dispatchCommand(CraftServer.java:641)   [23:51:36警告]:at   net.minecraft.server.v1_8_R3.PlayerConnection.handleCommand(PlayerConnection.java:1162)   [23:51:36警告]:at   net.minecraft.server.v1_8_R3.PlayerConnection.a(PlayerConnection.java:997)   [23:51:36警告]:at   net.minecraft.server.v1_8_R3.PacketPlayInChat.a(PacketPlayInChat.java:45)   [23:51:36警告]:at   net.minecraft.server.v1_8_R3.PacketPlayInChat.a(PacketPlayInChat.java:1)   [23:51:36警告]:at   net.minecraft.server.v1_8_R3.PlayerConnectionUtils $ 1.run(的SourceFile:13)   [23:51:36警告]:at   java.util.concurrent.Executors $ RunnableAdapter.call(Unknown Source)   [23:51:36警告]:在java.util.concurrent.FutureTask.run(未知   来源)[23:51:36警告]:at   net.minecraft.server.v1_8_R3.SystemUtils.a(SourceFile:44)[23:51:36   警告]:at   net.minecraft.server.v1_8_R3.MinecraftServer.B(MinecraftServer.java:715)   [23:51:36警告]:at   net.minecraft.server.v1_8_R3.DedicatedServer.B(DedicatedServer.java:374)   [23:51:36警告]:at   net.minecraft.server.v1_8_R3.MinecraftServer.A(MinecraftServer.java:654)   [23:51:36警告]:at   net.minecraft.server.v1_8_R3.MinecraftServer.run(MinecraftServer.java:557)   [23:51:36警告]:在java.lang.Thread.run(未知来源)

4 个答案:

答案 0 :(得分:0)

我认为你正在反向创建外键,这是不正确的。

由于您的map表格有regionId,因此您应该在地图表中为其创建FOREIGN KEY,而不是region本身。因此,在脚本中更改它以便以这种方式创建map表:

FOREIGN KEY (regionId) REFERENCES regions(id)

同样适用于maxLocationId表的region列。外键应在region表中定义,而不是locations本身。

任何外键都应引用引用表中的PRIMARY KEY,如果不引用,则mysql不会创建它。

此外,您应该在创建表和定义PRIMARY KEY时保持依赖顺序,然后在它们之间创建任何引用FOREIGN KEY。

例如,您应首先创建region表并定义其PRIMARY KEY。之后,您应该创建一个map表,其中引用了region,现在您可以在map表中定义引用id(或通常为PRIMARY)的外键KEY region列上的regionId表格。

有关创建外键的概念和语法,请参阅this参考。

答案 1 :(得分:0)

为什么你的区域表中有FOREIGN KEY(id)REFERENCES map(regionId)?它应该是另一种方式不是它(区域表是主表,它的表由表映射引用)?

所以在创建表映射DDL

中应该是这样的
OnResize

与FK内部位置表相同,我认为应该是相反的方式

答案 2 :(得分:0)

您无法在一个表中创建多个主键 就像你在地图表中所做的那样

"CREATE TABLE maps (" 
                + "name VARCHAR(32) NOT NULL,"
                + "mapType VARCHAR(32) NOT NULL,"
                + "world VARCHAR(32) NOT NULL,"
                + "referenceId INT(32) NOT NULL,"
                + "regionId INT(32) NOT NULL,"
                + "testmode BIT(1) NOT NULL,"
                + "edition BIT(1) NOT NULL,"
                + "finished BIT(1) NOT NULL,"
                + "PRIMARY KEY (name, referenceId, regionId))"
                + "ENGINE = InnoDB "
                + "DEFAULT CHARACTER SET = utf8;";

要创建外键约束,您必须提供该表的主键的引用,您要用它来绑定当前表

看看 https://www.w3schools.com/sql/sql_foreignkey.asp

CREATE TABLE Orders (
    OrderID int NOT NULL,
    OrderNumber int NOT NULL,
    PersonID int,
    PRIMARY KEY (OrderID),
    FOREIGN KEY (PersonID) REFERENCES Persons(PersonID)
); 

答案 3 :(得分:0)

您只需要设置所有约束的唯一名称。 约束的名称在整个数据库中必须是唯一的。