diff options
27 files changed, 1041 insertions, 90 deletions
diff --git a/mysql-test/include/rpl_events.inc b/mysql-test/include/rpl_events.inc new file mode 100644 index 00000000000..5f4cc3c6985 --- /dev/null +++ b/mysql-test/include/rpl_events.inc @@ -0,0 +1,101 @@ +################################################################## +# Author: Giuseppe, Chuck Bell # +# Date: 17-January-2007 # +# Purpose: To test that event effects are replicated # +# in both row based and statement based format # +################################################################## + +--disable_warnings +DROP EVENT IF EXISTS justonce; +drop table if exists t1,t2; +--enable_warnings + +# first, we need a table to record something from an event + +eval CREATE TABLE `t1` ( + `id` INT(10) UNSIGNED NOT NULL AUTO_INCREMENT, + `c` VARCHAR(50) NOT NULL, + `ts` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE +CURRENT_TIMESTAMP, + PRIMARY KEY (`id`) +) ENGINE=$engine_type DEFAULT CHARSET=utf8; + +INSERT INTO t1 (c) VALUES ('manually'); + +# then, we create the event +CREATE EVENT justonce ON SCHEDULE AT NOW() + INTERVAL 2 SECOND DO INSERT INTo t1 +(c) VALUES ('from justonce'); + +# wait 3 seconds, so the event can trigger +--real_sleep 3 + +# check that table t1 contains something +--echo "in the master" +--enable_info +--replace_column 3 TIMESTAMP +SELECT * FROM t1; +--disable_info + +sync_slave_with_master; +connection slave; + +--echo "in the slave" +--enable_info +--replace_column 3 TIMESTAMP +SELECT * FROM t1; +--disable_info + +# Create an event on the slave and check to see what the originator is. +--disable_warnings +DROP EVENT IF EXISTS test.slave_once; +--enable_warnings + +CREATE EVENT test.slave_once ON SCHEDULE EVERY 5 MINUTE DO +INSERT INTO t1(c) VALUES ('from slave_once'); +SELECT db, name, status, originator FROM mysql.event; + +--disable_warnings +DROP EVENT IF EXISTS test.slave_once; +--enable_warnings + +connection master; + +# BUG#20384 - disable events on slave +DROP EVENT IF EXISTS test.justonce; +CREATE EVENT test.er ON SCHEDULE EVERY 3 SECOND DO +INSERT INTO t1(c) VALUES ('from er'); +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; + +sync_slave_with_master; +connection slave; +--echo "in the slave" +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; + +connection master; +--echo "in the master" +ALTER EVENT test.er ON SCHEDULE EVERY 5 SECOND DO INSERT into t1(c) VALUES ('from alter er'); +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; + +sync_slave_with_master; +connection slave; +--echo "in the slave" +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; + +connection master; +--echo "in the master" +DROP EVENT test.er; +--replace column 8 DATETIME +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; + +--disable_info + +sync_slave_with_master; +connection slave; +--echo "in the slave" +--replace column 8 DATETIME +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; + +--echo "in the master" +connection master; +DROP TABLE t1; + diff --git a/mysql-test/include/rpl_udf.inc b/mysql-test/include/rpl_udf.inc new file mode 100644 index 00000000000..ef20327078e --- /dev/null +++ b/mysql-test/include/rpl_udf.inc @@ -0,0 +1,187 @@ +##################################################################### +# Author: Chuck Bell # +# Date: 2006-12-21 # +# Purpose: To test that UDFs are replicated in both row based and # +# statement based format. This tests work completed in WL#3629. # +# # +# This test is designed to exercise two of the three types of UDFs: # +# 1) UDFs via loadable libraries, and 2) UDFs with a SQL body. # +##################################################################### + +--source include/have_udf.inc + +# +# To run this tests the "sql/udf_example.c" need to be compiled into +# udf_example.so and LD_LIBRARY_PATH should be setup to point out where +# the library are. +# + +connection master; +--disable_warnings +drop table if exists t1; +--enable_warnings + +# +# Test 1) Test UDFs via loadable libraries +# +--echo "*** Test 1) Test UDFs via loadable libraries *** +--echo "Running on the master" +--enable_info +--replace_result $UDF_EXAMPLE_LIB UDF_EXAMPLE_LIB +eval CREATE FUNCTION myfunc_double RETURNS REAL SONAME "$UDF_EXAMPLE_LIB"; +--replace_result $UDF_EXAMPLE_LIB UDF_EXAMPLE_LIB +eval CREATE FUNCTION myfunc_int RETURNS INTEGER SONAME "$UDF_EXAMPLE_LIB"; +--replace_result $UDF_EXAMPLE_LIB UDF_EXAMPLE_LIB +--error ER_CANT_FIND_DL_ENTRY +eval CREATE FUNCTION myfunc_nonexist RETURNS INTEGER SONAME "$UDF_EXAMPLE_LIB"; +SELECT * FROM mysql.func; +--disable_info + +save_master_pos; +connection slave; +sync_with_master; + +# Check to see that UDF CREATE statements were replicated +--echo "Running on the slave" +--enable_info +SELECT * FROM mysql.func; +--disable_info + +connection master; + +# Use the UDFs to do something +--echo "Running on the master" +--enable_info +eval CREATE TABLE t1(sum INT, price FLOAT(24)) ENGINE=$engine_type; +INSERT INTO t1 VALUES(myfunc_int(100), myfunc_double(50.00)); +INSERT INTO t1 VALUES(myfunc_int(10), myfunc_double(5.00)); +INSERT INTO t1 VALUES(myfunc_int(200), myfunc_double(25.00)); +INSERT INTO t1 VALUES(myfunc_int(1), myfunc_double(500.00)); +SELECT * FROM t1 ORDER BY sum; +--disable_info + +sync_slave_with_master; + +# Check to see if data was replicated +--echo "Running on the slave" +--enable_info +SELECT * FROM t1 ORDER BY sum; + +# Check to see that the functions are available for execution on the slave +SELECT myfunc_int(25); +SELECT myfunc_double(75.00); +--disable_info + +connection master; + +# Drop the functions +--echo "Running on the master" +--enable_info +DROP FUNCTION myfunc_double; +DROP FUNCTION myfunc_int; +SELECT * FROM mysql.func; +--disable_info + +sync_slave_with_master; + +# Check to see if the UDFs were dropped on the slave +--echo "Running on the slave" +--enable_info +SELECT * FROM mysql.func; +--disable_info + +connection master; + +# Cleanup +--echo "Running on the master" +--enable_info +DROP TABLE t1; +--disable_info + +# +# Test 2) Test UDFs with SQL body +# +--echo "*** Test 2) Test UDFs with SQL body *** +--echo "Running on the master" +--enable_info +CREATE FUNCTION myfuncsql_int(i INT) RETURNS INTEGER DETERMINISTIC RETURN i; +CREATE FUNCTION myfuncsql_double(d DOUBLE) RETURNS INTEGER DETERMINISTIC RETURN d * 0.95; +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +--disable_info + +sync_slave_with_master; + +# Check to see that UDF CREATE statements were replicated +--echo "Running on the slave" +--enable_info +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +--disable_info + +connection master; + +# Use the UDFs to do something +--echo "Running on the master" +--enable_info +eval CREATE TABLE t1(sum INT, price FLOAT(24)) ENGINE=$engine_type; +INSERT INTO t1 VALUES(myfuncsql_int(100), myfuncsql_double(50.00)); +INSERT INTO t1 VALUES(myfuncsql_int(10), myfuncsql_double(5.00)); +INSERT INTO t1 VALUES(myfuncsql_int(200), myfuncsql_double(25.00)); +INSERT INTO t1 VALUES(myfuncsql_int(1), myfuncsql_double(500.00)); +SELECT * FROM t1 ORDER BY sum; +--disable_info + +sync_slave_with_master; + +# Check to see if data was replicated +--echo "Running on the slave" +--enable_info +SELECT * FROM t1 ORDER BY sum; +--disable_info + +connection master; + +# Modify the UDFs to add a comment +--echo "Running on the master" +--enable_info +ALTER FUNCTION myfuncsql_int COMMENT "This was altered."; +ALTER FUNCTION myfuncsql_double COMMENT "This was altered."; +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +--disable_info + +sync_slave_with_master; + +# Check to see if data was replicated +--echo "Running on the slave" +--enable_info +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; + +# Check to see that the functions are available for execution on the slave +SELECT myfuncsql_int(25); +SELECT myfuncsql_double(75.00); +--disable_info + +connection master; + +# Drop the functions +--echo "Running on the master" +--enable_info +DROP FUNCTION myfuncsql_double; +DROP FUNCTION myfuncsql_int; +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +--disable_info + +sync_slave_with_master; + +# Check to see if the UDFs were dropped on the slave +--echo "Running on the slave" +--enable_info +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +--disable_info + +connection master; + +# Cleanup +--echo "Running on the master" +--enable_info +DROP TABLE t1; +--disable_info diff --git a/mysql-test/lib/init_db.sql b/mysql-test/lib/init_db.sql index c6c0f1d81dd..14ff2603a84 100644 --- a/mysql-test/lib/init_db.sql +++ b/mysql-test/lib/init_db.sql @@ -610,7 +610,7 @@ CREATE TABLE event ( last_executed DATETIME default NULL, starts DATETIME default NULL, ends DATETIME default NULL, - status ENUM('ENABLED','DISABLED') NOT NULL default 'ENABLED', + status ENUM('ENABLED','DISABLED','SLAVESIDE_DISABLED') NOT NULL default 'ENABLED', on_completion ENUM('DROP','PRESERVE') NOT NULL default 'DROP', sql_mode set( 'REAL_AS_FLOAT', @@ -645,6 +645,7 @@ CREATE TABLE event ( 'HIGH_NOT_PRECEDENCE' ) DEFAULT '' NOT NULL, comment char(64) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL default '', + originator int(10) NOT NULL, PRIMARY KEY (db, name) ) ENGINE=MyISAM DEFAULT CHARSET=utf8 COMMENT 'Events'; diff --git a/mysql-test/r/events.result b/mysql-test/r/events.result index af864c57efa..3193f45d554 100644 --- a/mysql-test/r/events.result +++ b/mysql-test/r/events.result @@ -193,7 +193,7 @@ create event руут21 on schedule every '50:23:59:95' day_second COMMENT 'това е 1 SHOW CREATE EVENT руут21; Event sql_mode Create Event руут21 CREATE EVENT `руут21` ON SCHEDULE EVERY '51 0:0:35' DAY_SECOND ON COMPLETION NOT PRESERVE ENABLE COMMENT 'това е 1251 коментар' DO select 1 -insert into mysql.event (db, name, body, definer, interval_value, interval_field) values (database(), "root22", "select 1", user(), 100, "SECOND_MICROSECOND"); +insert into mysql.event (db, name, body, definer, interval_value, interval_field, originator) values (database(), "root22", "select 1", user(), 100, "SECOND_MICROSECOND", 1); show create event root22; ERROR 42000: This version of MySQL doesn't yet support 'MICROSECOND' SHOW EVENTS; @@ -225,18 +225,18 @@ drop event руут21; set names latin1; CREATE EVENT intact_check ON SCHEDULE EVERY 10 HOUR DO SELECT "nothing"; SHOW EVENTS; -Db Name Definer Type Execute at Interval value Interval field Starts Ends Status -events_test intact_check root@localhost RECURRING NULL 10 HOUR # # ENABLED +Db Name Definer Type Execute at Interval value Interval field Starts Ends Status Originator +events_test intact_check root@localhost RECURRING NULL 10 HOUR # # ENABLED 1 ALTER TABLE mysql.event ADD dummy INT FIRST; SHOW EVENTS; -ERROR HY000: Column count of mysql.event is wrong. Expected 16, found 17. Table probably corrupted +ERROR HY000: Column count of mysql.event is wrong. Expected 17, found 18. Table probably corrupted ALTER TABLE mysql.event DROP dummy, ADD dummy2 VARCHAR(64) FIRST; SHOW EVENTS; -ERROR HY000: Column count of mysql.event is wrong. Expected 16, found 17. Table probably corrupted +ERROR HY000: Column count of mysql.event is wrong. Expected 17, found 18. Table probably corrupted ALTER TABLE mysql.event DROP dummy2; SHOW EVENTS; -Db Name Definer Type Execute at Interval value Interval field Starts Ends Status -events_test intact_check root@localhost RECURRING NULL 10 HOUR # # ENABLED +Db Name Definer Type Execute at Interval value Interval field Starts Ends Status Originator +events_test intact_check root@localhost RECURRING NULL 10 HOUR # # ENABLED 1 CREATE TABLE event_like LIKE mysql.event; INSERT INTO event_like SELECT * FROM mysql.event; ALTER TABLE mysql.event MODIFY db char(64) character set cp1251 default ''; @@ -258,10 +258,11 @@ event CREATE TABLE `event` ( `last_executed` datetime DEFAULT NULL, `starts` datetime DEFAULT NULL, `ends` datetime DEFAULT NULL, - `status` enum('ENABLED','DISABLED') NOT NULL DEFAULT 'ENABLED', + `status` enum('ENABLED','DISABLED','SLAVESIDE_DISABLED') NOT NULL DEFAULT 'ENABLED', `on_completion` enum('DROP','PRESERVE') NOT NULL DEFAULT 'DROP', `sql_mode` set('REAL_AS_FLOAT','PIPES_AS_CONCAT','ANSI_QUOTES','IGNORE_SPACE','NOT_USED','ONLY_FULL_GROUP_BY','NO_UNSIGNED_SUBTRACTION','NO_DIR_IN_CREATE','POSTGRESQL','ORACLE','MSSQL','DB2','MAXDB','NO_KEY_OPTIONS','NO_TABLE_OPTIONS','NO_FIELD_OPTIONS','MYSQL323','MYSQL40','ANSI','NO_AUTO_VALUE_ON_ZERO','NO_BACKSLASH_ESCAPES','STRICT_TRANS_TABLES','STRICT_ALL_TABLES','NO_ZERO_IN_DATE','NO_ZERO_DATE','INVALID_DATES','ERROR_FOR_DIVISION_BY_ZERO','TRADITIONAL','NO_AUTO_CREATE_USER','HIGH_NOT_PRECEDENCE') NOT NULL DEFAULT '', `comment` char(64) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL DEFAULT '', + `originator` int(10) NOT NULL, PRIMARY KEY (`db`,`name`) ) ENGINE=MyISAM DEFAULT CHARSET=utf8 COMMENT='Events' SELECT event_name FROM INFORMATION_SCHEMA.EVENTS; @@ -269,8 +270,8 @@ ERROR HY000: Cannot load from mysql.event. Table probably corrupted. See error l ALTER TABLE mysql.event MODIFY db char(64) character set utf8 collate utf8_bin default ''; "This should work" SHOW EVENTS; -Db Name Definer Type Execute at Interval value Interval field Starts Ends Status -events_test intact_check root@localhost RECURRING NULL 10 HOUR # # ENABLED +Db Name Definer Type Execute at Interval value Interval field Starts Ends Status Originator +events_test intact_check root@localhost RECURRING NULL 10 HOUR # # ENABLED 1 ALTER TABLE mysql.event MODIFY db char(64) character set cp1251 default ''; SELECT event_name FROM INFORMATION_SCHEMA.EVENTS; ERROR HY000: Cannot load from mysql.event. Table probably corrupted. See error log. @@ -279,14 +280,14 @@ SELECT event_name FROM INFORMATION_SCHEMA.EVENTS; ERROR HY000: Cannot load from mysql.event. Table probably corrupted. See error log. ALTER TABLE mysql.event DROP comment, DROP starts; SELECT event_name FROM INFORMATION_SCHEMA.EVENTS; -ERROR HY000: Column count of mysql.event is wrong. Expected 16, found 14. Table probably corrupted +ERROR HY000: Column count of mysql.event is wrong. Expected 17, found 15. Table probably corrupted DROP TABLE mysql.event; CREATE TABLE mysql.event like event_like; INSERT INTO mysql.event SELECT * FROM event_like; DROP TABLE event_like; SHOW EVENTS; -Db Name Definer Type Execute at Interval value Interval field Starts Ends Status -events_test intact_check root@localhost RECURRING NULL 10 HOUR # # ENABLED +Db Name Definer Type Execute at Interval value Interval field Starts Ends Status Originator +events_test intact_check root@localhost RECURRING NULL 10 HOUR # # ENABLED 1 DROP EVENT intact_check; create event e_26 on schedule at '2017-01-01 00:00:00' disable do set @a = 5; select db, name, body, definer, convert_tz(execute_at, 'UTC', 'SYSTEM'), on_completion from mysql.event; @@ -399,5 +400,5 @@ ERROR 42000: Incorrect database name 'aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa SHOW EVENTS FROM ``; ERROR 42000: Incorrect database name '' SHOW EVENTS FROM `events\\test`; -Db Name Definer Type Execute at Interval value Interval field Starts Ends Status +Db Name Definer Type Execute at Interval value Interval field Starts Ends Status Originator drop database events_test; diff --git a/mysql-test/r/events_grant.result b/mysql-test/r/events_grant.result index a28c30a9345..87906216e40 100644 --- a/mysql-test/r/events_grant.result +++ b/mysql-test/r/events_grant.result @@ -2,8 +2,8 @@ CREATE DATABASE IF NOT EXISTS events_test; use events_test; CREATE EVENT one_event ON SCHEDULE EVERY 10 SECOND DO SELECT 123; SHOW EVENTS; -Db Name Definer Type Execute at Interval value Interval field Starts Ends Status -events_test one_event root@localhost RECURRING NULL 10 SECOND # # ENABLED +Db Name Definer Type Execute at Interval value Interval field Starts Ends Status Originator +events_test one_event root@localhost RECURRING NULL 10 SECOND # # ENABLED 1 SELECT EVENT_CATALOG, EVENT_SCHEMA, EVENT_NAME, DEFINER, EVENT_BODY, EVENT_DEFINITION, EVENT_TYPE, EXECUTE_AT, INTERVAL_VALUE, INTERVAL_FIELD, STATUS,ON_COMPLETION, EVENT_COMMENT FROM INFORMATION_SCHEMA.EVENTS ORDER BY EVENT_SCHEMA, EVENT_NAME; EVENT_CATALOG EVENT_SCHEMA EVENT_NAME DEFINER EVENT_BODY EVENT_DEFINITION EVENT_TYPE EXECUTE_AT INTERVAL_VALUE INTERVAL_FIELD STATUS ON_COMPLETION EVENT_COMMENT NULL events_test one_event root@localhost SQL SELECT 123 RECURRING NULL 10 SECOND ENABLED NOT PRESERVE @@ -29,8 +29,8 @@ ERROR 42000: Access denied for user 'ev_test'@'localhost' to database 'events_te USE events_test; "We should see one event"; SHOW EVENTS; -Db Name Definer Type Execute at Interval value Interval field Starts Ends Status -events_test one_event root@localhost RECURRING NULL 10 SECOND # # ENABLED +Db Name Definer Type Execute at Interval value Interval field Starts Ends Status Originator +events_test one_event root@localhost RECURRING NULL 10 SECOND # # ENABLED 1 SELECT CONCAT("Let's create some new events from the name of ", USER()); CONCAT("Let's create some new events from the name of ", USER()) Let's create some new events from the name of ev_test@localhost @@ -40,18 +40,18 @@ CREATE EVENT two_event ON SCHEDULE EVERY 20 SECOND ON COMPLETION NOT PRESERVE CO CREATE EVENT three_event ON SCHEDULE EVERY 20 SECOND ON COMPLETION PRESERVE COMMENT "three event" DO SELECT 123; "Now we should see 3 events:"; SHOW EVENTS; -Db Name Definer Type Execute at Interval value Interval field Starts Ends Status -events_test one_event root@localhost RECURRING NULL 10 SECOND # # ENABLED -events_test three_event ev_test@localhost RECURRING NULL 20 SECOND # # ENABLED -events_test two_event ev_test@localhost RECURRING NULL 20 SECOND # # ENABLED +Db Name Definer Type Execute at Interval value Interval field Starts Ends Status Originator +events_test one_event root@localhost RECURRING NULL 10 SECOND # # ENABLED 1 +events_test three_event ev_test@localhost RECURRING NULL 20 SECOND # # ENABLED 1 +events_test two_event ev_test@localhost RECURRING NULL 20 SECOND # # ENABLED 1 "This should show us only 2 events:"; SHOW EVENTS LIKE 't%event'; -Db Name Definer Type Execute at Interval value Interval field Starts Ends Status -events_test three_event ev_test@localhost RECURRING NULL 20 SECOND # # ENABLED -events_test two_event ev_test@localhost RECURRING NULL 20 SECOND # # ENABLED +Db Name Definer Type Execute at Interval value Interval field Starts Ends Status Originator +events_test three_event ev_test@localhost RECURRING NULL 20 SECOND # # ENABLED 1 +events_test two_event ev_test@localhost RECURRING NULL 20 SECOND # # ENABLED 1 "This should show us no events:"; SHOW EVENTS FROM test LIKE '%'; -Db Name Definer Type Execute at Interval value Interval field Starts Ends Status +Db Name Definer Type Execute at Interval value Interval field Starts Ends Status Originator GRANT EVENT ON events_test2.* TO ev_test@localhost; USE events_test2; CREATE EVENT four_event ON SCHEDULE EVERY 20 SECOND DO SELECT 42; diff --git a/mysql-test/r/events_restart_phase1.result b/mysql-test/r/events_restart_phase1.result index a7a46fa0ab1..2b0f4141c7c 100644 --- a/mysql-test/r/events_restart_phase1.result +++ b/mysql-test/r/events_restart_phase1.result @@ -7,6 +7,6 @@ create event abc2 on schedule every 1 second do insert into execution_log value( create event abc3 on schedule every 1 second do insert into execution_log value('abc3'); select name from execution_log; name -insert into mysql.event values ('db1','bad','select 42','root@localhost',NULL,1000,'MICROSECOND','2006-05-05 17:39:11','2006-05-05 17:39:20','2016-05-05 15:39:24','2016-05-05 15:39:11',NULL,'ENABLED','DROP','','comment1'); -insert into mysql.event values ('db1','bad2','sect','root@localhost',NULL,1000,'SECOND','2006-05-05 17:39:11','2006-05-05 17:39:20','2016-05-05 15:39:24','2016-05-05 15:39:11',NULL,'ENABLED','DROP','','comment2'); +insert into mysql.event values ('db1','bad','select 42','root@localhost',NULL,1000,'MICROSECOND','2006-05-05 17:39:11','2006-05-05 17:39:20','2016-05-05 15:39:24','2016-05-05 15:39:11',NULL,'ENABLED','DROP','','comment1',1); +insert into mysql.event values ('db1','bad2','sect','root@localhost',NULL,1000,'SECOND','2006-05-05 17:39:11','2006-05-05 17:39:20','2016-05-05 15:39:24','2016-05-05 15:39:11',NULL,'ENABLED','DROP','','comment2',1); "Now we restart the server" diff --git a/mysql-test/r/rpl_events.result b/mysql-test/r/rpl_events.result new file mode 100644 index 00000000000..59bd16adbf6 --- /dev/null +++ b/mysql-test/r/rpl_events.result @@ -0,0 +1,133 @@ +set global event_scheduler=1; +stop slave; +drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9; +reset master; +reset slave; +drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9; +start slave; +set binlog_format=row; +DROP EVENT IF EXISTS justonce; +drop table if exists t1,t2; +CREATE TABLE `t1` ( +`id` INT(10) UNSIGNED NOT NULL AUTO_INCREMENT, +`c` VARCHAR(50) NOT NULL, +`ts` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE +CURRENT_TIMESTAMP, +PRIMARY KEY (`id`) +) ENGINE=MyISAM DEFAULT CHARSET=utf8; +INSERT INTO t1 (c) VALUES ('manually'); +CREATE EVENT justonce ON SCHEDULE AT NOW() + INTERVAL 2 SECOND DO INSERT INTo t1 +(c) VALUES ('from justonce'); +"in the master" +SELECT * FROM t1; +id c ts +1 manually TIMESTAMP +2 from justonce TIMESTAMP +affected rows: 2 +"in the slave" +SELECT * FROM t1; +id c ts +1 manually TIMESTAMP +2 from justonce TIMESTAMP +affected rows: 2 +DROP EVENT IF EXISTS test.slave_once; +CREATE EVENT test.slave_once ON SCHEDULE EVERY 5 MINUTE DO +INSERT INTO t1(c) VALUES ('from slave_once'); +SELECT db, name, status, originator FROM mysql.event; +db name status originator +test justonce SLAVESIDE_DISABLED 1 +test slave_once ENABLED 2 +DROP EVENT IF EXISTS test.slave_once; +DROP EVENT IF EXISTS test.justonce; +Warnings: +Note 1305 Event justonce does not exist +CREATE EVENT test.er ON SCHEDULE EVERY 3 SECOND DO +INSERT INTO t1(c) VALUES ('from er'); +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; +db name status originator +test er ENABLED 1 +"in the slave" +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; +db name status originator +test er SLAVESIDE_DISABLED 1 +"in the master" +ALTER EVENT test.er ON SCHEDULE EVERY 5 SECOND DO INSERT into t1(c) VALUES ('from alter er'); +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; +db name status originator +test er ENABLED 1 +"in the slave" +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; +db name status originator +test er SLAVESIDE_DISABLED 1 +"in the master" +DROP EVENT test.er; +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; +db name status originator +"in the slave" +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; +db name status originator +"in the master" +DROP TABLE t1; +set binlog_format=statement; +DROP EVENT IF EXISTS justonce; +drop table if exists t1,t2; +CREATE TABLE `t1` ( +`id` INT(10) UNSIGNED NOT NULL AUTO_INCREMENT, +`c` VARCHAR(50) NOT NULL, +`ts` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE +CURRENT_TIMESTAMP, +PRIMARY KEY (`id`) +) ENGINE=MyISAM DEFAULT CHARSET=utf8; +INSERT INTO t1 (c) VALUES ('manually'); +CREATE EVENT justonce ON SCHEDULE AT NOW() + INTERVAL 2 SECOND DO INSERT INTo t1 +(c) VALUES ('from justonce'); +"in the master" +SELECT * FROM t1; +id c ts +1 manually TIMESTAMP +2 from justonce TIMESTAMP +affected rows: 2 +"in the slave" +SELECT * FROM t1; +id c ts +1 manually TIMESTAMP +2 from justonce TIMESTAMP +affected rows: 2 +DROP EVENT IF EXISTS test.slave_once; +CREATE EVENT test.slave_once ON SCHEDULE EVERY 5 MINUTE DO +INSERT INTO t1(c) VALUES ('from slave_once'); +SELECT db, name, status, originator FROM mysql.event; +db name status originator +test justonce SLAVESIDE_DISABLED 1 +test slave_once ENABLED 2 +DROP EVENT IF EXISTS test.slave_once; +DROP EVENT IF EXISTS test.justonce; +Warnings: +Note 1305 Event justonce does not exist +CREATE EVENT test.er ON SCHEDULE EVERY 3 SECOND DO +INSERT INTO t1(c) VALUES ('from er'); +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; +db name status originator +test er ENABLED 1 +"in the slave" +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; +db name status originator +test er SLAVESIDE_DISABLED 1 +"in the master" +ALTER EVENT test.er ON SCHEDULE EVERY 5 SECOND DO INSERT into t1(c) VALUES ('from alter er'); +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; +db name status originator +test er ENABLED 1 +"in the slave" +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; +db name status originator +test er SLAVESIDE_DISABLED 1 +"in the master" +DROP EVENT test.er; +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; +db name status originator +"in the slave" +SELECT db, name, status, originator FROM mysql.event WHERE db = 'test' AND name = 'er'; +db name status originator +"in the master" +DROP TABLE t1; diff --git a/mysql-test/r/rpl_udf.result b/mysql-test/r/rpl_udf.result new file mode 100644 index 00000000000..156876d07de --- /dev/null +++ b/mysql-test/r/rpl_udf.result @@ -0,0 +1,310 @@ +stop slave; +drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9; +reset master; +reset slave; +drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9; +start slave; +set binlog_format=row; +drop table if exists t1; +"*** Test 1) Test UDFs via loadable libraries *** +"Running on the master" +CREATE FUNCTION myfunc_double RETURNS REAL SONAME "UDF_EXAMPLE_LIB"; +affected rows: 0 +CREATE FUNCTION myfunc_int RETURNS INTEGER SONAME "UDF_EXAMPLE_LIB"; +affected rows: 0 +CREATE FUNCTION myfunc_nonexist RETURNS INTEGER SONAME "UDF_EXAMPLE_LIB"; +ERROR HY000: Can't find symbol 'myfunc_nonexist' in library +SELECT * FROM mysql.func; +name ret dl type +myfunc_double 1 udf_example.dll function +myfunc_int 2 udf_example.dll function +affected rows: 2 +"Running on the slave" +SELECT * FROM mysql.func; +name ret dl type +myfunc_double 1 udf_example.dll function +myfunc_int 2 udf_example.dll function +affected rows: 2 +"Running on the master" +CREATE TABLE t1(sum INT, price FLOAT(24)) ENGINE=MyISAM; +affected rows: 0 +INSERT INTO t1 VALUES(myfunc_int(100), myfunc_double(50.00)); +affected rows: 1 +INSERT INTO t1 VALUES(myfunc_int(10), myfunc_double(5.00)); +affected rows: 1 +INSERT INTO t1 VALUES(myfunc_int(200), myfunc_double(25.00)); +affected rows: 1 +INSERT INTO t1 VALUES(myfunc_int(1), myfunc_double(500.00)); +affected rows: 1 +SELECT * FROM t1 ORDER BY sum; +sum price +1 48.5 +10 48.75 +100 48.6 +200 49 +affected rows: 4 +"Running on the slave" +SELECT * FROM t1 ORDER BY sum; +sum price +1 48.5 +10 48.75 +100 48.6 +200 49 +affected rows: 4 +SELECT myfunc_int(25); +myfunc_int(25) +25 +affected rows: 1 +SELECT myfunc_double(75.00); +myfunc_double(75.00) +50.00 +affected rows: 1 +"Running on the master" +DROP FUNCTION myfunc_double; +affected rows: 0 +DROP FUNCTION myfunc_int; +affected rows: 0 +SELECT * FROM mysql.func; +name ret dl type +affected rows: 0 +"Running on the slave" +SELECT * FROM mysql.func; +name ret dl type +affected rows: 0 +"Running on the master" +DROP TABLE t1; +affected rows: 0 +"*** Test 2) Test UDFs with SQL body *** +"Running on the master" +CREATE FUNCTION myfuncsql_int(i INT) RETURNS INTEGER DETERMINISTIC RETURN i; +affected rows: 0 +CREATE FUNCTION myfuncsql_double(d DOUBLE) RETURNS INTEGER DETERMINISTIC RETURN d * 0.95; +affected rows: 0 +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +db name type param_list body comment +test myfuncsql_double FUNCTION d DOUBLE RETURN d * 0.95 +test myfuncsql_int FUNCTION i INT RETURN i +affected rows: 2 +"Running on the slave" +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +db name type param_list body comment +test myfuncsql_double FUNCTION d DOUBLE RETURN d * 0.95 +test myfuncsql_int FUNCTION i INT RETURN i +affected rows: 2 +"Running on the master" +CREATE TABLE t1(sum INT, price FLOAT(24)) ENGINE=MyISAM; +affected rows: 0 +INSERT INTO t1 VALUES(myfuncsql_int(100), myfuncsql_double(50.00)); +affected rows: 1 +INSERT INTO t1 VALUES(myfuncsql_int(10), myfuncsql_double(5.00)); +affected rows: 1 +INSERT INTO t1 VALUES(myfuncsql_int(200), myfuncsql_double(25.00)); +affected rows: 1 +INSERT INTO t1 VALUES(myfuncsql_int(1), myfuncsql_double(500.00)); +affected rows: 1 +SELECT * FROM t1 ORDER BY sum; +sum price +1 475 +10 5 +100 47 +200 24 +affected rows: 4 +"Running on the slave" +SELECT * FROM t1 ORDER BY sum; +sum price +1 475 +10 5 +100 47 +200 24 +affected rows: 4 +"Running on the master" +ALTER FUNCTION myfuncsql_int COMMENT "This was altered."; +affected rows: 0 +ALTER FUNCTION myfuncsql_double COMMENT "This was altered."; +affected rows: 0 +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +db name type param_list body comment +test myfuncsql_double FUNCTION d DOUBLE RETURN d * 0.95 This was altered. +test myfuncsql_int FUNCTION i INT RETURN i This was altered. +affected rows: 2 +"Running on the slave" +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +db name type param_list body comment +test myfuncsql_double FUNCTION d DOUBLE RETURN d * 0.95 This was altered. +test myfuncsql_int FUNCTION i INT RETURN i This was altered. +affected rows: 2 +SELECT myfuncsql_int(25); +myfuncsql_int(25) +25 +affected rows: 1 +SELECT myfuncsql_double(75.00); +myfuncsql_double(75.00) +71 +affected rows: 1 +"Running on the master" +DROP FUNCTION myfuncsql_double; +affected rows: 0 +DROP FUNCTION myfuncsql_int; +affected rows: 0 +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +db name type param_list body comment +affected rows: 0 +"Running on the slave" +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +db name type param_list body comment +affected rows: 0 +"Running on the master" +DROP TABLE t1; +affected rows: 0 +set binlog_format=statement; +drop table if exists t1; +"*** Test 1) Test UDFs via loadable libraries *** +"Running on the master" +CREATE FUNCTION myfunc_double RETURNS REAL SONAME "UDF_EXAMPLE_LIB"; +affected rows: 0 +CREATE FUNCTION myfunc_int RETURNS INTEGER SONAME "UDF_EXAMPLE_LIB"; +affected rows: 0 +CREATE FUNCTION myfunc_nonexist RETURNS INTEGER SONAME "UDF_EXAMPLE_LIB"; +ERROR HY000: Can't find symbol 'myfunc_nonexist' in library +SELECT * FROM mysql.func; +name ret dl type +myfunc_int 2 udf_example.dll function +myfunc_double 1 udf_example.dll function +affected rows: 2 +"Running on the slave" +SELECT * FROM mysql.func; +name ret dl type +myfunc_int 2 udf_example.dll function +myfunc_double 1 udf_example.dll function +affected rows: 2 +"Running on the master" +CREATE TABLE t1(sum INT, price FLOAT(24)) ENGINE=MyISAM; +affected rows: 0 +INSERT INTO t1 VALUES(myfunc_int(100), myfunc_double(50.00)); +affected rows: 1 +INSERT INTO t1 VALUES(myfunc_int(10), myfunc_double(5.00)); +affected rows: 1 +INSERT INTO t1 VALUES(myfunc_int(200), myfunc_double(25.00)); +affected rows: 1 +INSERT INTO t1 VALUES(myfunc_int(1), myfunc_double(500.00)); +affected rows: 1 +SELECT * FROM t1 ORDER BY sum; +sum price +1 48.5 +10 48.75 +100 48.6 +200 49 +affected rows: 4 +"Running on the slave" +SELECT * FROM t1 ORDER BY sum; +sum price +1 48.5 +10 48.75 +100 48.6 +200 49 +affected rows: 4 +SELECT myfunc_int(25); +myfunc_int(25) +25 +affected rows: 1 +SELECT myfunc_double(75.00); +myfunc_double(75.00) +50.00 +affected rows: 1 +"Running on the master" +DROP FUNCTION myfunc_double; +affected rows: 0 +DROP FUNCTION myfunc_int; +affected rows: 0 +SELECT * FROM mysql.func; +name ret dl type +affected rows: 0 +"Running on the slave" +SELECT * FROM mysql.func; +name ret dl type +affected rows: 0 +"Running on the master" +DROP TABLE t1; +affected rows: 0 +"*** Test 2) Test UDFs with SQL body *** +"Running on the master" +CREATE FUNCTION myfuncsql_int(i INT) RETURNS INTEGER DETERMINISTIC RETURN i; +affected rows: 0 +CREATE FUNCTION myfuncsql_double(d DOUBLE) RETURNS INTEGER DETERMINISTIC RETURN d * 0.95; +affected rows: 0 +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +db name type param_list body comment +test myfuncsql_double FUNCTION d DOUBLE RETURN d * 0.95 +test myfuncsql_int FUNCTION i INT RETURN i +affected rows: 2 +"Running on the slave" +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +db name type param_list body comment +test myfuncsql_double FUNCTION d DOUBLE RETURN d * 0.95 +test myfuncsql_int FUNCTION i INT RETURN i +affected rows: 2 +"Running on the master" +CREATE TABLE t1(sum INT, price FLOAT(24)) ENGINE=MyISAM; +affected rows: 0 +INSERT INTO t1 VALUES(myfuncsql_int(100), myfuncsql_double(50.00)); +affected rows: 1 +INSERT INTO t1 VALUES(myfuncsql_int(10), myfuncsql_double(5.00)); +affected rows: 1 +INSERT INTO t1 VALUES(myfuncsql_int(200), myfuncsql_double(25.00)); +affected rows: 1 +INSERT INTO t1 VALUES(myfuncsql_int(1), myfuncsql_double(500.00)); +affected rows: 1 +SELECT * FROM t1 ORDER BY sum; +sum price +1 475 +10 5 +100 47 +200 24 +affected rows: 4 +"Running on the slave" +SELECT * FROM t1 ORDER BY sum; +sum price +1 475 +10 5 +100 47 +200 24 +affected rows: 4 +"Running on the master" +ALTER FUNCTION myfuncsql_int COMMENT "This was altered."; +affected rows: 0 +ALTER FUNCTION myfuncsql_double COMMENT "This was altered."; +affected rows: 0 +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +db name type param_list body comment +test myfuncsql_double FUNCTION d DOUBLE RETURN d * 0.95 This was altered. +test myfuncsql_int FUNCTION i INT RETURN i This was altered. +affected rows: 2 +"Running on the slave" +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +db name type param_list body comment +test myfuncsql_double FUNCTION d DOUBLE RETURN d * 0.95 This was altered. +test myfuncsql_int FUNCTION i INT RETURN i This was altered. +affected rows: 2 +SELECT myfuncsql_int(25); +myfuncsql_int(25) +25 +affected rows: 1 +SELECT myfuncsql_double(75.00); +myfuncsql_double(75.00) +71 +affected rows: 1 +"Running on the master" +DROP FUNCTION myfuncsql_double; +affected rows: 0 +DROP FUNCTION myfuncsql_int; +affected rows: 0 +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +db name type param_list body comment +affected rows: 0 +"Running on the slave" +SELECT db, name, type, param_list, body, comment FROM mysql.proc WHERE db = 'test' AND name LIKE 'myfuncsql%'; +db name type param_list body comment +affected rows: 0 +"Running on the master" +DROP TABLE t1; +affected rows: 0 diff --git a/mysql-test/r/system_mysql_db.result b/mysql-test/r/system_mysql_db.result index c93fbfba6e2..a8ea6ffa19f 100644 --- a/mysql-test/r/system_mysql_db.result +++ b/mysql-test/r/system_mysql_db.result @@ -220,10 +220,11 @@ event CREATE TABLE `event` ( `last_executed` datetime DEFAULT NULL, `starts` datetime DEFAULT NULL, `ends` datetime DEFAULT NULL, - `status` enum('ENABLED','DISABLED') NOT NULL DEFAULT 'ENABLED', + `status` enum('ENABLED','DISABLED','SLAVESIDE_DISABLED') NOT NULL DEFAULT 'ENABLED', `on_completion` enum('DROP','PRESERVE') NOT NULL DEFAULT 'DROP', `sql_mode` set('REAL_AS_FLOAT','PIPES_AS_CONCAT','ANSI_QUOTES','IGNORE_SPACE','NOT_USED','ONLY_FULL_GROUP_BY','NO_UNSIGNED_SUBTRACTION','NO_DIR_IN_CREATE','POSTGRESQL','ORACLE','MSSQL','DB2','MAXDB','NO_KEY_OPTIONS','NO_TABLE_OPTIONS','NO_FIELD_OPTIONS','MYSQL323','MYSQL40','ANSI','NO_AUTO_VALUE_ON_ZERO','NO_BACKSLASH_ESCAPES','STRICT_TRANS_TABLES','STRICT_ALL_TABLES','NO_ZERO_IN_DATE','NO_ZERO_DATE','INVALID_DATES','ERROR_FOR_DIVISION_BY_ZERO','TRADITIONAL','NO_AUTO_CREATE_USER','HIGH_NOT_PRECEDENCE') NOT NULL DEFAULT '', `comment` char(64) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL DEFAULT '', + `originator` int(10) NOT NULL, PRIMARY KEY (`db`,`name`) ) ENGINE=MyISAM DEFAULT CHARSET=utf8 COMMENT='Events' show create table general_log; diff --git a/mysql-test/t/events.test b/mysql-test/t/events.test index 6eb514fc13c..d2444bbea68 100644 --- a/mysql-test/t/events.test +++ b/mysql-test/t/events.test @@ -160,7 +160,7 @@ SHOW CREATE EVENT root20; set names cp1251; create event руут21 on schedule every '50:23:59:95' day_second COMMENT 'това е 1251 коментар' do select 1; SHOW CREATE EVENT руут21; -insert into mysql.event (db, name, body, definer, interval_value, interval_field) values (database(), "root22", "select 1", user(), 100, "SECOND_MICROSECOND"); +insert into mysql.event (db, name, body, definer, interval_value, interval_field, originator) values (database(), "root22", "select 1", user(), 100, "SECOND_MICROSECOND", 1); --error ER_NOT_SUPPORTED_YET show create event root22; --error ER_NOT_SUPPORTED_YET diff --git a/mysql-test/t/events_restart_phase1.test b/mysql-test/t/events_restart_phase1.test index 92783ddaef7..ce9b77d4ff0 100644 --- a/mysql-test/t/events_restart_phase1.test +++ b/mysql-test/t/events_restart_phase1.test @@ -14,6 +14,6 @@ create event abc3 on schedule every 1 second do insert into execution_log value( --sleep 1.5 select name from execution_log; -insert into mysql.event values ('db1','bad','select 42','root@localhost',NULL,1000,'MICROSECOND','2006-05-05 17:39:11','2006-05-05 17:39:20','2016-05-05 15:39:24','2016-05-05 15:39:11',NULL,'ENABLED','DROP','','comment1'); -insert into mysql.event values ('db1','bad2','sect','root@localhost',NULL,1000,'SECOND','2006-05-05 17:39:11','2006-05-05 17:39:20','2016-05-05 15:39:24','2016-05-05 15:39:11',NULL,'ENABLED','DROP','','comment2'); +insert into mysql.event values ('db1','bad','select 42','root@localhost',NULL,1000,'MICROSECOND','2006-05-05 17:39:11','2006-05-05 17:39:20','2016-05-05 15:39:24','2016-05-05 15:39:11',NULL,'ENABLED','DROP','','comment1',1); +insert into mysql.event values ('db1','bad2','sect','root@localhost',NULL,1000,'SECOND','2006-05-05 17:39:11','2006-05-05 17:39:20','2016-05-05 15:39:24','2016-05-05 15:39:11',NULL,'ENABLED','DROP','','comment2',1); --echo "Now we restart the server" diff --git a/mysql-test/t/rpl_events.test b/mysql-test/t/rpl_events.test new file mode 100644 index 00000000000..895e94c438b --- /dev/null +++ b/mysql-test/t/rpl_events.test @@ -0,0 +1,24 @@ +################################################################## +# Author: Giuseppe # +# Date: 2006-12-20 # +# Purpose: To test that event effects are replicated # +# in both row based and statement based format # +################################################################## + +set global event_scheduler=1; + +--source include/not_embedded.inc +--source include/master-slave.inc + +let $engine_type= MyISAM; + +set binlog_format=row; + +# Embedded server doesn't support binlogging +--source include/rpl_events.inc + +set binlog_format=statement; + +# Embedded server doesn't support binlogging +--source include/rpl_events.inc + diff --git a/mysql-test/t/rpl_udf.test b/mysql-test/t/rpl_udf.test new file mode 100644 index 00000000000..262ad04630c --- /dev/null +++ b/mysql-test/t/rpl_udf.test @@ -0,0 +1,22 @@ +################################################################### +# Author: Chuck Bell # +# Date: 2006-12-21 # +# Purpose: To test that UDFs are replicated in both row based and # +# statement based format. This tests work completed in WL#3629. # +################################################################### + +--source include/not_embedded.inc +--source include/master-slave.inc + +let $engine_type= MyISAM; + +set binlog_format=row; + +# Embedded server doesn't support binlogging +--source include/rpl_udf.inc + +set binlog_format=statement; + +# Embedded server doesn't support binlogging +--source include/rpl_udf.inc + diff --git a/scripts/mysql_create_system_tables.sh b/scripts/mysql_create_system_tables.sh index cc86def1a5c..ddb90b55633 100644 --- a/scripts/mysql_create_system_tables.sh +++ b/scripts/mysql_create_system_tables.sh @@ -832,7 +832,7 @@ then c_ev="$c_ev last_executed DATETIME default NULL," c_ev="$c_ev starts DATETIME default NULL," c_ev="$c_ev ends DATETIME default NULL," - c_ev="$c_ev status ENUM('ENABLED','DISABLED') NOT NULL default 'ENABLED'," + c_ev="$c_ev status ENUM('ENABLED','DISABLED','SLAVESIDE_DISABLED') NOT NULL default 'ENABLED'," c_ev="$c_ev on_completion ENUM('DROP','PRESERVE') NOT NULL default 'DROP'," c_ev="$c_ev sql_mode set(" c_ev="$c_ev 'REAL_AS_FLOAT'," @@ -867,6 +867,7 @@ then c_ev="$c_ev 'HIGH_NOT_PRECEDENCE'" c_ev="$c_ev ) DEFAULT '' NOT NULL," c_ev="$c_ev comment char(64) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL default ''," + c_ev="$c_ev originator int(10) NOT NULL, c_ev="$c_ev PRIMARY KEY (db, name)" c_ev="$c_ev ) ENGINE=MyISAM DEFAULT CHARSET=utf8 COMMENT 'Events';" fi diff --git a/scripts/mysql_fix_privilege_tables.sql b/scripts/mysql_fix_privilege_tables.sql index 9cdea507493..4d661dd8146 100644 --- a/scripts/mysql_fix_privilege_tables.sql +++ b/scripts/mysql_fix_privilege_tables.sql @@ -648,7 +648,7 @@ CREATE TABLE event ( last_executed DATETIME default NULL, starts DATETIME default NULL, ends DATETIME default NULL, - status ENUM('ENABLED','DISABLED') NOT NULL default 'ENABLED', + status ENUM('ENABLED','DISABLED','SLAVESIDE_DISABLED') NOT NULL default 'ENABLED', on_completion ENUM('DROP','PRESERVE') NOT NULL default 'DROP', sql_mode set( 'REAL_AS_FLOAT', @@ -683,6 +683,7 @@ CREATE TABLE event ( 'HIGH_NOT_PRECEDENCE' ) DEFAULT '' NOT NULL, comment char(64) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL default '', + originator int(10) NOT NULL, PRIMARY KEY (db,name) ) ENGINE=MyISAM DEFAULT CHARSET=utf8 COMMENT 'Events'; @@ -737,6 +738,8 @@ ALTER TABLE event ADD sql_mode UPDATE user SET Event_priv=Super_priv WHERE @hadEventPriv = 0; ALTER TABLE event MODIFY name char(64) CHARACTER SET utf8 NOT NULL default ''; +ALTER TABLE event ADD COLUMN originator INT(10) NOT NULL; +ALTER TABLE event MODIFY COLUMN status ENUM('ENABLED','DISABLED','SLAVESIDE_DISABLED') NOT NULL default 'ENABLED'; # # TRIGGER privilege diff --git a/sql/event_data_objects.cc b/sql/event_data_objects.cc index 07575a6d33a..4c3524f47ac 100644 --- a/sql/event_data_objects.cc +++ b/sql/event_data_objects.cc @@ -58,7 +58,8 @@ Event_parse_data::new_instance(THD *thd) */ Event_parse_data::Event_parse_data() - :on_completion(ON_COMPLETION_DROP), status(ENABLED), + :on_completion(Event_basic::ON_COMPLETION_DROP), + status(Event_basic::ENABLED), item_starts(NULL), item_ends(NULL), item_execute_at(NULL), starts_null(TRUE), ends_null(TRUE), execute_at_null(TRUE), item_expression(NULL), expression(0) @@ -550,9 +551,9 @@ Event_parse_data::check_parse_data(THD *thd) init_name(thd, identifier); init_definer(thd); - ret= init_execute_at(thd) || init_interval(thd) || init_starts(thd) || init_ends(thd); + check_originator_id(thd); DBUG_RETURN(ret); } @@ -599,6 +600,30 @@ Event_parse_data::init_definer(THD *thd) /* + Set the originator id of the event to the server_id if executing on + the master or set to the server_id of the master if executing on + the slave. If executing on slave, also set status to SLAVESIDE_DISABLED. + + SYNOPSIS + Event_parse_data::check_originator_id() +*/ +void Event_parse_data::check_originator_id(THD *thd) +{ + /* Disable replicated events on slave. */ + if ((thd->system_thread == SYSTEM_THREAD_SLAVE_SQL) || + (thd->system_thread == SYSTEM_THREAD_SLAVE_IO)) + { + DBUG_PRINT("info", ("Invoked object status set to SLAVESIDE_DISABLED.")); + if (status == Event_basic::ENABLED) + status = Event_basic::SLAVESIDE_DISABLED; + originator = thd->server_id; + } + else + originator = server_id; +} + + +/* Constructor SYNOPSIS @@ -927,8 +952,23 @@ Event_queue_element::load_from_row(TABLE *table) goto error; DBUG_PRINT("load_from_row", ("Event [%s] is [%s]", name.str, ptr)); - status= (ptr[0]=='E'? Event_queue_element::ENABLED: - Event_queue_element::DISABLED); + + /* Set event status (ENABLED | SLAVESIDE_DISABLED | DISABLED) */ + switch (ptr[0]) + { + case 'E' : + status = Event_queue_element::ENABLED; + break; + case 'S' : + status = Event_queue_element::SLAVESIDE_DISABLED; + break; + case 'D' : + status = Event_queue_element::DISABLED; + break; + } + if ((ptr= get_field(&mem_root, table->field[ET_FIELD_ORIGINATOR])) == NullS) + goto error; + originator = table->field[ET_FIELD_ORIGINATOR]->val_int(); /* ToDo : Andrey . Find a way not to allocate ptr on event_mem_root */ if ((ptr= get_field(&mem_root, @@ -1199,7 +1239,7 @@ Event_queue_element::compute_next_execution_time() (long) TIME_to_ulonglong_datetime(&last_executed), (long) this)); - if (status == Event_queue_element::DISABLED) + if (status != Event_queue_element::ENABLED) { DBUG_PRINT("compute_next_execution_time", ("Event %s is DISABLED", name.str)); @@ -1601,6 +1641,8 @@ Event_timed::get_create_event(THD *thd, String *buf) if (status == Event_timed::ENABLED) buf->append(STRING_WITH_LEN("ENABLE")); + else if (status == Event_timed::SLAVESIDE_DISABLED) + buf->append(STRING_WITH_LEN("SLAVESIDE_DISABLE")); else buf->append(STRING_WITH_LEN("DISABLE")); diff --git a/sql/event_data_objects.h b/sql/event_data_objects.h index e00b0b94eaf..a63340e67c8 100644 --- a/sql/event_data_objects.h +++ b/sql/event_data_objects.h @@ -22,17 +22,33 @@ #define EVEX_BAD_PARAMS -5 #define EVEX_MICROSECOND_UNSUP -6 - class sp_head; class Sql_alloc; - class Event_basic { protected: MEM_ROOT mem_root; public: + /* + ENABLED = feature can function normally (is turned on) + SLAVESIDE_DISABLED = feature is turned off on slave + DISABLED = feature is turned off + */ + enum enum_status + { + ENABLED = 1, + DISABLED, + SLAVESIDE_DISABLED + }; + + enum enum_on_completion + { + ON_COMPLETION_DROP = 1, + ON_COMPLETION_PRESERVE + }; + LEX_STRING dbname; LEX_STRING name; LEX_STRING definer;// combination of user and host @@ -57,20 +73,9 @@ protected: bool last_executed_changed; public: - enum enum_status - { - ENABLED = 1, - DISABLED - }; - - enum enum_on_completion - { - ON_COMPLETION_DROP = 1, - ON_COMPLETION_PRESERVE - }; - - enum enum_on_completion on_completion; - enum enum_status status; + int on_completion; + int status; + longlong originator; TIME last_executed; TIME execute_at; @@ -194,19 +199,10 @@ private: class Event_parse_data : public Sql_alloc { public: - enum enum_status - { - ENABLED = 1, - DISABLED - }; - enum enum_on_completion - { - ON_COMPLETION_DROP = 1, - ON_COMPLETION_PRESERVE - }; - enum enum_on_completion on_completion; - enum enum_status status; + int on_completion; + int status; + longlong originator; const uchar *body_begin; @@ -268,6 +264,7 @@ private: report_bad_value(const char *item_name, Item *bad_item); Event_parse_data(const Event_parse_data &); /* Prevent use of these */ + void Event_parse_data::check_originator_id(THD *thd); void operator=(Event_parse_data &); }; diff --git a/sql/event_db_repository.cc b/sql/event_db_repository.cc index 940930ec4c6..1b001db984c 100644 --- a/sql/event_db_repository.cc +++ b/sql/event_db_repository.cc @@ -94,7 +94,7 @@ const TABLE_FIELD_W_TYPE event_table_fields[ET_FIELD_COUNT] = }, { { C_STRING_WITH_LEN("status") }, - { C_STRING_WITH_LEN("enum('ENABLED','DISABLED')") }, + { C_STRING_WITH_LEN("enum('ENABLED','DISABLED','SLAVESIDE_DISABLED')") }, {NULL, 0} }, { @@ -118,6 +118,11 @@ const TABLE_FIELD_W_TYPE event_table_fields[ET_FIELD_COUNT] = { C_STRING_WITH_LEN("comment") }, { C_STRING_WITH_LEN("char(64)") }, { C_STRING_WITH_LEN("utf8") } + }, + { + { C_STRING_WITH_LEN("originator") }, + { C_STRING_WITH_LEN("int(10)") }, + {NULL, 0} } }; @@ -170,6 +175,9 @@ mysql_event_fill_row(THD *thd, TABLE *table, Event_parse_data *et, fields[ET_FIELD_STATUS]->store((longlong)et->status, TRUE); + fields[ET_FIELD_ORIGINATOR]->store((longlong)et->originator, TRUE); + + /* Change the SQL_MODE only if body was present in an ALTER EVENT and of course always during CREATE EVENT. @@ -535,7 +543,6 @@ Event_db_repository::create_event(THD *thd, Event_parse_data *parse_data, goto err; } - DBUG_PRINT("info", ("name: %.*s", parse_data->name.length, parse_data->name.str)); @@ -603,6 +610,8 @@ Event_db_repository::create_event(THD *thd, Event_parse_data *parse_data, if ((ret= mysql_event_fill_row(thd, table, parse_data, FALSE))) goto err; + table->field[ET_FIELD_STATUS]->store((longlong)parse_data->status, TRUE); + /* Close active transaction only if We are going to modify disk */ if (end_active_trans(thd)) goto err; diff --git a/sql/event_db_repository.h b/sql/event_db_repository.h index 1457fb64e2e..ff23b1f5c85 100644 --- a/sql/event_db_repository.h +++ b/sql/event_db_repository.h @@ -19,7 +19,7 @@ enum enum_events_table_field { - ET_FIELD_DB = 0, + ET_FIELD_DB = 0, ET_FIELD_NAME, ET_FIELD_BODY, ET_FIELD_DEFINER, @@ -35,6 +35,7 @@ enum enum_events_table_field ET_FIELD_ON_COMPLETION, ET_FIELD_SQL_MODE, ET_FIELD_COMMENT, + ET_FIELD_ORIGINATOR, ET_FIELD_COUNT /* a cool trick to count the number of fields :) */ }; diff --git a/sql/event_queue.cc b/sql/event_queue.cc index 068abbe3408..d951e926901 100644 --- a/sql/event_queue.cc +++ b/sql/event_queue.cc @@ -218,7 +218,8 @@ Event_queue::create_event(THD *thd, LEX_STRING dbname, LEX_STRING name) new_element= new Event_queue_element(); res= db_repository->load_named_event(thd, dbname, name, new_element); - if (res || new_element->status == Event_queue_element::DISABLED) + if (res || new_element->status == Event_queue_element::DISABLED + || new_element->status == Event_queue_element::SLAVESIDE_DISABLED) delete new_element; else { @@ -231,7 +232,6 @@ Event_queue::create_event(THD *thd, LEX_STRING dbname, LEX_STRING name) pthread_cond_broadcast(&COND_queue_state); UNLOCK_QUEUE_DATA(); } - DBUG_RETURN(res); } @@ -271,7 +271,7 @@ Event_queue::update_event(THD *thd, LEX_STRING dbname, LEX_STRING name, delete new_element; goto end; } - else if (new_element->status == Event_queue_element::DISABLED) + else if (new_element->status != Event_queue_element::ENABLED) { DBUG_PRINT("info", ("The event is disabled.")); /* diff --git a/sql/events.cc b/sql/events.cc index e6224915d6b..80ee613a6b9 100644 --- a/sql/events.cc +++ b/sql/events.cc @@ -347,7 +347,15 @@ Events::create_event(THD *thd, Event_parse_data *parse_data, bool if_not_exists) DBUG_RETURN(TRUE); } + /* + Turn off row binlogging of this statement and use statement-based + so that all supporting tables are updated for CREATE EVENT command. + */ + if (thd->current_stmt_binlog_row_based) + thd->clear_current_stmt_binlog_row_based(); + pthread_mutex_lock(&LOCK_event_metadata); + /* On error conditions my_error() is called so no need to handle here */ if (!(ret= db_repository->create_event(thd, parse_data, if_not_exists))) { @@ -357,6 +365,15 @@ Events::create_event(THD *thd, Event_parse_data *parse_data, bool if_not_exists) DBUG_ASSERT(ret == OP_LOAD_ERROR); my_error(ER_EVENT_MODIFY_QUEUE_ERROR, MYF(0)); } + else /* Binlog the create event. */ + { + if (mysql_bin_log.is_open()) + { + thd->clear_error(); + thd->binlog_query(THD::MYSQL_QUERY_TYPE, + thd->query, thd->query_length, FALSE, FALSE); + } + } } pthread_mutex_unlock(&LOCK_event_metadata); @@ -396,7 +413,15 @@ Events::update_event(THD *thd, Event_parse_data *parse_data, sp_name *rename_to) DBUG_RETURN(TRUE); } + /* + Turn off row binlogging of this statement and use statement-based + so that all supporting tables are updated for UPDATE EVENT command. + */ + if (thd->current_stmt_binlog_row_based) + thd->clear_current_stmt_binlog_row_based(); + pthread_mutex_lock(&LOCK_event_metadata); + /* On error conditions my_error() is called so no need to handle here */ if (!(ret= db_repository->update_event(thd, parse_data, new_dbname, new_name))) { @@ -406,6 +431,15 @@ Events::update_event(THD *thd, Event_parse_data *parse_data, sp_name *rename_to) DBUG_ASSERT(ret == OP_LOAD_ERROR); my_error(ER_EVENT_MODIFY_QUEUE_ERROR, MYF(0)); } + else /* Binlog the alter event. */ + { + if (mysql_bin_log.is_open()) + { + thd->clear_error(); + thd->binlog_query(THD::MYSQL_QUERY_TYPE, + thd->query, thd->query_length, FALSE, FALSE); + } + } } pthread_mutex_unlock(&LOCK_event_metadata); @@ -445,12 +479,27 @@ Events::drop_event(THD *thd, LEX_STRING dbname, LEX_STRING name, bool if_exists, DBUG_RETURN(TRUE); } + /* + Turn off row binlogging of this statement and use statement-based so + that all supporting tables are updated for DROP EVENT command. + */ + if (thd->current_stmt_binlog_row_based) + thd->clear_current_stmt_binlog_row_based(); + pthread_mutex_lock(&LOCK_event_metadata); /* On error conditions my_error() is called so no need to handle here */ if (!(ret= db_repository->drop_event(thd, dbname, name, if_exists))) { if (!only_from_disk) event_queue->drop_event(thd, dbname, name); + + /* Binlog the drop event. */ + if (mysql_bin_log.is_open()) + { + thd->clear_error(); + thd->binlog_query(THD::MYSQL_QUERY_TYPE, + thd->query, thd->query_length, FALSE, FALSE); + } } pthread_mutex_unlock(&LOCK_event_metadata); DBUG_RETURN(ret); diff --git a/sql/lex.h b/sql/lex.h index 45155da7692..6e0f1c711f2 100644 --- a/sql/lex.h +++ b/sql/lex.h @@ -467,6 +467,7 @@ static SYMBOL symbols[] = { { "SIGNED", SYM(SIGNED_SYM)}, { "SIMPLE", SYM(SIMPLE_SYM)}, { "SLAVE", SYM(SLAVE)}, + { "SLAVESIDE_DISABLE", SYM(SLAVESIDE_DISABLE_SYM)}, { "SNAPSHOT", SYM(SNAPSHOT_SYM)}, { "SMALLINT", SYM(SMALLINT)}, { "SOCKET", SYM(SOCKET_SYM)}, diff --git a/sql/slave.cc b/sql/slave.cc index 3a9cde42059..aa018f560ed 100644 --- a/sql/slave.cc +++ b/sql/slave.cc @@ -2387,10 +2387,25 @@ Slave SQL thread aborted. Can't execute init_slave query"); /* Print any warnings issued */ List_iterator_fast<MYSQL_ERROR> it(thd->warn_list); MYSQL_ERROR *err; + /* + Added controlled slave thread cancel for replication + of user-defined variables. + */ + bool udf_error = false; while ((err= it++)) + { + if (err->code == ER_CANT_OPEN_LIBRARY) + udf_error = true; sql_print_warning("Slave: %s Error_code: %d",err->msg, err->code); - - sql_print_error("\ + } + if (udf_error) + sql_print_error("Error loading user-defined library, slave SQL " + "thread aborted. Install the missing library, and restart the " + "slave SQL thread with \"SLAVE START\". We stopped at log '%s' " + "position %s", RPL_LOG_NAME, llstr(rli->group_master_log_pos, + llbuff)); + else + sql_print_error("\ Error running query, slave SQL thread aborted. Fix the problem, and restart \ the slave SQL thread with \"SLAVE START\". We stopped at log \ '%s' position %s", RPL_LOG_NAME, llstr(rli->group_master_log_pos, llbuff)); diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index ce7f34e3a06..de304976c0d 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -3866,7 +3866,6 @@ create_sp_error: if (check_access(thd, DELETE_ACL, "mysql", 0, 1, 0, 0)) goto error; - /* Does NOT write to binlog */ if (!(res = mysql_drop_function(thd, &lex->spname->m_name))) { send_ok(thd); diff --git a/sql/sql_show.cc b/sql/sql_show.cc index 881cf7dc6c4..6a6e7ce3225 100644 --- a/sql/sql_show.cc +++ b/sql/sql_show.cc @@ -52,7 +52,8 @@ enum enum_i_s_events_fields ISE_CREATED, ISE_LAST_ALTERED, ISE_LAST_EXECUTED, - ISE_EVENT_COMMENT + ISE_EVENT_COMMENT, + ISE_ORIGINATOR }; @@ -4393,10 +4394,23 @@ copy_event_to_schema_table(THD *thd, TABLE *sch_table, TABLE *event_table) } /* status */ - if (et.status == Event_timed::ENABLED) - sch_table->field[ISE_STATUS]->store(STRING_WITH_LEN("ENABLED"), scs); - else - sch_table->field[ISE_STATUS]->store(STRING_WITH_LEN("DISABLED"), scs); + + switch (et.status) + { + case Event_timed::ENABLED: + sch_table->field[ISE_STATUS]->store(STRING_WITH_LEN("ENABLED"), scs); + break; + case Event_timed::SLAVESIDE_DISABLED: + sch_table->field[ISE_STATUS]->store(STRING_WITH_LEN("SLAVESIDE_DISABLED"), + scs); + break; + case Event_timed::DISABLED: + sch_table->field[ISE_STATUS]->store(STRING_WITH_LEN("DISABLED"), scs); + break; + default: + DBUG_ASSERT(0); + } + sch_table->field[ISE_ORIGINATOR]->store(et.originator, TRUE); /* on_completion */ if (et.on_completion == Event_timed::ON_COMPLETION_DROP) @@ -4935,9 +4949,7 @@ int mysql_schema_table(THD *thd, LEX *lex, TABLE_LIST *table_list) TABLE *table; DBUG_ENTER("mysql_schema_table"); if (!(table= table_list->schema_table->create_table(thd, table_list))) - { DBUG_RETURN(1); - } table->s->tmp_table= SYSTEM_TMP_TABLE; table->grant.privilege= SELECT_ACL; /* @@ -5429,13 +5441,14 @@ ST_FIELD_INFO events_fields_info[]= {"SQL_MODE", 65535, MYSQL_TYPE_STRING, 0, 0, 0}, {"STARTS", 0, MYSQL_TYPE_TIMESTAMP, 0, 1, "Starts"}, {"ENDS", 0, MYSQL_TYPE_TIMESTAMP, 0, 1, "Ends"}, - {"STATUS", 8, MYSQL_TYPE_STRING, 0, 0, "Status"}, + {"STATUS", 18, MYSQL_TYPE_STRING, 0, 0, "Status"}, {"ON_COMPLETION", 12, MYSQL_TYPE_STRING, 0, 0, 0}, {"CREATED", 0, MYSQL_TYPE_TIMESTAMP, 0, 0, 0}, {"LAST_ALTERED", 0, MYSQL_TYPE_TIMESTAMP, 0, 0, 0}, {"LAST_EXECUTED", 0, MYSQL_TYPE_TIMESTAMP, 0, 1, 0}, + {"ORIGINATOR", 10, MYSQL_TYPE_LONG, 0, 0, "Originator"}, {"EVENT_COMMENT", NAME_LEN, MYSQL_TYPE_STRING, 0, 0, 0}, - {0, 0, MYSQL_TYPE_STRING, 0, 0, 0} + {0, 0, MYSQL_TYPE_STRING, 0, 0, 0} }; diff --git a/sql/sql_udf.cc b/sql/sql_udf.cc index 7dec58d9b6e..3ab161bb04f 100644 --- a/sql/sql_udf.cc +++ b/sql/sql_udf.cc @@ -403,6 +403,13 @@ int mysql_create_function(THD *thd,udf_func *udf) DBUG_RETURN(1); } + /* + Turn off row binlogging of this statement and use statement-based + so that all supporting tables are updated for CREATE FUNCTION command. + */ + if (thd->current_stmt_binlog_row_based) + thd->clear_current_stmt_binlog_row_based(); + rw_wrlock(&THR_LOCK_udf); if ((hash_search(&udf_hash,(byte*) udf->name.str, udf->name.length))) { @@ -466,6 +473,15 @@ int mysql_create_function(THD *thd,udf_func *udf) goto err; } rw_unlock(&THR_LOCK_udf); + + /* Binlog the create function. */ + if (mysql_bin_log.is_open()) + { + thd->clear_error(); + thd->binlog_query(THD::MYSQL_QUERY_TYPE, + thd->query, thd->query_length, FALSE, FALSE); + } + DBUG_RETURN(0); err: @@ -484,11 +500,20 @@ int mysql_drop_function(THD *thd,const LEX_STRING *udf_name) char *exact_name_str; uint exact_name_len; DBUG_ENTER("mysql_drop_function"); + if (!initialized) { my_message(ER_OUT_OF_RESOURCES, ER(ER_OUT_OF_RESOURCES), MYF(0)); DBUG_RETURN(1); } + + /* + Turn off row binlogging of this statement and use statement-based + so that all supporting tables are updated for DROP FUNCTION command. + */ + if (thd->current_stmt_binlog_row_based) + thd->clear_current_stmt_binlog_row_based(); + rw_wrlock(&THR_LOCK_udf); if (!(udf=(udf_func*) hash_search(&udf_hash,(byte*) udf_name->str, (uint) udf_name->length))) @@ -525,6 +550,15 @@ int mysql_drop_function(THD *thd,const LEX_STRING *udf_name) close_thread_tables(thd); rw_unlock(&THR_LOCK_udf); + + /* Binlog the drop function. */ + if (mysql_bin_log.is_open()) + { + thd->clear_error(); + thd->binlog_query(THD::MYSQL_QUERY_TYPE, + thd->query, thd->query_length, FALSE, FALSE); + } + DBUG_RETURN(0); err: rw_unlock(&THR_LOCK_udf); diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index 9c062407921..67251159327 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -813,6 +813,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b, ulong *yystacksize); %token SIGNED_SYM %token SIMPLE_SYM /* SQL-2003-N */ %token SLAVE +%token SLAVESIDE_DISABLE_SYM %token SMALLINT /* SQL-2003-R */ %token SNAPSHOT_SYM %token SOCKET_SYM @@ -1632,12 +1633,17 @@ ev_schedule_time: EVERY_SYM expr interval opt_ev_status: /* empty */ { $$= 0; } | ENABLE_SYM { - Lex->event_parse_data->status= Event_parse_data::ENABLED; + Lex->event_parse_data->status= Event_basic::ENABLED; + $$= 1; + } + | SLAVESIDE_DISABLE_SYM + { + Lex->event_parse_data->status= Event_basic::SLAVESIDE_DISABLED; $$= 1; } | DISABLE_SYM { - Lex->event_parse_data->status= Event_parse_data::DISABLED; + Lex->event_parse_data->status= Event_basic::DISABLED; $$= 1; } ; @@ -1667,13 +1673,13 @@ ev_on_completion: ON COMPLETION_SYM PRESERVE_SYM { Lex->event_parse_data->on_completion= - Event_parse_data::ON_COMPLETION_PRESERVE; + Event_basic::ON_COMPLETION_PRESERVE; $$= 1; } | ON COMPLETION_SYM NOT_SYM PRESERVE_SYM { Lex->event_parse_data->on_completion= - Event_parse_data::ON_COMPLETION_DROP; + Event_basic::ON_COMPLETION_DROP; $$= 1; } ; @@ -9832,6 +9838,7 @@ keyword_sp: | SIMPLE_SYM {} | SHARE_SYM {} | SHUTDOWN {} + | SLAVESIDE_DISABLE_SYM {} | SNAPSHOT_SYM {} | SOUNDS_SYM {} | SQL_CACHE_SYM {} |