【问题标题】:MySQL can't select from existing table because it doesn't exist?MySQL 无法从现有表中选择,因为它不存在?
【发布时间】:2014-11-20 14:29:00
【问题描述】:

我不知道发生了什么。我有一张名为project_share_invite 的表。几个小时前(在我们的生产环境中)我无法再针对该表发出 SELECT。 MySQL 声称该表不存在,尽管它显示在show tables 上。今天在机器上发生的唯一值得注意的事件是例行软件包升级(通过 apt)。

mysql> use analytics;
Database changed

mysql> show tables like 'project_share_invite';
+--------------------------------------------+
| Tables_in_analytics (project_share_invite) |
+--------------------------------------------+
| project_share_invite                       |
+--------------------------------------------+
1 row in set (0.00 sec)

mysql> select count(*) from project_share_invite;
ERROR 1146 (42S02): Table 'analytics.project_share_invite' doesn't exist

想法?这对我来说没有任何意义。

更新:该表的文件仍然存在于磁盘上(分别为project_share_invite.frmproject_share_invite.idb)并且其中有内容。

快速重启 MySQL 并没有解决这个问题。

更新:使用 root 帐户而不是特定用户帐户时的结果相同。

更新:我也无法重新创建表。

CREATE TABLE `analytics`.`project_share_invite` ( ... )
ERROR 1146 (42S02): Table 'analytics.project_share_invite' doesn't exist

更新:应该先检查错误日志:

InnoDB: Load table 'analytics/project_share_invite' failed, the table has missing foreign key indexes. 

虽然我不知道它是怎么变成这种状态的。

【问题讨论】:

  • 先愚蠢的问题:表的名字末尾有空格吗?是否有任何project_share_invite 文件从 MySQL 数据目录中删除?
  • 尝试运行这个以及额外的检查.. SELECT table_name, table_type, engine FROM information_schema.tables WHERE table_schema = 'analytics';
  • 谢谢大家。这些文件仍然存在于磁盘上(添加了该信息)。该表在information_schema.tables 中也正确显示。
  • 对我来说唯一有意义的是,不再存在允许登录用户针对此架构的表进行选择的选择访问权限。
  • 不幸的是,以 mysql root 用户身份登录时也会出现相同的行为。

标签: mysql


【解决方案1】:

此错误通常是由在文件系统级别移动文件引起的。

请记住,SHOW TABLES 只是读取 .frm 文件,但是一旦您查询该表,MySQL 就会调用存储引擎。 InnoDB 有自己的内部元数据管理方式,“数据字典”始终存储在ibdata1 中。

因此,如果您移动了 datadir 但忘记了 ibdata1 文件(或从另一个实例复制了 ibdata1),那么 InnoDB 数据字典将不知道该表,即使 SHOW TABLES 知道。

另一种可能是您复制了数据文件,现在它们没有写入所有权或文件权限。因此,例如 .frm 文件是可读的,但 .ibd 不是。它们应该由 mysql:mysql 拥有和写入。

如果您的 apt 升级更改了文件位置或文件权限,这也可能导致此问题。我建议使用ls -l 来验证文件的权限。

【讨论】:

    【解决方案2】:

    看起来您在 MySQL 中遇到了一个已知错误,其中存在外键约束,但关联的索引已被删除。见:http://bugs.mysql.com/bug.php?id=68148

    根据 MySQL 的版本(似乎您需要 5.6 或 >),您可以通过关闭外键检查然后重新创建丢失的索引来解决此问题。

    SET FOREIGN_KEY_CHECKS=0;
    

    您应该使用 SHOW CREATE TABLE table name 检查结构

    然后使用CREATE INDEX 重新创建丢失的索引。

    【讨论】:

    • 很棒的回应和帮助
    • 注意:该错误被标记为已修复,但该修复只会阻止您删除索引。如果您使用FOREIGN_KEY_CHECKS=0 设置进行更改,您仍然可能会遇到这种情况。我们在 MySQL 5.7.28 上更改了一个数据库上的字符集并忘记了跨数据库外键后,设法进入了这个问题。
    • 即使将 foreign_key_checks 设置为 0,mysql 也不允许我执行 SHOW CREATE TABLE 查询。查询以以下错误结束,“引擎中不存在该表。”。请帮我解决这个问题。
    猜你喜欢
    • 2014-04-08
    • 2015-03-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-12-05
    • 1970-01-01
    • 1970-01-01
    • 2011-04-23
    相关资源
    最近更新 更多