diff --git a/maxscale-system-test/CMakeLists.txt b/maxscale-system-test/CMakeLists.txt index 615a919a9..27ec1d99f 100644 --- a/maxscale-system-test/CMakeLists.txt +++ b/maxscale-system-test/CMakeLists.txt @@ -632,6 +632,9 @@ add_test_executable(avro_alter.cpp avro_alter avro LABELS avrorouter binlogroute # In the binlog router setup stop Master and promote one of the Slaves to be new Master add_test_executable(binlog_change_master.cpp binlog_change_master setup_binlog_tx_safe LABELS binlogrouter BREAKS_REPL) +# In the binlog router setup stop Master and promote one of the Slaves to be new Master (use GTID) +add_test_executable(binlog_change_master.cpp binlog_change_master_gtid setup_binlog_tx_safe_gtid LABELS binlogrouter BREAKS_REPL) + # trying to start binlog setup with incomplete Maxscale.cnf add_test_executable(binlog_incompl.cpp binlog_incompl binlog_incompl LABELS binlogrouter BREAKS_REPL) @@ -672,14 +675,17 @@ add_test_executable(mxs781_binlog_wrong_passwrd.cpp mxs781_binlog_wrong_passwrd # Regression case for crash if long host name is used for binlog router (in 'change master to ...') add_test_executable(mxs813_long_hostname.cpp mxs813_long_hostname setup_binlog LABELS binlogrouter BREAKS_REPL) -# configure binlog rouer setup, execute queries and transactions, check data; +# configure binlog router setup, execute queries and transactions, check data; add_test_executable(setup_binlog.cpp setup_binlog setup_binlog LABELS binlogrouter BREAKS_REPL) -# configure binlog rouer setup, execute queries and transactions, check data; install semysync plugin, backends started with --binlog-checksum=CRC32 option +# configure binlog router setup, execute queries and transactions, check data; +add_test_executable(setup_binlog_gtid.cpp setup_binlog_gtid setup_binlog_gtid LABELS binlogrouter BREAKS_REPL) + +# configure binlog router setup, execute queries and transactions, check data; install semysync plugin, backends started with --binlog-checksum=CRC32 option # disabled because it is included into setup_binlog test, separate test was created for debugging # add_test_executable(setup_binlog_crc_32.cpp setup_binlog_crc_32 setup_binlog LABELS binlogrouter BREAKS_REPL) -# configure binlog rouer setup, execute queries and transactions, check data; install semysync plugin, backends started with --binlog-checksum=NONE option +# configure binlog router setup, execute queries and transactions, check data; install semysync plugin, backends started with --binlog-checksum=NONE option # disabled because it is included into setup_binlog test, separate test was created for debugging # add_test_executable(setup_binlog_crc_none.cpp setup_binlog_crc_none setup_binlog LABELS binlogrouter LIGHT BREAKS_REPL) diff --git a/maxscale-system-test/README.md b/maxscale-system-test/README.md index 1e332b408..6f3314a4b 100644 --- a/maxscale-system-test/README.md +++ b/maxscale-system-test/README.md @@ -65,3 +65,4 @@ System level tests for MaxScale |no_nodes_check|if yes backend checks are not executed (needed in case of RDS or similar backend)| |no_backend_log_copy|if yes logs from backend nodes are not copied (needed in case of RDS or similar backend)| |no_maxscale_start|Do not start Maxscale automatically| +|no_vm_revert|If true tests do not revert VMs after the test even if test failed| diff --git a/maxscale-system-test/binlog_change_master.cpp b/maxscale-system-test/binlog_change_master.cpp index ae6ed077f..c0f5dbae8 100644 --- a/maxscale-system-test/binlog_change_master.cpp +++ b/maxscale-system-test/binlog_change_master.cpp @@ -25,7 +25,7 @@ TestConnections * Test ; int exit_flag; int master = 0; int i_trans = 0; -const int trans_max = 100; +const int trans_max = 300; int failed_transaction_num = 0; /** The amount of rows each transaction inserts */ @@ -78,6 +78,13 @@ int main(int argc, char *argv[]) Test = new TestConnections(argc, argv); Test->set_timeout(3000); + if (strcmp(Test->test_name, "binlog_change_master_gtid") == 0) + { + Test->binlog_master_gtid = true; + Test->binlog_slave_gtid = true; + Test->tprintf("Using GTID\n"); + } + Test->repl->connect(); execute_query(Test->repl->nodes[0], (char *) "DROP TABLE IF EXISTS t1;"); Test->repl->close_connections(); @@ -119,13 +126,12 @@ int main(int argc, char *argv[]) Test->repl->block_node(0); Test->stop_timeout(); - sleep(30); + sleep(180); Test->tprintf("Done! Waiting for thread\n"); exit_flag = 1; pthread_join(transaction_thread_t, NULL ); Test->tprintf("Done!\n"); - Test->tprintf("Checking data on the node3 (slave)\n"); char sql[256]; char rep[256]; @@ -160,7 +166,6 @@ int main(int argc, char *argv[]) } Test->repl->close_connections(); - int rval = Test->global_result; delete Test; return rval; @@ -174,6 +179,12 @@ const char * setup_slave1 = MASTER_LOG_FILE='%s',\ MASTER_LOG_POS=%s,\ MASTER_PORT=%d"; +const char * setup_slave_gtid = + "change master to MASTER_HOST='%s',\ + MASTER_USER='repl',\ + MASTER_PASSWORD='repl',\ + MASTER_PORT=%d, \ + MASTER_USE_GTID=Slave_pos"; int select_new_master(TestConnections * test) @@ -229,7 +240,6 @@ int select_new_master(TestConnections * test) test->tprintf("log file name %s\n", maxscale_log_file); sprintf(maxscale_log_file_new, "%s%06d", maxscale_log_file, pd + 1); - test->try_query(test->repl->nodes[2], (char *) "reset master"); test->tprintf("Flush logs %d times\n", pd + 1); for (int k = 0; k < pd + 1; k++) { @@ -248,12 +258,25 @@ int select_new_master(TestConnections * test) test->add_result(mysql_errno(binlog), "Error connection to binlog router %s\n", mysql_error(binlog)); char str[1024]; - //sprintf(str, setup_slave1, test->repl->IP[2], log_file_new, test->repl->port[2]); - sprintf(str, setup_slave1, test->repl->IP[2], maxscale_log_file_new, "4", test->repl->port[2]); + + if (test->binlog_master_gtid) + { + test->tprintf("Configuring new master with GTID\n"); + sprintf(str, setup_slave_gtid, test->repl->IP[2], test->repl->port[2]); + } + else + { + test->tprintf("Configuring new master with FILE and POS\n"); + //sprintf(str, setup_slave1, test->repl->IP[2], log_file_new, test->repl->port[2]); + sprintf(str, setup_slave1, test->repl->IP[2], maxscale_log_file_new, "4", test->repl->port[2]); + } test->tprintf("change master query: %s\n", str); test->try_query(binlog, str); - + test->tprintf("start slave\n"); test->try_query(binlog, "start slave"); + test->tprintf("start slave one more\n"); + test->try_query(binlog, "start slave"); + test->tprintf("slave started!\n"); test->repl->close_connections(); @@ -305,6 +328,8 @@ void *transaction_thread( void *ptr ) failed_transaction_num = i_trans; Test->tprintf("Closing connection\n"); mysql_close(conn); + Test->tprintf("Waiting for repication\n"); + sleep(15); Test->tprintf("Calling select_new_master()\n"); select_new_master(Test); master = 2; diff --git a/maxscale-system-test/cnf/maxscale.cnf.template.setup_binlog_gtid b/maxscale-system-test/cnf/maxscale.cnf.template.setup_binlog_gtid new file mode 100755 index 000000000..b74cbdbe2 --- /dev/null +++ b/maxscale-system-test/cnf/maxscale.cnf.template.setup_binlog_gtid @@ -0,0 +1,38 @@ +[maxscale] +threads=###threads### +log_warning=1 + +[Binlog_Service] +type=service +router=binlogrouter +user=skysql +passwd=skysql +version_string=5.6.15-log +#router_options=server-id=3,user=repl,password=repl,master-id=1 +router_options=server_id=3,user=repl,password=repl,longburst=500,heartbeat=30,binlogdir=/var/lib/maxscale/Binlog_Service,mariadb10_master_gtid=on,mariadb10_slave_gtid=on,transaction_safety=on,mariadb10-compatibility=1 + + +[Binlog Listener] +type=listener +service=Binlog_Service +protocol=MySQLClient +port=5306 + +[CLI] +type=service +router=cli + +[CLI Listener] +type=listener +service=CLI +protocol=maxscaled +#address=localhost +socket=default + +[master] +type=server +address=###node_server_IP_1### +port=###node_server_port_1### +protocol=MySQLBackend + + diff --git a/maxscale-system-test/cnf/maxscale.cnf.template.setup_binlog_tx_safe_gtid b/maxscale-system-test/cnf/maxscale.cnf.template.setup_binlog_tx_safe_gtid new file mode 100755 index 000000000..de234f2b4 --- /dev/null +++ b/maxscale-system-test/cnf/maxscale.cnf.template.setup_binlog_tx_safe_gtid @@ -0,0 +1,41 @@ +[maxscale] +threads=###threads### +log_warning=1 + +[Binlog_Service] +type=service +router=binlogrouter +#servers=master +user=skysql +passwd=skysql +version_string=5.6.15-log +#router_options=server-id=3,user=repl,password=repl,master-id=1 +router_options=server-id=3,user=repl,password=repl,longburst=500,heartbeat=30,binlogdir=/var/lib/maxscale/Binlog_Service,mariadb10_master_gtid=on,mariadb10_slave_gtid=on,transaction_safety=on,mariadb10-compatibility=1 + + + +# +[Binlog Listener] +type=listener +service=Binlog_Service +protocol=MySQLClient +port=5306 + +[CLI] +type=service +router=cli + +[CLI Listener] +type=listener +service=CLI +protocol=maxscaled +#address=localhost +socket=default + +[master] +type=server +address=###node_server_IP_1### +port=###node_server_port_1### +protocol=MySQLBackend + + diff --git a/maxscale-system-test/setup_binlog_gtid.cpp b/maxscale-system-test/setup_binlog_gtid.cpp new file mode 100644 index 000000000..a535a68a6 --- /dev/null +++ b/maxscale-system-test/setup_binlog_gtid.cpp @@ -0,0 +1,48 @@ +/** + * @file setup_binlog_gtid.cpp test of simple binlog router setup + + */ + + +#include +#include "testconnections.h" +#include "maxadmin_operations.h" +#include "sql_t1.h" + +#include "test_binlog_fnc.h" + + +int main(int argc, char *argv[]) +{ + + TestConnections * Test = new TestConnections(argc, argv); + Test->set_timeout(3000); + int options_set = 3; + if (Test->smoke) + { + options_set = 1; + } + + Test->repl->connect(); + execute_query(Test->repl->nodes[0], (char *) "DROP TABLE IF EXISTS t1;"); + Test->repl->close_connections(); + sleep(5); + + Test->binlog_master_gtid = true; + Test->binlog_slave_gtid = true; +// for (int option = 0; option < options_set; option++) + //{ + // Test->binlog_cmd_option = option; + Test->start_binlog(); + test_binlog(Test); + //} + + Test->check_log_err("SET NAMES utf8mb4", false); + Test->check_log_err("set autocommit=1", false); + Test->check_log_err("select USER()", false); + + int rval = Test->global_result; + delete Test; + return rval; +} + diff --git a/maxscale-system-test/test_binlog_fnc.cpp b/maxscale-system-test/test_binlog_fnc.cpp index f76d0aaa0..79d26f0fb 100644 --- a/maxscale-system-test/test_binlog_fnc.cpp +++ b/maxscale-system-test/test_binlog_fnc.cpp @@ -192,7 +192,8 @@ void test_binlog(TestConnections* Test) Test->stop_timeout(); // test SLAVE STOP/START - for (int j = 0; j < 3; j++) + Test->tprintf("test SLAVE STOP/START"); + for (int j = 1; j < 2; j++) { Test->set_timeout(100); Test->repl->connect(); @@ -212,6 +213,9 @@ void test_binlog(TestConnections* Test) { Test->tprintf("FLUSH LOGS on master\n"); execute_query(Test->repl->nodes[0], (char *) "FLUSH LOGS"); + execute_query(Test->repl->nodes[0], (char *) "FLUSH LOGS"); + execute_query(Test->repl->nodes[0], (char *) "FLUSH LOGS"); + execute_query(Test->repl->nodes[0], (char *) "FLUSH LOGS"); } Test->add_result(insert_into_t1(Test->repl->nodes[0], 4), "INSERT into t1 failed\n"); diff --git a/maxscale-system-test/testconnections.cpp b/maxscale-system-test/testconnections.cpp index c858a13ef..487a95814 100644 --- a/maxscale-system-test/testconnections.cpp +++ b/maxscale-system-test/testconnections.cpp @@ -42,7 +42,8 @@ TestConnections::TestConnections(int argc, char *argv[]): no_backend_log_copy(false), use_snapshots(false), verbose(false), rwsplit_port(4006), readconn_master_port(4008), readconn_slave_port(4009), binlog_port(5306), global_result(0), binlog_cmd_option(0), enable_timeouts(true), use_ipv6(false), - no_galera(false) + no_galera(false), binlog_master_gtid(false), binlog_slave_gtid(false), + no_vm_revert(true) { chdir(test_dir); gettimeofday(&start_time, NULL); @@ -271,8 +272,15 @@ TestConnections::~TestConnections() if (global_result != 0 ) { - tprintf("Reverting snapshot\n"); - revert_snapshot((char*) "clean"); + if (no_vm_revert) + { + tprintf("no_vm_revert flag is set, not reverting VMs\n"); + } + else + { + tprintf("Reverting snapshot\n"); + revert_snapshot((char*) "clean"); + } } delete repl; @@ -519,6 +527,12 @@ int TestConnections::read_env() { maxscale::start = false; } + + env = getenv("no_vm_revert"); + if ((env != NULL) && ((strcasecmp(env, "no") == 0) || (strcasecmp(env, "false") == 0) )) + { + no_vm_revert = false; + } } int TestConnections::print_env() @@ -874,6 +888,7 @@ int TestConnections::start_binlog() tprintf("Connecting to all backend nodes\n"); repl->connect(); + tprintf("Stopping everything\n"); for (i = 0; i < repl->N; i++) { execute_query(repl->nodes[i], "stop slave"); @@ -888,18 +903,32 @@ int TestConnections::start_binlog() tprintf("ls binlog data dir on Maxscale node\n"); add_result(ssh_maxscale(true, "ls -la %s/", maxscale_binlog_dir), "ls failed\n"); - tprintf("show master status\n"); - find_field(repl->nodes[0], (char *) "show master status", (char *) "File", &log_file[0]); - find_field(repl->nodes[0], (char *) "show master status", (char *) "Position", &log_pos[0]); - tprintf("Real master file: %s\n", log_file); - tprintf("Real master pos : %s\n", log_pos); + if (binlog_master_gtid) + { + // GTID to connect real Master + tprintf("GTID for connection 1st slave to master!\n"); + try_query(repl->nodes[1], (char *) "stop slave"); + try_query(repl->nodes[1], (char *) "SET @@global.gtid_slave_pos=''"); + sprintf(sys1, "CHANGE MASTER TO MASTER_HOST='%s', MASTER_PORT=%d, MASTER_USER='repl', MASTER_PASSWORD='repl', MASTER_USE_GTID=Slave_pos", + repl->IP[0], repl->port[0]); + try_query(repl->nodes[1], sys1); + try_query(repl->nodes[1], (char *) "start slave"); + } + else + { + tprintf("show master status\n"); + find_field(repl->nodes[0], (char *) "show master status", (char *) "File", &log_file[0]); + find_field(repl->nodes[0], (char *) "show master status", (char *) "Position", &log_pos[0]); + tprintf("Real master file: %s\n", log_file); + tprintf("Real master pos : %s\n", log_pos); - tprintf("Stopping first slave (node 1)\n"); - try_query(repl->nodes[1], (char *) "stop slave;"); - //repl->no_set_pos = true; - repl->no_set_pos = false; - tprintf("Configure first backend slave node to be slave of real master\n"); - repl->set_slave(repl->nodes[1], repl->IP[0], repl->port[0], log_file, log_pos); + tprintf("Stopping first slave (node 1)\n"); + try_query(repl->nodes[1], (char *) "stop slave;"); + //repl->no_set_pos = true; + repl->no_set_pos = false; + tprintf("Configure first backend slave node to be slave of real master\n"); + repl->set_slave(repl->nodes[1], repl->IP[0], repl->port[0], log_file, log_pos); + } tprintf("Starting back Maxscale\n"); add_result(start_maxscale(), "Maxscale start failed\n"); @@ -909,10 +938,24 @@ int TestConnections::start_binlog() add_result(mysql_errno(binlog), "Error connection to binlog router %s\n", mysql_error(binlog)); - repl->no_set_pos = true; - tprintf("configuring Maxscale binlog router\n"); - repl->set_slave(binlog, repl->IP[0], repl->port[0], log_file, log_pos); + if (binlog_master_gtid) + { + // GTID to connect real Master + tprintf("GTID for connection binlog router to master!\n"); + try_query(binlog, (char *) "stop slave"); + try_query(binlog, (char *) "SET @@global.gtid_slave_pos=''"); + sprintf(sys1, "CHANGE MASTER TO MASTER_HOST='%s', MASTER_PORT=%d, MASTER_USER='repl', MASTER_PASSWORD='repl', MASTER_USE_GTID=Slave_pos", + repl->IP[0], repl->port[0]); + try_query(binlog, sys1); + } + else + { + repl->no_set_pos = true; + tprintf("configuring Maxscale binlog router\n"); + repl->set_slave(binlog, repl->IP[0], repl->port[0], log_file, log_pos); + + } // ssl between binlog router and Master if (backend_ssl) { @@ -922,30 +965,48 @@ int TestConnections::start_binlog() tprintf("Configuring Master ssl: %s\n", sys1); try_query(binlog, sys1); } - try_query(binlog, "start slave"); try_query(binlog, "show slave status"); - repl->no_set_pos = false; - - // get Master status from Maxscale binlog - tprintf("show master status\n"); - fflush(stdout); - find_field(binlog, (char *) "show master status", (char *) "File", &log_file[0]); - find_field(binlog, (char *) "show master status", (char *) "Position", &log_pos[0]); - - tprintf("Maxscale binlog master file: %s\n", log_file); - fflush(stdout); - tprintf("Maxscale binlog master pos : %s\n", log_pos); - fflush(stdout); - - tprintf("Setup all backend nodes except first one to be slaves of binlog Maxscale node\n"); - fflush(stdout); - for (i = 2; i < repl->N; i++) + if (binlog_slave_gtid) { - try_query(repl->nodes[i], (char *) "stop slave;"); - repl->set_slave(repl->nodes[i], maxscale_IP, binlog_port, log_file, log_pos); + tprintf("GTID for connection slaves to binlog router!\n"); + tprintf("Setup all backend nodes except first one to be slaves of binlog Maxscale node\n"); + fflush(stdout); + for (i = 2; i < repl->N; i++) + { + try_query(repl->nodes[i], (char *) "stop slave"); + try_query(repl->nodes[i], (char *) "SET @@global.gtid_slave_pos=''"); + sprintf(sys1, "CHANGE MASTER TO MASTER_HOST='%s', MASTER_PORT=%d, MASTER_USER='repl', MASTER_PASSWORD='repl', MASTER_USE_GTID=Slave_pos", + maxscale_IP, binlog_port); + try_query(repl->nodes[i], sys1); + try_query(repl->nodes[i], (char *) "start slave"); + } } + else + { + repl->no_set_pos = false; + + // get Master status from Maxscale binlog + tprintf("show master status\n"); + fflush(stdout); + find_field(binlog, (char *) "show master status", (char *) "File", &log_file[0]); + find_field(binlog, (char *) "show master status", (char *) "Position", &log_pos[0]); + + tprintf("Maxscale binlog master file: %s\n", log_file); + fflush(stdout); + tprintf("Maxscale binlog master pos : %s\n", log_pos); + fflush(stdout); + + tprintf("Setup all backend nodes except first one to be slaves of binlog Maxscale node\n"); + fflush(stdout); + for (i = 2; i < repl->N; i++) + { + try_query(repl->nodes[i], (char *) "stop slave"); + repl->set_slave(repl->nodes[i], maxscale_IP, binlog_port, log_file, log_pos); + } + } + repl->close_connections(); try_query(binlog, "show slave status"); mysql_close(binlog); diff --git a/maxscale-system-test/testconnections.h b/maxscale-system-test/testconnections.h index a7cb095d0..258143f34 100644 --- a/maxscale-system-test/testconnections.h +++ b/maxscale-system-test/testconnections.h @@ -252,11 +252,29 @@ public: */ bool backend_ssl; + /** + * @brief binlog_master_gtid If true start_binlog() function configures Maxscale + * binlog router to use GTID to connect to Master + */ + bool binlog_master_gtid; + + /** + * @brief binlog_slave_gtid If true start_binlog() function configures slaves + * to use GTID to connect to Maxscale binlog router + */ + bool binlog_slave_gtid; + /** * @brief no_galera Do not check, restart and use Galera setup; all Galera tests will fail */ bool no_galera; + /** + * @brief no_vm_revert If true tests do not revert VMs after the test even if test failed + * (use it for debugging) + */ + bool no_vm_revert; + /** * @brief ssl_options string with ssl configuration for command line client */