MySQL逻辑架构

在执行下面这个查询语句时,如:

 mysql> select * from t where ID=1;

我们看到的只是输入一条语句,返回一行执行结果,却不知道这条语句在 MySQL内部的执行过程。

MySQL逻辑架构

MySQL 可以分为 Server 层和存储引擎层两部分。

MySQL逻辑架构

Server 层包括连接器、查询缓存、分析器、优化器、执行器等,涵盖 MySQL 的大多数核心服 务功能,以及所有的内置函数(如日期、时间、数学和加密函数等),所有跨存储引擎的功能都 在这一层实现,比如存储过程、触发器、视图等。

存储引擎层负责数据的存储和提取。其架构模式是插件式的,如InnoDB、MyISAM、 Memory 等存储引擎。

Server 层

连接器

客户端或程序连接数据库就是与连接器打交道,连接器负责跟客户端建立连 接、获取权限、维持和管理连接。

可以使用以下命令查询连接情况。

show processlist

其中的 Command 列显示 为“Sleep”的这一行,就表示现在系统里面有一个空闲连接。客户端如果太长时间没动静,连接器就会自动将它断开。这个时间是由参数 wait_timeout 控制 的,默认值是 8 小时。

查询缓存

MySQL 拿到一个查询请求后,会先到查询缓存看看,之前是不是执行过这条语句。之前执行过 的语句及其结果可能会以 key-value 对的形式,被直接缓存在内存中。key 是查询的语句, value 是查询的结果。如果你的查询能够直接在这个缓存中找到 key,那么这个 value 就会被直 接返回给客户端。如果语句不在查询缓存中,就会继续后面的执行阶段。执行完成后,执行结果会被存入查询缓存 中。

要使用查询缓存,为什么呢?因为查询缓存往往弊大于利。对于更新压力大的数据库 来说,查询缓存的命中率会非常低。

MySQL 8.0 版本直接将查询缓存的整块功能删除了。

分析器

MySQL 需要知道sql要做什么,因此 需要对 SQL 语句做解析。

优化器

经过了分析器,MySQL 就知道sql要做什么了。在开始执行之前,还要先经过优化器的处理。

优化器是在表里面有多个索引的时候,决定使用哪个索引;或者在一个语句有多表关联(join) 的时候,决定各个表的连接顺序。优化器阶段完成后,这个语句的执行方案就确定下来了。

执行器

MySQL 通过分析器知道了sql要做什么,通过优化器知道了sql该怎么做,于是就进入了执行器阶 段,开始执行语句。

日志模块

redo log(重做日志)

Mysql如果每一次的更新操作都需要写进磁盘,然后磁盘也要找到 对应的那条记录,然后再更新,整个过程 IO 成本、查找成本都很高。

当Mysql有一条记录需要更新的时候,InnoDB 引擎就会先把记录写到 redo log里面,并更新内存,这个时候更新就算完成了。同时,InnoDB 引擎会在适当的时候,将这个操作记录更新到磁盘里面,而这个更新往往是在系统比较空闲的时候做。InnoDB 的 redo log 是固定大小的,如果redo log 满了,这时候不能再执行新的更新,得停下来先擦 掉一些记录,把 checkpoint 推进一下写入磁盘。有了 redo log,InnoDB 就可以保证即使数据库发生异常重启,之前提交的记录都不会丢失, 这个能力称为crash-safe。

binlog(归档日志)

redo log 是 InnoDB 引擎特有的日志,而 Server 层也有自己的日志,称为 binlog(归档日志)。

1、redo log 是 InnoDB 引擎特有的;binlog 是 MySQL 的 Server 层实现的,所有引擎都可 以使用。

2.、redo log 是物理日志,记录的是“在某个数据页上做了什么修改”;binlog 是逻辑日志, 记录的是这个语句的原始逻辑,比如“给 ID=2 这一行的 c 字段加 1 ”。

3、redo log 是循环写的,空间固定会用完;binlog 是可以追加写入的。“追加写”是指 binlog 文件写到一定大小后会切换到下一个,并不会覆盖以前的日志。

两阶段提交

 “两阶段提交”是为了让两份日志之间的逻辑一致。

MySQL逻辑架构

数据恢复过程

比如某天下午两点发现中午十二点有一次误删表,需要找回数 据,那你可以这么做: 首先,找到最近的一次全量备份,如果你运气好,可能就是昨天晚上的一个备份,从这个备 份恢复到临时库;

然后,从备份的时间点开始,将备份的 binlog 依次取出来,重放到中午误删表之前的那个时 刻。

这样你的临时库就跟误删之前的线上库一样了,然后你可以把表数据从临时库取出来,按需要恢 复到线上库去。

参数配置

innodb_flush_log_at_trx_commit 这个参数设置成 1 的 时候,表示每次事务的 redo log 都直接持久化到磁盘。这个参数建议你设置成 1,这样可以 保证 MySQL 异常重启之后数据不丢失。

sync_binlog 这个参数设置成 1 的时候,表示每次事务的 binlog 都持久化到磁盘。这个参数也建议你设置成 1,这样可以保证 MySQL 异常重启之后 binlog 不丢失。

 

关注公众号,发送 yys 获取《云原生架构白皮书》。

MySQL逻辑架构

 

上一篇:alert日志中出现Private Strand Flush Not Complete的处理方法


下一篇:MySQL 重要参数 innodb_flush_log_at_trx_commit 和 sync_binlog