聊到MySQL5.7 到 8.0.23数据字典更改,当然原先frm 文件不见了,多出了mysql.ibd文件。那到底改了什么。仅仅是文件名字的替换。
Serialized Dictionary Information是指表结构元数据。MySQL 8.0通过在元数据发生变化时序列化元数据,提供了崩溃安全性。它的输出是JSON (JavaScript对象表示法)格式,称为序列化字典信息(SDI)。
对于InnoDB表,SDI与InnoDB用户表空间中的数据一起存储。对于MyISAM和其他存储引擎,它被写入数据目录中的.sdi文件。
除了临时表空间和撤销表空间文件外,所有InnoDB表空间文件中都存在SDI。InnoDB表空间文件中的SDI记录仅描述表空间中包含的表和表空间对象。
-
SDI数据通过对表或检查表的DDL操作进行更新的。
-
MySQL服务器使用DDL操作期间访问的内部API来创建和维护SDI记录。
-
当MySQL服务器升级到一个新的版本或版本时,SDI数据不会更新。
-
记录数据方式:对于InnoDB,一条SDI记录需要一个索引页,默认大小为16KB。但实际SDI数据被压缩以减少存储空间。
-
分区表:
对于由多个表空间组成的分区InnoDB表,SDI数据存储在第一个分区的表空间文件中。
注意,这个SDI只是元数据的备份。它不是元数据本身。数据字典完全存在于InnoDB数据字典表空间中。
SDI数据的存在提供了元数据冗余。那么,如果数据字典不可用,可以使用ibd2sdi工具直接从InnoDB表空间文件中提取对象元数据。
ibd2sdi是一个用于从InnoDB表空间文件中提取序列化字典信息(SDI)的实用程序,导出格式为JSON。所有的InnoDB表空间文件都存在SDI数据。
2.ibd2sdi可以
- file-per-table 表空间文件上运行(*.ibd files)文件,
- 一般表空间文件 (*.ibd files)。
- 系统表空间文件 (ibdata* files)
- 数据字典表空间(mysql.ibd)。
- 它不支持temporary表空间或undo表空间。
- ibd2sdi可以在运行时使用,也可以在服务器离线时使用。在进行与SDI相关的DDL操作、回滚操作和undo log purge操作时,可能会出现ibd2sdi读取存储在表空间中的SDI数据失败的短时间间隔。
ibd2sqi目前功能,只是单纯的提取字典信息。核心还是抽取数据部分。
[root@ens8 mysql]# ibd2sdi -v ibd2sdi Ver 8.0.23 for Linux on x86_64 (MySQL Community Server - GPL) [root@ens8 emp]# ibd2sdi ./departments.ibd
比如:
1.sdi_version->dd_version:
从mysql8.0.19升级到 8.0.23版本
2.created,last_altered:创建时间是最后更新时间
3.字段有哪些,长度,引擎 文件路径 等
[root@ens8 mysql]# ibd2sdi --skip-data ./db1/a1.ibd ["ibd2sdi", { "type": 1, "id": 1222 }, { "type": 2, "id": 142 }]
对于MyISAM引擎的直接cat sdi文件即可:
3.数据恢复操作
1.MyISAM引擎表恢复操作
##创建表 模拟数据
mysql>CREATE TABLE `depart_myisam` (
`dept_no` char(4) COLLATE utf8mb4_bin NOT NULL,
`dept_name` varchar(40) COLLATE utf8mb4_bin NOT NULL,
PRIMARY KEY (`dept_no`)
) ENGINE=MYISAM;
mysql>INSERT INTO depart_myisam(dept_no,dept_name) VALUES('001','Beijing');
##cp 数据文件之后
mysql>DROP TABLE depart_myisam;
##恢复操作,文件拷贝
shell> cp depart_myisam_2389.sdi /opt/data8.0/tmp
shell> cp depart_myisam.* /opt/data8.0/mysql/emp
shell>chown -R mysql.mysql ./depart_myisam_2389.sdi
shell>chown -R mysql.mysql ./depart_myisam.*
##导入文件
mysql>IMPORT TABLE FROM '/opt/data8.0/tmp/depart_myisam_2389.sdi';
备注;.sdi文件可以放在由secure_file_priv系统变量命名的目录中,data目录中。
.MYD .MYI 文件放到实际数据目录下
2.ibd恢复
分析独立表空间:
以下方式简单通过shell ,手动创建表结构。
shell>ibd2sdi --type=1 t1.ibd --dump-file=/opt/script/json/t1.txt
shell>cat t1.txt | grep -P 'name|column_type_utf8[" :]+\K[^"]+'
备注:table (type=1) and tablespace (type=2)
备注:创建新表时,必须需要之前表PRIMARY信息,其他索引可无。
恢复操作:
#1.目标实例上,丢弃刚新创建的表的表空间
mysql> ALTER TABLE t1 DISCARD TABLESPACE;
#2.运行FLUSH TABLES…以暂停要导入的表。当表处于静默状态时,该表上只允许有只读事务。
mysql> FLUSH TABLES t1 FOR EXPORT;
##3.复制文件
shell> cp /bak/world/t1.{ibd,cfg} /datadir/world
shell>chown -R mysql.mysql /datadir/world/t1.*
#4.使用UNLOCK TABLES来释放FLUSH TABLES获得的锁
mysql> UNLOCK TABLES;
##5.在目标实例上,导入表空间:
mysql> ALTER TABLE t1 IMPORT TABLESPACE;
备注:如有原表结构最好,没有的情况下只能分析ibd文件。
对于表结构分析ibd2sdi工具,没有 mysql-utilities工具那样灵活。
目前来说需要通过shell,jp 或则 python 进行二次分析才可以。
- 可以说Serialized Dictionary Information(SDI)结构数据字典,看起来非常舒服,很多信息都透明化,易懂易读。
- 对于ibd2sdi工具,当数据库宕机系统表结构无法抽取时,分析还是比较麻烦的。所以日常备份很重要。目前从ibd2sdi索引的信息怎么定位,没有找到好的方式。
技术能力的提升,源于每天默默无闻坚持地努力!