204 lines
6.5 KiB
Plaintext
204 lines
6.5 KiB
Plaintext
# ==== Purpose ====
|
|
# Like rpl_atomic_ddl.test this test file
|
|
# proves successful slave service recovery after a simulated failure
|
|
# at handling recoverable DDL queries.
|
|
# The "half" atomic cases include those DDL statements that can not
|
|
# roll back. Once this feature is implemented for a statement it can
|
|
# merged with the fully atomic ones of rpl_atomic_ddl.test.
|
|
# See rpl_atomic_ddl.test for more info.
|
|
#
|
|
# ==== Implementation ====
|
|
#
|
|
# Mostly follows rpl_atomic_ddl.test.
|
|
# Difference is in that the slave does not try to simulate
|
|
# a failure before binary logging stage has been completed. That is
|
|
# only SET @@GLOBAL.debug="+d,crash_commit_after_log" and
|
|
# pre_binlog_check, see below commented, is not used.
|
|
#
|
|
# ==== References ====
|
|
# WL#9175 Correct recovery of DDL statements/transactions by binary log
|
|
#
|
|
#
|
|
# Params:
|
|
# --let $rpl_atomic_ddl_print_verbose # get out more info
|
|
#
|
|
# === Limitations ===
|
|
# --force-restart is required to run the test.
|
|
#
|
|
# When the object deletion was interrupted by crash
|
|
# there could be errors on object recreation attempt like
|
|
# 1007: Can't create database '...'; database exists
|
|
# due to
|
|
# Bug #25663287 DROP DATABASE DOESN'T GETS RECOVERED CORRECTLY UPON POST BINLOG CRASH/RESTART
|
|
# or asserts like in
|
|
# Bug #25651042 TANSACTION DOES NOT POST-CRASH RECOVER IN INNODB EVEN IF PREPARED AND BINLOGGED
|
|
#
|
|
|
|
--let $rpl_atomic_ddl_print_verbose=1
|
|
|
|
--source include/not_crashrep.inc
|
|
--source include/not_valgrind.inc
|
|
--source include/have_log_bin.inc
|
|
--source include/have_debug.inc
|
|
--source include/have_binlog_format_mixed.inc
|
|
--let $rpl_gtid_utils= 1
|
|
--source include/master-slave.inc
|
|
|
|
--source include/rpl_connection_slave.inc
|
|
call mtr.add_suppression("The slave coordinator and worker threads are stopped");
|
|
call mtr.add_suppression("Slave worker thread has failed to apply an event");
|
|
call mtr.add_suppression("Error writing relay log configuration");
|
|
call mtr.add_suppression("Table 't_2' already exists");
|
|
call mtr.add_suppression("Operating system error number .* in a file operation");
|
|
call mtr.add_suppression("Cannot open datafile for read-onl");
|
|
call mtr.add_suppression("The error means the system cannot");
|
|
--disable_query_log
|
|
call mtr.add_suppression("You need to use --log-bin to make.* work");
|
|
call mtr.add_suppression("Could not find a valid tablespace file for");
|
|
--enable_query_log
|
|
|
|
--source include/rpl_connection_master.inc
|
|
|
|
# instructing gtid_step_assert that is called by a sourced file
|
|
# to satisfy to gtid-mode OFF as well.
|
|
--let $gtid_mode_on= `SELECT @@GLOBAL.GTID_MODE = 'ON'`
|
|
--let $gtid_mode= `SELECT @@GLOBAL.GTID_MODE`
|
|
--let $gtid_step_gtid_mode_agnostic=`SELECT '$gtid_mode' != 'ON'`
|
|
|
|
if (!$crash_commit)
|
|
{
|
|
--let $commit_message=Crash right after the query has been binary-logged before committed in the engine
|
|
--let $crash_commit="+d,crash_commit_after_log"
|
|
}
|
|
|
|
|
|
# Master load
|
|
#
|
|
# Start off with the master side logger table (see the master opt
|
|
# file) that record DDL queries that will be subject to crash
|
|
# simulation on the slave side. The table will hold prescribed
|
|
# post-recovery checks to be performed on the slave side.
|
|
#
|
|
--let $master_log_table=t_checks
|
|
--let $master_log_db=master_db
|
|
--eval CREATE DATABASE $master_log_db
|
|
|
|
--let $save_curr_db=`SELECT database()`
|
|
--eval USE $master_log_db
|
|
--eval CREATE TABLE IF NOT EXISTS $master_log_table (id INT AUTO_INCREMENT NOT NULL PRIMARY KEY, ddl_query TEXT, pre_binlog_check TEXT, post_binlog_check TEXT);
|
|
|
|
--eval USE $save_curr_db
|
|
|
|
--source include/sync_slave_sql_with_master.inc
|
|
--source include/stop_slave_sql.inc
|
|
|
|
--source include/rpl_connection_master.inc
|
|
|
|
#
|
|
# The test
|
|
#
|
|
|
|
# I. Load generation on master:
|
|
|
|
--let $do_post_prepare=0
|
|
--let $do_post_binlog=0
|
|
--let $do_only_regular_logging=1
|
|
--let $do_show_binlog_events= 0
|
|
--let $do_count_queries=1
|
|
--let $count_ddl_queries=0
|
|
# table name to use by the sourced file below and on this level
|
|
--let $table=t_2
|
|
--source extra/binlog_tests/binlog_ddl_half_atomic.inc
|
|
|
|
--source include/rpl_connection_slave.inc
|
|
--source include/start_slave_io.inc
|
|
|
|
--source include/rpl_connection_master.inc
|
|
--source include/sync_slave_io_with_master.inc
|
|
|
|
# The receiver thread must be stopped now which
|
|
# crash-safely memorizes the last received event coordinates.
|
|
--source include/rpl_connection_slave.inc
|
|
--source include/stop_slave_io.inc
|
|
|
|
# II. Event execution on slave interrupted by errors
|
|
|
|
#--source include/rpl_connection_slave.inc
|
|
# First, a regular error
|
|
--eval CREATE TABLE $table (a int)
|
|
START SLAVE SQL_THREAD;
|
|
--let $slave_sql_errno=convert_error(ER_TABLE_EXISTS_ERROR)
|
|
--source include/wait_for_slave_sql_error.inc
|
|
--eval DROP TABLE $table
|
|
|
|
# The rest is crash-restart in loop of number of DDL queries
|
|
# in the master load.
|
|
--let $loops=$count_ddl_queries
|
|
--let $id=0
|
|
while ($loops)
|
|
{
|
|
--inc $id
|
|
|
|
# Find the loop's query and it post-recovery checks upon the first recovery
|
|
--source include/rpl_connection_master.inc
|
|
|
|
--let $current_query=`SELECT ddl_query FROM $master_log_db.$master_log_table WHERE id = $id `
|
|
#--let $pre_binlog_check=`SELECT pre_binlog_check FROM $master_log_db.$master_log_table WHERE id = $id`
|
|
--let $post_binlog_check=`SELECT post_binlog_check FROM $master_log_db.$master_log_table WHERE id = $id`
|
|
if ($rpl_atomic_ddl_print_verbose)
|
|
{
|
|
--echo Loop: $id out of $count_ddl_queries; current query: '$current_query'; pre-binlog check: '$pre_binlog_check'; pre-commit check: '$post_binlog_check';
|
|
}
|
|
|
|
--source include/rpl_connection_slave.inc
|
|
#
|
|
# Commit recovery upon the pre-commit crash.
|
|
#
|
|
--source include/expect_crash.inc
|
|
--echo *** Query: '$current_query'. $commit_message. ***
|
|
--eval SET @@GLOBAL.debug=$crash_commit
|
|
--source include/gtid_step_reset.inc
|
|
--error 0,2013
|
|
START SLAVE SQL_THREAD;
|
|
|
|
# Server wait for stop and restart
|
|
--enable_reconnect
|
|
--source include/wait_until_disconnected.inc
|
|
--let $rpl_server_number= 2
|
|
--source include/rpl_start_server.inc
|
|
--disable_reconnect
|
|
|
|
--source include/rpl_connection_slave.inc
|
|
# Proof of the commit recovery is one committed gtid
|
|
--let $gtid_step_only_count=1
|
|
--let $gtid_step_count=1
|
|
--source include/gtid_step_assert.inc
|
|
|
|
# Proof by the master side post-recovery checks
|
|
if ($post_binlog_check)
|
|
{
|
|
if (!`$post_binlog_check`)
|
|
{
|
|
--echo *** State check upon recovery after the pre-commit crash fails ***
|
|
--die
|
|
}
|
|
}
|
|
|
|
--dec $loops
|
|
} # end of while
|
|
|
|
# Eventually:
|
|
|
|
--source include/rpl_connection_slave.inc
|
|
--source include/start_slave.inc
|
|
|
|
--source include/rpl_connection_master.inc
|
|
--eval DROP DATABASE $master_log_db
|
|
|
|
--source include/sync_slave_sql_with_master.inc
|
|
|
|
|
|
--source include/rpl_end.inc
|
|
|
|
|