MySQL外键错误:无法创建表

时间:2017-12-31 14:06:50

标签: mysql sql database

我正在尝试在MySQL数据库中创建名为class_membershistory的两个表。 class_members表包含有关成员的信息,并创建为:

CREATE TABLE `class_members` (
  `id` int(11) NOT NULL,
  `username` varchar(65) NOT NULL DEFAULT '',
  `password` varchar(65) NOT NULL DEFAULT '',
  `email` varchar(65) NOT NULL,
  `mod_timestamp` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
  PRIMARY KEY (`id`),
  UNIQUE KEY `username_UNIQUE` (`username`),
  UNIQUE KEY `id_UNIQUE` (`id`),
  UNIQUE KEY `email_UNIQUE` (`email`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 

class_members表已成功创建。

创建包含history foreign key class_members引用的CREATE TABLE `History` ( `history_id` INT(11) NOT NULL AUTO_INCREMENT, `username` VARCHAR(65) NOT NULL DEFAULT '', `timestamp` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, `ip` VARCHAR(20) NOT NULL, PRIMARY KEY (`history_id`), CONSTRAINT `fk_history_member` FOREIGN KEY (`username`) REFERENCES `class_members` (`username`) ON UPDATE CASCADE); 表时,我遇到了问题。

我使用的命令如下:

ERROR 1005 (HY000): Can't create table 'testDB.History' (errno: 150)

当我执行上述命令时,我收到此错误:

History

我试图找出为什么我无法阅读ENGINE=InnoDB DEFAULT CHARSET=utf8表 (about ERROR 1005)  但我不明白为什么

关注评论,我创建了一个新的数据库并尝试使用上面的命令创建,我仍然得到错误。见附图 enter image description here

更新(已解决)

我找到了为什么上面的屏幕截图中出现错误。要解决这个问题,我们必须在历史表创建命令的末尾添加 CREATE TABLE `History` ( `history_id` INT(11) NOT NULL AUTO_INCREMENT, `username` VARCHAR(65) NOT NULL DEFAULT '', `timestamp` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, `ip` VARCHAR(20) NOT NULL, PRIMARY KEY (`history_id`), CONSTRAINT `fk_history_member` FOREIGN KEY (`username`) REFERENCES `class_members` (`username`) ON UPDATE CASCADE)ENGINE=InnoDB DEFAULT CHARSET=utf8;

    private async Task<T> GetResponse<T>(Dictionary<string, object> args, string method)
    {
        try
        {
            var response = await _client.PostAsJsonAsync(method, args);


            return await Deserialise<T>(response.Content); 

        }
        catch (OperationCanceledException)
        {
            return await Task.FromResult(default(T));
        }
    }

    private async Task<T> Deserialise<T>(HttpContent content)
    {
        using (var stream = await content.ReadAsStreamAsync())
        using (var streamReader = new StreamReader(stream))
        using (var reader = new JsonTextReader(streamReader))
        {
            var serializer = new JsonSerializer();
            try
            {
                return serializer.Deserialize<T>(reader);
            }
            catch (JsonSerializationException e)
            {
                throw new ClientException("Failed to deserialize object, see inner exception and content for more details", e) { Content = reader.ReadAsString() };
            }
        }
    }

这很有效。

2 个答案:

答案 0 :(得分:2)

您的查询适用于rextester

确保您还没有名为history的现有表格。如果我重新创建history表,我会得到:

  

无法删除或更新父行:外键约束失败

您可以通过运行rextester一次查询来重现此操作,然后移除drop table if exists history;行,然后重新运行。

如果您尝试在同一批次中创建两次表,则可以改为:

  

表'历史'已经存在

答案 1 :(得分:0)

我认为你的问题来自索引的起源。以这种方式尝试代码;

CREATE TABLE `class_members` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `username` varchar(65) NOT NULL DEFAULT '',
  `password` varchar(65) NOT NULL DEFAULT '',
  `email` varchar(65) NOT NULL,
  `mod_timestamp` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
  PRIMARY KEY (`id`),
  UNIQUE KEY `username_UNIQUE` (`username`),
  UNIQUE KEY `id_UNIQUE` (`id`),
  UNIQUE KEY `email_UNIQUE` (`email`),
    INDEX `index_username` (`username`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

CREATE TABLE `History` ( 
  `history_id` INT(11) NOT NULL AUTO_INCREMENT, 
  `username` VARCHAR(65) NOT NULL DEFAULT '', 
  `timestamp` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, 
  `ip` VARCHAR(20) NOT NULL,  
  PRIMARY KEY (`history_id`), 
  CONSTRAINT `fk_history_member` FOREIGN KEY (`username`) 
  REFERENCES `class_members` (`username`) 
  ON UPDATE CASCADE);

对于SQLFiddle示例; Click Here