首页 > 数据库 >由mysql rewrite插件带来的8.0升级问题及解决方案

由mysql rewrite插件带来的8.0升级问题及解决方案

时间:2023-08-15 17:25:42浏览次数:42  
标签:8.0 插件 rewrite MY 08 mysql proc

一、问题发生

在客户现场遇到一个语句,走mysql的执行计划,总是不能达到预期的join顺序,需手动执行straight join。为了让sql能够自动转换,想到了5.7开始支持的rewriter plugin,于是在测试环境测试了一把(结果发现只能做一些简单的查询重写,稍微复杂的多表关联,总是匹配不成功,这个按下不表,后续再进行学习分享)。测试完成后,准备升级到8.0版本,看看8.0有没有新的特性支持。然而升级启动时,却没有启动成功,error log中打印内容如下:

1 [ERROR] [MY-013235] [Server] Error in parsing Routine 'query_rewrite'.'flush_rewrite_rules' during upgrade. You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'QUERY CACHE;   IF NOT message_text IS NULL THEN     SIGNAL SQLSTATE '45000' SET ' at line 6
View Code

根据错误提示,在解析存储过程'query_rewrite'.'flush_rewrite_rules'的时候报错,然后更新数据字典错误,实例无法启动。这很容易想到刚刚安装的rewrite插件,查看安装插件执行过的脚本(/usr/local/mysql5.7/share/install_rewriter.sql),得到这个存储过程定义:

1 CREATE PROCEDURE query_rewrite.flush_rewrite_rules()
2 BEGIN
3   DECLARE message_text VARCHAR(100);
4   COMMIT;
5   SELECT load_rewrite_rules() INTO message_text;
6   RESET QUERY CACHE;
7   IF NOT message_text IS NULL THEN
8     SIGNAL SQLSTATE '45000' SET MESSAGE_TEXT = message_text;
9   END IF;
View Code

其中有一个命令,“RESET QUERY CACHE”,这个命令是从query cache中删除所有查询结果。而query cache在8.0版本已经不在支持。我们可以看到8.0版本的rewriter 这个脚本的定义删除了这个命令(/usr/local/mysql8.0/share/install_rewriter.sql):

1 CREATE PROCEDURE query_rewrite.flush_rewrite_rules()
2 BEGIN
3   DECLARE message_text VARCHAR(100);
4   COMMIT;
5   SELECT load_rewrite_rules() INTO message_text;
6   IF NOT message_text IS NULL THEN
7     SIGNAL SQLSTATE '45000' SET MESSAGE_TEXT = message_text;
8   END IF;
View Code

到此,似乎找到了问题的症结,即由于8.0中去除了query cache,无法升级rewriter的存储过程。但是怎么让实例继续往下升级,然后完成启动呢?

二、思考过程

起初,我没有仔细看报错,虽然知道是存储过程出了问题,但是实例无法启动,也没法修改或者卸载rewriter插件,于是抱着侥幸,测试了innodb_force_recovery,没有效果。

关闭rewriter_enabled参数也没有效果。

然后,我想之前修改密码时用过--init-file参数,可以通过指定--init-file=/usr/local/mysql5.7/share/uninstall_rewriter.sql来让mysqld启动时先卸载rewriter插件,再升级,这个过程不生效(报错的时候还没走到server启动)。

想来想去,似乎没法搞了,有点迷茫。当天没有再处理。

今天上午,我又想了歪招,既然是存储过程出的问题,而存储过程又存在mysql.proc表,proc表是个MyISAM表,是否可以通过工具来修改,不过搜了一下,貌似只有去分析FRM文件的工具,没有修改MYD的,于是放弃了。

三、解决

就在把焦点聚集到proc表,又没法改动的时候,我想起来,如果把当前的proc数据文件替换回没有安装过rewriter插件的5.7版本的呢。于是赶紧去查了下,果然,果然我的测试环境还有2个没有升级8.0,幸存的5.7.40!

对比了下,当前的proc和标准的proc差别:

1 ----添加插件前
2 -rw-r-----. 1 mysql mysql   9996 Mar 28 17:52 proc.frm
3 -rw-r-----. 1 mysql mysql 301604 Aug 15 14:35 proc.MYD
4 -rw-r-----. 1 mysql mysql   4096 Aug 15 14:35 proc.MYI
5 ---添加插件后
6 -rw-r-----. 1 mysql mysql   9996 Mar 16 17:22 proc.frm
7 -rw-r-----. 1 mysql mysql 301916 Aug 14 15:20 proc.MYD
8 -rw-r-----. 1 mysql mysql   4096 Aug 14 17:02 proc.MYI
View Code

于是把差异的proc.MYD同步到有问题的实例数据目录,再次启动,升级成功了:

 1 2023-08-15T15:04:52.981022+08:00 1 [Note] [MY-011088] [Server] Data dictionary initializing version '80023'.
 2 2023-08-15T15:05:02.565119+08:00 1 [Note] [MY-010337] [Server] Created Data Dictionary for upgrade
 3 2023-08-15T15:05:02.733144+08:00 0 [Warning] [MY-010918] [Repl] 'rpl_semi_sync_master' is deprecated and will be removed in a future release. Please use rpl_semi_sync_source instead.
 4 2023-08-15T15:05:02.733362+08:00 0 [Note] [MY-011130] [Repl] Semi-sync replication initialized for transactions.
 5 2023-08-15T15:05:02.733389+08:00 0 [Note] [MY-011142] [Repl] Semi-sync replication enabled on the master.
 6 2023-08-15T15:05:02.734599+08:00 0 [Note] [MY-011166] [Repl] Starting ack receiver thread.
 7 2023-08-15T15:05:02.734875+08:00 0 [Warning] [MY-010918] [Repl] 'rpl_semi_sync_slave' is deprecated and will be removed in a future release. Please use rpl_semi_sync_replica instead.
 8 2023-08-15T15:05:08.250726+08:00 2 [System] [MY-011003] [Server] Finished populating Data Dictionary tables with data.
 9 2023-08-15T15:05:08.254884+08:00 2 [Note] [MY-011008] [Server] Finished migrating TABLE statistics data.
10 2023-08-15T15:05:08.265917+08:00 2 [Note] [MY-011008] [Server] Finished migrating TABLE statistics data.
11 2023-08-15T15:05:08.900125+08:00 2 [Note] [MY-010006] [Server] Using data dictionary with version '80023'.
View Code

四、总结

搜索问题的时候,发现mysql讨论组也有发过类似的升级问题https://forums.mysql.com/read.php?20,686560,686560#msg-686560,没有提到解决方法。我刚遇到时,也是不知道如何是好,似乎实例要重做了(绝望时,我还提了bug:https://bugs.mysql.com/bug.php?id=112067&thanks=4,哈哈,这应该在官方不认为是一个bug,而是升级前没有认真检查~)。

还好没有放弃,最后的解决方式也是一种临时的对应策略。通过这次处理过程,发现自己存在如下问题:

1. 对8.0的升级不够熟悉,升级前以为in-place方式原地升级,替换下软件包,重启自动升级就完事了,殊不知5.7到8.0的功能变化,需要提前做好检测,避免8.0不再支持的功能导致升级失败,mysql官方地址:https://dev.mysql.com/doc/refman/8.0/en/upgrade-prerequisites.html 也可以通过mysql-shell工具提前检测下是否满足升级8.0的条件。

2.原理还是不够深入,操作没有细节把控,这块要加强学习总结能力。

标签:8.0,插件,rewrite,MY,08,mysql,proc
From: https://www.cnblogs.com/dbthinkinglab/p/17631559.html

相关文章

  • Day25(2023.08.09)
    行程8:45    到达上海市信息安全测评认证中心(黄浦区陆家浜路1308号)9:00  Linux核查11:30--13:00   吃饭休息13:00 Linux核查17:00      下班    其中/etc/passwd/etc/hosts.equiv/etc/login.defs/etc......
  • 微信ipad协议8.0.40 加好友功能
    友情链接:geweapi.com点击即可访问!好友请求验证小提示:v_3 v_4可以参考搜索接口请求URL:http://域名地址/api/contacts/verifyuser请求方式:POST请求头:Content-Type:application/jsonX-GEWE-TOKEN:后台获取参数:参数名必填数据类型说明appid是string设备idconfig否object其他配置......
  • EXP 一款 Java 插件化热插拔框架
    EXP一款Java插件化热插拔框架前言多年以来,ToB的应用程序都面临定制化需求应该怎么搞的问题。举例,大部分本地化软件厂家,都有一个标准程序,这个程序支持大部分企业的功能需求,但面对世界500强等大客户时,他们的特殊需求,厂家通常是无法拒绝的(通常因为订单大,给的多,可背书)。比如......
  • mybatis 插件
    插件的使用1、在配置文件配置plugins<plugins><plugininterceptor="com.test.plugin.MyBatisInterceptor"></plugin>...</plugins>2、拦截器开发实现Interceptor接口,在对应的拦截器类上配置注解,指定拦截方法@Intercepts(@Signature(type=Executor.cl......
  • mysql 5.0升级到8.0
    1.替换新的驱动jar包       <dependency>           <groupId>com.mysql</groupId>           <artifactId>mysql-connector-j</artifactId>           <version>8.0.31</version>       </dependency>        ......
  • 8.0 Python 使用进程与线程
    python进程与线程是并发编程的两种常见方式。进程是操作系统中的一个基本概念,表示程序在操作系统中的一次执行过程,拥有独立的地址空间、资源、优先级等属性。线程是进程中的一条执行路径,可以看做是轻量级的进程,与同一个进程中的其他线程共享相同的地址空间和资源。线程和进程都......
  • 8.0 Python 使用进程与线程
    python进程与线程是并发编程的两种常见方式。进程是操作系统中的一个基本概念,表示程序在操作系统中的一次执行过程,拥有独立的地址空间、资源、优先级等属性。线程是进程中的一条执行路径,可以看做是轻量级的进程,与同一个进程中的其他线程共享相同的地址空间和资源。线程和进程都可......
  • 【程序员高阶工具】idea自带的http客户端插件使用
    idea自带的http客户端插件使用一.前言http客户端的工具还是很多的,如postman,jmeter,apifox等。其中jmeter只支持本地,如果多成员间需要协作,需要进行文件传输,较为繁琐。postman和apifox,更方便进行用户间共享,但是这些工具的使用,需要打开第三方软件,从研发人员的角度不是很简便。目......
  • 修改审计插件源码编译mariadb获取审计插件
    环境:OS:Centos7mariadb:10.4.29背景:mysql5.7.35版本之后就不能使用mariadb自带的审计插件(windows版本的除外),需要修改源码文件重新编译获取审计插件 1.安装编译所需依赖#yuminstall-yopenssllibssl-devbuild-essentialbisonlibncurses-devcmakegcc-gcc+gitnc......
  • Ubuntu18.04 配置
    一、环境系统:ubuntu-18.04.6-desktop-amd64.isoVMware:17二、SSH服务1.更新源2.安装openssh3.配置sshgedit1vi/etc/apt/sources.list23debhttps://mirrors.tuna.tsinghua.edu.cn/ubuntu/bionicmainrestricteduniversemultiverse4debhttps://mirrors.tuna.ts......