MySQL 存储引擎

MySQL 存储引擎

1. 介绍 plugin storage engine

存储引擎相当于Linux 文件系统。
插件的模式存在。作用在表的一种属性。

2. MySQL中的存储引擎类型

Oracle MySQL : 
mysql> show engines;
MRG_MYISAM         
CSV                
MyISAM             
BLACKHOLE          
PERFORMANCE_SCHEMA 
InnoDB             
ARCHIVE            
MEMORY             
FEDERATED          

笔试题: 请你列举MySQL 支持的存储引擎种类?
InnoDB、MyISAM、CSV、Memory…
MySQL 5.5 版本以后,默认的引擎是InnoDB。

Percona , MariaDB 其他的存储引擎种类:
TokuDB , Myrocks等。
特性:
1. 更高的压缩比。
2. 更快速的插入性能。

生产案例:真实学生案例-监控系统优化。
环境: zabbix 3.x   ,  centos 7.3 , mariaDB 5.5  ,监控2000+节点
现象 : zabbix卡的要死 ,每隔3-4个月,都要重新搭建一遍zabbix,存储空间经常爆满.
问题 : 1. zabbix 版本 
          2. 数据库版本
          3. zabbix数据库500G,存在一个文件里
优化建议:
1.数据库版本升级到10.x最新版本,zabbix升级更高版本
2.存储引擎改为tokudb
3.监控数据按月份进行切割(二次开发:zabbix 数据保留机制功能重写,数据库分表)
4.关闭binlog和双1
5.参数调整....

优化结果:
监控状态良好

为什么?
1. 原生态支持TokuDB,另外经过测试环境,10.x要比5.5版本性能 高2-3倍
2. TokuDB:insert数据比Innodb快的多,数据压缩比要Innodb高
3.监控数据按月份进行切割,为了能够truncate每个分区表,立即释放空间
4.关闭binlog ----->减少无关日志的记录.
5.参数调整...----->安全性参数关闭,提高性能.

晚上作业:
参考文档:
https://www.jianshu.com/p/898d2e4bd3a7

3. InnoDB核心特性的介绍

聚簇索引
AHI 自适应hash索引
change buffer
事务
MVCC 多版本并发控制
行级锁
外键
复制特性
支持热备
自动故障恢复(ACSR)
双写机制

面试题: 
1. 请你介绍InnoDB存储引擎的核心特性?
2. 请说明InnoDB和MyISAM的区别?

经典案例: 将MyIAM存储引擎替换为InnoDB-1
环境: centos 5.8 ,MySQL 5.0版本,MyISAM存储引擎,网站业务(LAMT),数据量50G左右
现象问题: 业务压力大的时候,非常卡;经历过宕机,会有部分数据丢失.
问题分析:
1.MyISAM存储引擎表级锁,在高并发时,会有很高锁等待
2.MyISAM存储引擎不支持事务,在断电时,会有可能丢失数据
3.主从复制,1年多没同步了。
职责
1.监控锁的情况:有很多的表锁等待
2.存储引擎查看:所有表默认是MyISAM
解决方案:
1.升级MySQL 5.6.2x版本
2. 迁移所有表到新环境,替换存储引擎
3. 开启双1安全参数

4. 存储引擎替换生产案例

经典案例: 将MyIAM存储引擎替换为InnoDB-2
MySQL 版本 5.6 ,由于历史遗留问题,一部分表是MyISAM。
找出MyISAM表,全部替换为InnoDB。

查询业务库中,非InnoDB的表。
SELECT table_schema,table_name,ENGINE
FROM information_schema.tables 
WHERE table_schema NOT IN ('sys','information_schema','performance_schema','mysql')
AND ENGINE!='INNODB';
查询业务库中,非InnoDB的表批量替换为InnoDB
修改配置文件
vim /etc/my.cnf 
#添加配置并重启
secure-file-priv=/tmp

SELECT CONCAT("ALTER TABLE ",table_schema,".",table_name," ENGINE=INNODB;")
FROM information_schema.tables 
WHERE table_schema NOT IN ('sys','information_schema','performance_schema','mysql')
AND ENGINE!='INNODB' INTO OUTFILE '/tmp/alter.sql';

5. 存储引擎基础管理

5.1 使用 SELECT 确认会话存储引擎

SELECT @@default_storage_engine;

5.2 存储引擎(不代表生产操作)

5.2.1 会话级别:

set default_storage_engine=myisam;

5.2.2 全局级别(仅影响新会话):

set global default_storage_engine=myisam;
重启之后,所有参数均失效.

如果要永久生效:
写入配置文件
vim /etc/my.cnf
[mysqld]
default_storage_engine=InnoDB

存储引擎是表级别的,每个表创建时可以指定不同的存储引擎,但是我们建议统一为innodb.

5.3 SHOW 确认每个表的存储引擎:

SHOW CREATE TABLE City\G;
SHOW TABLE STATUS LIKE 'CountryLanguage'\G

5.4 INFORMATION_SCHEMA 确认每个表的存储引擎

select table_schema,table_name ,engine from information_schema.tables where table_schema not in ('sys','mysql','information_schema','performance_schema');
Master [world]>show table status;
Master [world]>show create table city;

5.5 修改一个表的存储引擎

alter table t1 engine innodb;
批量替换: 
SELECT CONCAT("ALTER TABLE ",table_schema,".",table_name," ENGINE=INNODB;")
FROM information_schema.tables 
WHERE table_schema NOT IN ('sys','information_schema','performance_schema','mysql')
AND ENGINE!='INNODB' INTO OUTFILE '/tmp/alter.sql';

注意:此命令我们经常使用他,进行innodb表的碎片整理

5.6 案例:平常处理过的MySQL问题–碎片处理

环境:centos7.4,MySQL 5.7.20,InnoDB存储引擎
业务特点:数据量级较大,经常需要按月delete删除历史数据.
问题:磁盘空间占用很大,不释放
处理方法:
以前:将数据逻辑导出,手工drop表,然后导入进去
现在:
对表进行按月进行分表(partition,中间件,归档表pt-archive)
业务替换为truncate方式

5.7 扩展:如何批量修改

需求:将zabbix库中的所有表,innodb替换为tokudb
select concat(“alter table zabbix.”,table_name," engine tokudb;") from
information_schema.tables where table_schema=‘zabbix’ into outfile ‘/tmp/tokudb.sql’;

6. InnoDB 体系结构

6.1 物理存储结构

6.1.1 宏观

city.frm : 数据字典信息(列定义)
city.ibd : 表空间数据文件,存储数据行和索引
ibdata1 : 共享(系统)表空间文件
ib_logfileN : redo log文件,重做日志。
ibtmp1 : 临时表空间
ib_buffer_pool : 内存预热文件

6.1.2 微观

(1)ibd : 表空间数据文件,段---》区 ----》页
(2)ibdata1:https://dev.mysql.com/doc/refman/8.0/en/innodb-architecture.html
	#5.5 版本 :
	Data Dictionary,Double write,change buffer ,Undo,临时表,用户数据
	#5.6 版本 :
	Data Dictionary,Double write,change buffer ,Undo,临时表
	#5.7 版本 : 
	Data Dictionary,Double write,change buffer ,Undo
	#8.0 版本
	change buffer	
Data Dictionary :数据库当中所有表的结构、属性、状态、参数....
Double write    :自动故障恢复应用到的数据。
change buffer   :辅助索引需要更新数据。	
Undo            : 存储事务的回滚信息日志。
(3) ib_logfileN : 存储事务的前滚日志。内存数据页的变化。
(4) ibtmp1      :存储SQL处理过程中的中间数据(group by , having , join, union)。	

6.1.3 表空间存储管理方式

#介绍
在数据库引擎层,加入的逻辑的存储结构。来实现灵活的存储空间扩容。
MySQL 5.5 版本引入了表空间存储管理模式。
#表空间类型
– 共享表空间 :ibdata1~ibdataN
5.5 版本的默认模式。用来存储所有的系统数据+用户数据(数据行+索引)。
ibdata文件默认是一个,不够用了可以进行扩容。

独立表空间 :
5.6 版本+:
默认采用独立表空间模式。每张表都是独立的表空间(t1.ibd)。
共享表空间保留下来,只保存系统相关的数据。

5.7 和 8.0 版本中,将ibdata1进一步的瘦身。

操作
查看和配置表空间模式
mysql> select @@innodb_file_per_table;
mysql> set global innodb_file_per_table=0;
mysql> set global innodb_file_per_table=1;

==============================================

 案例: 表空间迁移技术:实现表快速迁移。 
1.  停止相关业务
mysql> lock tables t100w read;
mysql> delete from t100w where id=1000;
ERROR 1099 (HY000): Table 't100w' was locked with a READ lock and can't be updated
mysql> select * from t100w limit 10;

2. 目标库创建一摸一样的表	
mysql> create database test  charset utf8mb4;
Query OK, 1 row affected (0.01 sec)
mysql> use test;
mysql>  CREATE TABLE `t100w` (
    ->   `id` int(11) NOT NULL,
    ->   `num` int(11) DEFAULT NULL,
    ->   `k1` char(2) DEFAULT NULL,
    ->   `k2` char(4) DEFAULT NULL,
    ->   `dt` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
    ->   PRIMARY KEY (`id`),
    ->   KEY `idx` (`k1`,`k2`)
    -> ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 ;

3. 将目标空的ibd表空间删除
mysql> alter table t100w discard tablespace;

4. 迁移ibd至目标库
[root@db01 test]# cp /data/3306/data/test/t100w.ibd /data/3307/data/test/
[root@db01 test]# chown -R mysql.mysql /data

5. 导入表空间 
mysql> alter table t100w import tablespace;

4. 迁移ibd至目标库
[root@db01 test]# cp /data/3306/data/test/t100w.ibd /data/3307/data/test/
[root@db01 test]# chown -R mysql.mysql /data

5. 导入表空间 
mysql> alter table t100w import tablespace;
真实学员案例2则: 
1. 表空间迁移技术实现数据损坏恢复
案例背景:
硬件及软件环境:
	联想服务器(IBM) 
	磁盘500G 没有raid
	centos 6.8
	mysql 5.6.33  innodb引擎  独立表空间
	备份没有,日志也没开
开发用户专用库:
	jira(bug追踪) 、 confluence(内部知识库)    ------>LNMT
运维小组长 : 运维工作 + 数据库 

故障描述: 断电了,启动完成后 “/” 只读
fsck  重启,系统成功启动,mysql启动不了。
结果:confulence库在  , jira库不见了

交流
学员求助内容:
求助:这种情况怎么恢复?
我问:有备份没
求助:没有备份,没有主从,连二进制日志都没有。
我说:没招了,jira库需要硬盘恢复了。

求助:
1、jira问题拉倒中关村了
2、能不能暂时把confulence库先打开用着

学员尝试: 将生产库confulence,拷贝到1:1虚拟机上/var/lib/mysql,直接访问时访问不了的
问:有没有工具能直接读取ibd
我说:我查查,最后发现没有
虚拟机测试可行
我想出一个办法来:
表空间迁移:
create table xxx
alter table confulence.t1 discard tablespace;
alter table confulence.t1 import tablespace;

处理问题思路:

confulence库中一共有107张表。

1、创建107和和原来一模一样的表。
他有2016年的历史库,我让他去他同事电脑上 mysqldump备份confulence库
mysqldump -uroot -ppassw0rd -B confulence --no-data >test.sql
拿到你的测试库,进行恢复
到这步为止,表结构有了。

2、表空间删除。
select concat(‘alter table ‘,table_schema,’.‘table_name,’ discard tablespace;’) from information_schema.tables where table_schema=‘confluence’ into outfile ‘/tmp/discad.sql’;
source /tmp/discard.sql

执行过程中发现,有20-30个表无法成功。主外键关系
很绝望,一个表一个表分析表结构,很痛苦。
set foreign_key_checks=0 跳过外键检查。
把有问题的表表空间也删掉了。

3、拷贝生产中confulence库下的所有表的ibd文件拷贝到准备好的环境中
select concat(‘alter table ‘,table_schema,’.‘table_name,’ import tablespace;’) from information_schema.tables where table_schema=‘confluence’ into outfile ‘/tmp/import.sql’;

4、验证数据
表都可以访问了,数据挽回到了出现问题时刻的状态(2-8)

案例:
交通口: 核心库  ---抽取----》 违章数据  MySQL 5.6 (有备份,每周六全备,每天做日志增量)
周四下午 , 晚上8:00处理
背景:
1. 环境    : 5.6 版本 ,centos 7 , 两个核心库,数据量300G-400G。
2. 备份策略: 每周六全备,每天做日志增量
3. 故障时间周四下午,晚上20:00 开始处理故障
4. 网上文章,修改参数,误删除 rm -rf  ibdata1 ,数据库再也起不来了。

恢复过程: 
1. 恢复上周六全备,失败了。
原因: 
mysqldump -uroot -p123 -A &> /tmp/full.sql
mysqldump -uroot -p123 -A > /tmp/full.sql  2>/tmp/error.log

处理方法: 注释掉备份中的错误信息。正常恢复。

2. 尝试恢复binlog到故障之前的时间点。
失败了。 
expire_logs_days=3 
结论: 日志中间缺失,无法补偿。放弃这种恢复方案。

3. 尝试使用表空间迁移技术。
具体参照表空间迁移过程。

6.2 内存结构

6.2.1 innodb_buffer_pool

介绍:
InnoDB最大的内存区域,官方建议最多可设置大小物理内存的80%。生产建议70%以下。
作用:
缓冲数据页、索引页、数据字典、AHI、change buffer 、DW
数据页修改完成之后,会写入到磁盘表空间中。ibd frm ibdata1文件。
参数:
mysql> select @@innodb_buffer_pool_size;

6.2.2 innodb_log_buffer

介绍:
用来存储内存数据页的变化。数据修改完成之后,会将日志写入到磁盘日志文件中(ib_logfileN)。
参数:
mysql> select @@innodb_log_buffer_size;

晚上作业:
作业1 :
使用工具从frm文件中取出建表语句,实现表空间迁移。
https://pdf.us/2019/01/10/2620.html
作业2:
https://www.jianshu.com/p/898d2e4bd3a7

你可能感兴趣的:(DBA)