mirror of
https://github.com/MariaDB/server.git
synced 2025-01-30 18:41:56 +01:00
969669767b
The root cause is the WAL logging of file operation when the actual operation fails afterwards. It creates a situation with a log entry for a operation that would always fail. I could simulate both the backup scenario error and Innodb recovery failure exploiting the weakness. We are following WAL for file rename operation and once logged the operation must eventually complete successfully, or it is a major catastrophe. Right now, we fail for rename and handle it as normal error and it is the problem. I created a patch to address RENAME operation to a non existing schema where the destination schema directory is missing. The patch checks for the missing schema before logging in an attempt to avoid the failure after WAL log is written/flushed. I also checked that the schema cannot be dropped or there cannot be any race with other rename to the same file. This is protected by the MDL lock in SQL today. The patch should this be a good improvement over the current situation and solves the issue at hand.
50 lines
1.4 KiB
Text
50 lines
1.4 KiB
Text
--source include/have_innodb.inc
|
|
--source include/not_embedded.inc
|
|
|
|
CREATE DATABASE test_jfg;
|
|
CREATE DATABASE test_jfg2;
|
|
CREATE TABLE test_jfg.test (a int unsigned PRIMARY KEY) ENGINE=InnoDB;
|
|
RENAME TABLE test_jfg.test TO test_jfg2.test;
|
|
|
|
SELECT REPLACE(path,'\\','/') path
|
|
FROM INFORMATION_SCHEMA.INNODB_SYS_DATAFILES WHERE PATH LIKE '%test%';
|
|
|
|
DROP DATABASE test_jfg;
|
|
|
|
--source include/restart_mysqld.inc
|
|
|
|
DROP DATABASE test_jfg2;
|
|
|
|
CREATE DATABASE abc_def;
|
|
CREATE DATABASE abc_def2;
|
|
|
|
CREATE TABLE abc_def.test (a int unsigned PRIMARY KEY) ENGINE=InnoDB;
|
|
RENAME TABLE abc_def.test TO abc_def2.test1;
|
|
|
|
SELECT REPLACE(path,'\\','/') path
|
|
FROM INFORMATION_SCHEMA.INNODB_SYS_DATAFILES WHERE PATH LIKE '%test%';
|
|
|
|
DROP DATABASE abc_def;
|
|
|
|
--source include/restart_mysqld.inc
|
|
|
|
DROP DATABASE abc_def2;
|
|
|
|
call mtr.add_suppression("InnoDB: Cannot rename '.*t1.ibd' to '.*non_existing_db.*' because the target schema directory doesn't exist");
|
|
|
|
CREATE TABLE t1 (a INT) ENGINE=InnoDB;
|
|
INSERT INTO t1 VALUES(100);
|
|
--replace_result "\\" "/"
|
|
--error ER_ERROR_ON_RENAME
|
|
RENAME TABLE t1 TO non_existing_db.t1;
|
|
|
|
--let SEARCH_PATTERN= \[ERROR\] InnoDB: Cannot rename '.*t1\.ibd' to '.*non_existing_db
|
|
let SEARCH_FILE= $MYSQLTEST_VARDIR/log/mysqld.1.err;
|
|
--source include/search_pattern_in_file.inc
|
|
|
|
SET GLOBAL innodb_fast_shutdown=2;
|
|
--source include/restart_mysqld.inc
|
|
|
|
SELECT * FROM t1;
|
|
# Cleanup
|
|
DROP TABLE t1;
|