问小白 wenxiaobai
资讯
历史
科技
环境与自然
成长
游戏
财经
文学与艺术
美食
健康
家居
文化
情感
汽车
三农
军事
旅行
运动
教育
生活
星座命理

MySQL表显示"doesn't exist"错误?两种场景下的修复方案详解

创作时间:
作者:
@小白创作中心

MySQL表显示"doesn't exist"错误?两种场景下的修复方案详解

引用
CSDN
1.
https://blog.csdn.net/qq_34692500/article/details/139079271

上周有朋友反馈线上MySQL 5.7数据库查询 audit_log 表出现 "doesn't exist" 错误,查询不到任何数据,而其他表都正常。他不想删库重做,这种问题要怎么修复?

问题分析

查询 audit_log 表出现 "doesn't exist" 现象,通常是由于数据损坏导致的。首先排查了MySQL的数据目录,发现 audit_log 表的 .frm 文件丢失。接下来尝试了数据修复的 REPAIR TABLE 操作,但没有效果。最后只能通过处理表空间的操作来解决此问题。

为了模拟该问题,我从两个维度进行模拟:

  1. 丢失 .frm 文件
  2. 将当前实例的 .frm.ibd 文件全部废弃,导入从备份文件恢复后的 .frm.ibd 文件

表修复尝试

REPAIR TABLE audit_log;

.frm 文件丢失环境模拟

当前 audit_log 表查询一切正常,接下来手动删除 .frm 文件:

  1. 手动删除 .frm 文件
  2. 查询开始报 "doesn't exist" 错误

场景一:恢复 .frm 文件

  1. 创建一个新库 vss_tmp,创建一个新的 audit_log 表,表结构要与故障表一致:

    mysql> create database vss_tmp;
    Query OK, 1 row affected (0.00 sec)
    
    mysql> use vss_tmp
    Database changed
    
    mysql> CREATE TABLE `audit_log`  (
        ->   `id` int(11) NOT NULL AUTO_INCREMENT,
        ->   `user_id` int(11) NOT NULL,
        ->   `user_name` varchar(30) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL DEFAULT NULL,
        ->   `user_display` varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL DEFAULT NULL,
        ->   `action` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL,
        ->   `extra_info` longtext CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL,
        ->   `action_time` datetime(6) NOT NULL,
        ->   PRIMARY KEY (`id`) USING BTREE
        -> ) ENGINE = InnoDB AUTO_INCREMENT = 211 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_general_ci ROW_FORMAT = Dynamic;
    Query OK, 0 rows affected (0.01 sec)
    
  2. 将新建的 vss_tmp 库下的表结构拷贝到故障库 vss 中:

    1)拷贝前先执行 ALTER TABLE ... DISCARD TABLESPACE

     ```sql
     mysql> use vss
     Database changed
    
     mysql> show tables;
     Empty set (0.00 sec)
    
     mysql> select * from audit_log;
     ERROR 1146 (42S02): Table 'vss.audit_log' doesn't exist
    
     mysql> alter table audit_log discard tablespace;
     ERROR 1146 (42S02): Table 'vss.audit_log' doesn't exist
     ```
    

    2)执行 cp 操作,记得授权:

     ```bash
     bash-4.2# cd /var/lib/mysql/vss/
     bash-4.2# ls
     audit_log.ibd  db.opt
     bash-4.2# cd /var/lib/mysql/vss_tmp/
     bash-4.2# ls
     audit_log.frm  audit_log.ibd  db.opt
     bash-4.2# cp audit_log.frm ../vss/
     bash-4.2# cd ../vss
     bash-4.2# ls
     audit_log.frm  audit_log.ibd  db.opt
    
     [root@sql-audit-20230526 db1]# cd /var/lib/docker/volumes/5ad9cfe140f098b1352fad8dff1eea69e26ccf2dcab74ed0054de4c15302ae8a/_data/vss
     [root@sql-audit-20230526 vss]# ll -h
     total 112K
     -rw-r----- 1 root             root     8.6K May 19 11:32 audit_log.frm
     -rw-r----- 1 systemd-coredump ssh_keys  96K May 19 10:58 audit_log.ibd
     -rw-r----- 1 systemd-coredump ssh_keys   65 May 19 10:56 db.opt
     [root@sql-audit-20230526 vss]# chown -R systemd-coredump:ssh_keys audit_log.frm
     ```
    

    3)执行 IMPORT TABLESPACE 操作:

     ```sql
     mysql> use vss
     mysql> ALTER TABLE audit_log IMPORT TABLESPACE;
     ERROR 1813 (HY000): Tablespace 'vss/audit_log' exists.
     ```
    

    4)重启 MySQL:

     ```bash
     [root@sql-audit-20230526 vss]# docker restart mysql5.7
     mysql5.7
     ```
    

    5)查询恢复正常

场景二:从备份恢复的新实例拷贝数据 .frm.ibd 文件

环境准备

  • 新实例:vss_tmp 库,audit_log 表,9 条数据
  • 故障实例:vss 库,数据文件都已清除,报 "doesn't exist"

操作步骤

1)拷贝前先执行 ALTER TABLE ... DISCARD TABLESPACE

2)执行 cp 操作,记得授权:

```bash
bash-4.2# cd /var/lib/mysql/vss
bash-4.2# ls
db.opt
bash-4.2# cp /var/lib/mysql/vss_tmp/
audit_log.frm  audit_log.ibd  db.opt
bash-4.2# cp /var/lib/mysql/vss_tmp/audit_log.frm ./
bash-4.2# cp /var/lib/mysql/vss_tmp/audit_log.ibd ./
bash-4.2# ls
audit_log.frm  audit_log.ibd  db.opt

[root@sql-audit-20230526 vss]# cd /var/lib/docker/volumes/5ad9cfe140f098b1352fad8dff1eea69e26ccf2dcab74ed0054de4c15302ae8a/_data/vss
vss/     vss_tmp/
[root@sql-audit-20230526 vss]# cd /var/lib/docker/volumes/5ad9cfe140f098b1352fad8dff1eea69e26ccf2dcab74ed0054de4c15302ae8a/_data/vss
[root@sql-audit-20230526 vss]# ll -h
total 112K
-rw-r----- 1 root             root     8.6K May 19 12:00 audit_log.frm
-rw-r----- 1 root             root      96K May 19 12:01 audit_log.ibd
-rw-r----- 1 systemd-coredump ssh_keys   65 May 19 10:56 db.opt
[root@sql-audit-20230526 vss]# chown systemd-coredump:ssh_keys *
[root@sql-audit-20230526 vss]# ll -h
total 112K
-rw-r----- 1 systemd-coredump ssh_keys 8.6K May 19 12:00 audit_log.frm
-rw-r----- 1 systemd-coredump ssh_keys  96K May 19 12:01 audit_log.ibd
-rw-r----- 1 systemd-coredump ssh_keys   65 May 19 10:56 db.opt
```

3)执行 IMPORT TABLESPACE 操作:

```sql
mysql> use vss
Reading table information for completion of table and column names
You can turn off this feature to get a quicker startup with -A

mysql> ALTER TABLE audit_log IMPORT TABLESPACE;
Query OK, 0 rows affected, 2 warnings (0.01 sec)
```

4)重启 MySQL:

```bash
[root@sql-audit-20230526 vss]# docker restart mysql5.7
mysql5.7
```

5)查询恢复正常,9 条数据

注意事项

处理表空间的操作通常用于数据库备份、恢复和迁移的过程中,能够有效地管理表的表空间文件。需要注意的是,这些操作通常需要在数据库处于只读模式下执行,以确保数据的一致性和完整性。

© 2023 北京元石科技有限公司 ◎ 京公网安备 11010802042949号