当前位置: 首页 > 科技观察

从输入SQL到返回数据,到底发生了什么?

时间:2023-03-21 16:30:57 科技观察

SQL执行流程其实一个SQL从输入到返回数据的过程大致是这样的:建立连接,分析SQL,优化SQL,执行SQL。建立连接在我们向MySQL发送SQL之前,我们会输入帐号和密码来与MySQL建立连接。这部分工作实际上是由MySQL连接器处理的。连接器负责与客户端建立连接、获取权限、维护和管理连接。当我们使用管理员账户修改账户权限时,现有的连接权限不会受到影响,只有新建的连接才会使用新的权限设置。我们可以通过showprocesslist命令查看当前的连接状态,如下图所示。上图中的Command一栏显示Sleep有几个空闲连接。如果客户端长时间不移动,连接器会自动断开。该参数由wait_timeout控制,默认为8小时。分析SQL在MySQL8.0之前,当MySQL得到一个查询请求时,首先会去查询缓存中查看是否被检查过。如果是,则直接返回缓存的结果。但是8.0版本之后直接去掉了查询缓存功能。主要是因为查询缓存弊大于利。因为只要更新一个表,这个表上的查询缓存就会被清空。也许你只是缓存了结果,当一个更新操作到来时,所有这些缓存都会失效。因此,查询缓存适用于不经常更新的表,以提高查询效率。MySQL得到SQL后,会对SQL进行词法分析和语法分析。词法分析会分析每个词的意思,而语法分析则是分析语法是否正确。分析器会先进行词法分析,再进行语法分析。你输入的是一个由多个字符串和空格组成的SQL语句。MySQL需要识别其中的字符串是什么以及它们代表什么。例如:select表示查询,t表示t表,字符串ID识别为列ID。词法分析完成后,将进行语法分析。语法分析器根据词法分析的结果,根据语法规则判断输入的SQL语句是否满足MySQL语法。如果语法不满足,会有“YouhaveanerrorinyourSQLsyntax”的错误提示。优化SQL经过分析器,MySQL知道你要做什么。但是在开始执行之前,还得经过优化器的处理。当表中有多个索引时,优化器决定使用哪个索引。或者当一条语句有多个表关联(join)时,确定每个表的连接顺序。有时两种执行方式的逻辑结果是一样的,但是执行效率会不同,优化器的作用就是决定采用哪种方案。优化器阶段完成后,确定这条语句的执行计划,然后进入执行器阶段。执行SQLMySQL通过分析器知道你要做什么,通过优化器知道你要做什么,于是进入执行器阶段,开始执行语句。在开始执行的时候,首先要判断自己是否有对这张表T执行查询的权限,如果没有,会返回没有权限的错误。如果有权限,打开表继续执行。打开表时,执行器会根据表的引擎定义使用引擎提供的接口。例如语句select*fromTwhereID=10;,id字段没有索引,那么executor的执行过程如下:调用InnoDB引擎接口取这张表的第一行,判断ID值是否为10,如果不是,则跳过,如果是,则将该行存入结果集中。调用引擎接口取“下一行”,重复相同的判断逻辑,直到取到表的最后一行。执行器将上述遍历过程中满足条件的所有行组成的记录集作为结果集返回给客户端。至此,这条语句执行完毕。对于有索引的表,执行逻辑类似。首先调用的是“获取满足条件的第一行”接口,然后循环获取“满足条件的下一行”接口。这些接口已经在引擎中定义。你会在数据库的慢查询日志中看到一个rows_examined字段,表示在executor执行过程中该语句扫描了多少行。每次执行程序调用引擎获取数据行时都会累积此值。在某些场景下,执行器被调用一次,在引擎内部扫描多行,因此引擎扫描的行数与rows_examined并不完全相同。MySQL技术架构其实上面的流程是基于MySQL的技术架构,其技术架构如下图所示。一般来说,MySQL的技术架构可以分为两部分:服务器层和存储引擎层。Server层负责建立连接、解析SQL等功能。所有跨存储引擎的功能都在这一层实现,如存储过程、触发器、视图等。存储引擎层负责数据的存储和检索。其架构模型为插件式,支持InnoDB、MyISAM、Memory等多种存储引擎。现在最常用的存储引擎是InnoDB存储引擎,它从MySQL5.5.5开始成为了默认的存储引擎。InnoDB存储引擎是目前使用最广泛的InnoDB存储引擎。它的架构分为三个部分:后台线程、内存池和文件。其架构如下图所示。InnoDB存储引擎架构上图中,后台线程负责刷新内存池中的数据,内存池负责将数据缓存在磁盘上,文件是具体的数据存储。后台线程的主要工作是刷新内存池中的数据,保证缓冲池中的内存缓存是最新的数据。InnoDB存储引擎是多线程模型,所以后台有多个不同的后台线程,分别负责处理不同的任务。目前有4种不同类型的处理线程,分别是:MasterTread、IOThread、PurgeThread和PageCleanerThread。内存池是InnoDB管理的内存的总称,主要用于缓存磁盘数据,加快数据读取速度。根据其用途,内存池也可以分为三个部分:缓冲池、重做日志缓冲区和附加内存池。文件是数据库数据最终被访问的地方,存放着相关的数据文件,包括索引文件和数据文件。小结最后总结一下一条SQL语句从查询到返回数据的四个阶段,即:建立连接。客户端首先会与MySQL建立TCP连接,在连接器中进行连接管理、权限验证等操作。分析SQL。分析器执行词法和语法分析。词法分析知道要查询什么,语法分析判断语法是否有问题。优化SQL。优化器根据SQL的情况判断哪种执行方式更好,比如使用哪种索引,使用哪种表连接方式。执行SQL。优化器根据优化结果生成执行计划,执行器调用存储引擎的API执行查询,最终将数据返回给客户端。