Binlog events with binlog_format=MIXED are unconditionally logged in ROW format in some cases
Affects | Status | Importance | Assigned to | Milestone | |
---|---|---|---|---|---|
MySQL Server |
Unknown
|
Unknown
|
|||
Percona Server moved to https://jira.percona.com/projects/PS |
Fix Released
|
Medium
|
George Ormond Lorch III | ||
5.1 |
Invalid
|
Undecided
|
Unassigned | ||
5.5 |
Fix Released
|
Medium
|
George Ormond Lorch III | ||
5.6 |
Fix Released
|
Medium
|
George Ormond Lorch III |
Bug Description
Percona Server version:
Server version: 5.5.36-
When master and slave (with log-slave-updates enabled) are both running with MIXED mode replication and master executes a query that is logged in ROW format, after that query any other query that would be otherwise safe to log in STATEMENT format is unconditionally logged in ROW format.
The test case be repeated as follows:
-- Prepare the test case data on the master:
CREATE TABLE `t2` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`c` char(32) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=1018 DEFAULT CHARSET=latin1;
INSERT INTO `t2` VALUES (1, 'dummy'), (2, 'foo'), (3, 'ping'), (4, 'ding'), (5, 'ring');
create temporary table t2_temp(`id` int(11) NOT NULL, `c` char(32) DEFAULT NULL) ENGINE=InnoDB;
create index idx1 on t2_temp(id);
insert into t2_temp values(4, 'hello'), (5, 'world');
master [localhost] {msandbox} (test) > select * from t2;
+----+-------+
| id | c |
+----+-------+
| 1 | dummy |
| 2 | foo |
| 3 | ping |
| 4 | ding |
| 5 | ring |
+----+-------+
5 rows in set (0.00 sec)
master [localhost] {msandbox} (test) > select * from t2_temp
-> ;
+----+-------+
| id | c |
+----+-------+
| 4 | hello |
| 5 | world |
+----+-------+
2 rows in set (0.00 sec)
-- Now the below query when executed is correctly logged in ROW format on the master because it is an unsafe statement:
master [localhost] {msandbox} (test) > update t2, t2_temp set t2.c='updated' where t2.id=t2_temp.id;
Query OK, 2 rows affected (0.00 sec)
Rows matched: 2 Changed: 2 Warnings: 0
-- However the next simple insert is incorrectly logged in ROW format:
master [localhost] {msandbox} (test) > insert into t2 values(6, 'simple_insert');
Query OK, 1 row affected (0.00 sec)
This is true for any further queries that are executed, they are unconditionally logged in ROW format unless the connection is disconnected and a new connection to MySQL server is made.
-- Binary log events on the master:
mysqlbinlog -v data/mysql-
# at 602
#140428 21:24:34 server id 1 end_log_pos 759 Query thread_id=7 exec_time=0 error_code=0
SET TIMESTAMP=
SET @@session.
create temporary table t2_temp(`id` int(11) NOT NULL, `c` char(32) DEFAULT NULL) ENGINE=InnoDB
/*!*/;
# at 759
#140428 21:25:05 server id 1 end_log_pos 854 Query thread_id=7 exec_time=0 error_code=0
SET TIMESTAMP=
create index idx1 on t2_temp(id)
/*!*/;
# at 854
#140428 21:26:06 server id 1 end_log_pos 922 Query thread_id=7 exec_time=0 error_code=0
SET TIMESTAMP=
BEGIN
/*!*/;
# at 922
#140428 21:26:06 server id 1 end_log_pos 1037 Query thread_id=7 exec_time=0 error_code=0
SET TIMESTAMP=
insert into t2_temp values(4, 'hello'), (5, 'world')
/*!*/;
# at 1037
#140428 21:26:06 server id 1 end_log_pos 1106 Query thread_id=7 exec_time=0 error_code=0
SET TIMESTAMP=
COMMIT
/*!*/;
# at 1106
#140428 21:27:13 server id 1 end_log_pos 1183 Query thread_id=7 exec_time=0 error_code=0
SET TIMESTAMP=
BEGIN
/*!*/;
# at 1183
# at 1227
#140428 21:27:13 server id 1 end_log_pos 1227 Table_map: `test`.`t2` mapped to number 35
#140428 21:27:13 server id 1 end_log_pos 1303 Update_rows: table id 35 flags: STMT_END_F
BINLOG '
kateUxMBAAAALAA
kateUxgBAAAATAA
AARyaW5n/
'/*!*/;
### UPDATE test.t2
### WHERE
### @1=4
### @2='ding'
### SET
### @1=4
### @2='updated'
### UPDATE test.t2
### WHERE
### @1=5
### @2='ring'
### SET
### @1=5
### @2='updated'
# at 1303
#140428 21:27:13 server id 1 end_log_pos 1330 Xid = 350
COMMIT/*!*/;
# at 1330
#140428 21:28:03 server id 1 end_log_pos 1398 Query thread_id=7 exec_time=0 error_code=0
SET TIMESTAMP=
BEGIN
/*!*/;
# at 1398
# at 1442
#140428 21:28:03 server id 1 end_log_pos 1442 Table_map: `test`.`t2` mapped to number 35
#140428 21:28:03 server id 1 end_log_pos 1490 Write_rows: table id 35 flags: STMT_END_F
BINLOG '
w6teUxMBAAAALAA
w6teUxcBAAAAMAA
'/*!*/;
### INSERT INTO test.t2
### SET
### @1=6
### @2='simple_insert'
# at 1490
#140428 21:28:03 server id 1 end_log_pos 1517 Xid = 352
COMMIT/*!*/;
-- Binlog events on the slave
# at 463
#140428 21:24:34 server id 1 end_log_pos 620 Query thread_id=7 exec_time=0 error_code=0
SET TIMESTAMP=
create temporary table t2_temp(`id` int(11) NOT NULL, `c` char(32) DEFAULT NULL) ENGINE=InnoDB
/*!*/;
# at 620
#140428 21:25:05 server id 1 end_log_pos 715 Query thread_id=7 exec_time=0 error_code=0
SET TIMESTAMP=
create index idx1 on t2_temp(id)
/*!*/;
# at 715
#140428 21:26:06 server id 1 end_log_pos 783 Query thread_id=7 exec_time=0 error_code=0
SET TIMESTAMP=
BEGIN
/*!*/;
# at 783
#140428 21:26:06 server id 1 end_log_pos 898 Query thread_id=7 exec_time=0 error_code=0
SET TIMESTAMP=
insert into t2_temp values(4, 'hello'), (5, 'world')
/*!*/;
# at 898
#140428 21:26:06 server id 1 end_log_pos 967 Query thread_id=7 exec_time=0 error_code=0
SET TIMESTAMP=
COMMIT
/*!*/;
# at 967
#140428 21:27:13 server id 1 end_log_pos 1026 Query thread_id=7 exec_time=0 error_code=0
SET TIMESTAMP=
BEGIN
/*!*/;
# at 1026
# at 1070
#140428 21:27:13 server id 1 end_log_pos 1070 Table_map: `test`.`t2` mapped to number 34
#140428 21:27:13 server id 1 end_log_pos 1146 Update_rows: table id 34 flags: STMT_END_F
BINLOG '
kateUxMBAAAALAA
kateUxgBAAAATAA
AARyaW5n/
'/*!*/;
### UPDATE test.t2
### WHERE
### @1=4 /* INT meta=0 nullable=0 is_null=0 */
### @2='ding' /* STRING(32) meta=65056 nullable=1 is_null=0 */
### SET
### @1=4 /* INT meta=0 nullable=0 is_null=0 */
### @2='updated' /* STRING(32) meta=65056 nullable=1 is_null=0 */
### UPDATE test.t2
### WHERE
### @1=5 /* INT meta=0 nullable=0 is_null=0 */
### @2='ring' /* STRING(32) meta=65056 nullable=1 is_null=0 */
### SET
### @1=5 /* INT meta=0 nullable=0 is_null=0 */
### @2='updated' /* STRING(32) meta=65056 nullable=1 is_null=0 */
# at 1146
#140428 21:27:13 server id 1 end_log_pos 1173 Xid = 547
COMMIT/*!*/;
# at 1173
#140428 21:28:03 server id 1 end_log_pos 1232 Query thread_id=7 exec_time=0 error_code=0
SET TIMESTAMP=
BEGIN
/*!*/;
# at 1232
# at 1276
#140428 21:28:03 server id 1 end_log_pos 1276 Table_map: `test`.`t2` mapped to number 34
#140428 21:28:03 server id 1 end_log_pos 1324 Write_rows: table id 34 flags: STMT_END_F
BINLOG '
w6teUxMBAAAALAA
w6teUxcBAAAAMAA
'/*!*/;
### INSERT INTO test.t2
### SET
### @1=6 /* INT meta=0 nullable=0 is_null=0 */
### @2='simple_insert' /* STRING(32) meta=65056 nullable=1 is_null=0 */
# at 1324
#140428 21:28:03 server id 1 end_log_pos 1351 Xid = 549
COMMIT/*!*/;
Disconnecting the active connection and then reconnecting and then executing a similar INSERT query causes it to be logged correctly in STATEMENT format:
master [localhost] {msandbox} (test) > insert into t2 values(8, 'simple_
Query OK, 1 row affected (0.00 sec)
- binlog event on the master
# at 299
#140428 22:11:38 server id 1 end_log_pos 414 Query thread_id=5 exec_time=0 error_code=0
use `test`/*!*/;
SET TIMESTAMP=
DROP /*!40005 TEMPORARY */ TABLE IF EXISTS `t2_temp`
/*!*/;
# at 414
#140428 22:11:48 server id 1 end_log_pos 482 Query thread_id=6 exec_time=0 error_code=0
SET TIMESTAMP=
BEGIN
/*!*/;
# at 482
#140428 22:11:48 server id 1 end_log_pos 591 Query thread_id=6 exec_time=0 error_code=0
SET TIMESTAMP=
insert into t2 values(8, 'simple_
/*!*/;
# at 591
#140428 22:11:48 server id 1 end_log_pos 618 Xid = 39
COMMIT/*!*/;
- binlog event on the slave
# at 1546
#140428 21:43:18 server id 1 end_log_pos 1655 Query thread_id=9 exec_time=0 error_code=0
use `test`/*!*/;
SET TIMESTAMP=
insert into t2 values(8, 'simple_
/*!*/;
-- Binary log format on the master:
master [localhost] {msandbox} ((none)) > show variables like 'binlog_format';
+------
| Variable_name | Value |
+------
| binlog_format | MIXED |
+------
1 row in set (0.00 sec)
-- Binary log format on the slave:
slave1 [localhost] {msandbox} ((none)) > show variables like 'binlog_format';
+------
| Variable_name | Value |
+------
| binlog_format | MIXED |
+------
1 row in set (0.00 sec)
Related branches
- Laurynas Biveinis (community): Approve
-
Diff: 2662 lines (+779/-833)43 files modifiedmysql-test/extra/binlog_tests/drop_temp_table.test (+1/-0)
mysql-test/extra/binlog_tests/tmp_table.test (+0/-1)
mysql-test/extra/rpl_tests/rpl_drop_temp.test (+0/-4)
mysql-test/extra/rpl_tests/rpl_implicit_commit_binlog.test (+40/-15)
mysql-test/extra/rpl_tests/rpl_rewrt_db.test (+1/-3)
mysql-test/suite/binlog/r/binlog_database.result (+1/-2)
mysql-test/suite/binlog/r/binlog_format_switch_in_tmp_table.result (+0/-78)
mysql-test/suite/binlog/r/binlog_mix_drop_tmp_tbl.result (+57/-0)
mysql-test/suite/binlog/r/binlog_mix_tmp_table.result (+42/-0)
mysql-test/suite/binlog/r/binlog_row_tmp_table.result (+42/-0)
mysql-test/suite/binlog/r/binlog_stm_binlog.result (+8/-8)
mysql-test/suite/binlog/t/binlog_format_switch_in_tmp_table.test (+0/-76)
mysql-test/suite/binlog/t/binlog_mix_drop_tmp_tbl.test (+4/-0)
mysql-test/suite/binlog/t/binlog_mix_tmp_table.test (+2/-0)
mysql-test/suite/binlog/t/binlog_row_tmp_table.test (+2/-0)
mysql-test/suite/binlog/t/binlog_stm_drop_tmp_tbl.test (+1/-2)
mysql-test/suite/binlog/t/binlog_stm_tmp_table.test (+2/-0)
mysql-test/suite/rpl/r/rpl_bug58546.result (+44/-0)
mysql-test/suite/rpl/r/rpl_mix_drop_temp.result (+40/-0)
mysql-test/suite/rpl/r/rpl_mix_rewrt_db.result (+218/-0)
mysql-test/suite/rpl/r/rpl_mixed_drop_create_temp_table.result (+94/-118)
mysql-test/suite/rpl/r/rpl_mixed_implicit_commit_binlog.result (+3/-7)
mysql-test/suite/rpl/r/rpl_mixed_mixing_engines.result (+0/-12)
mysql-test/suite/rpl/r/rpl_non_direct_mixed_mixing_engines.result (+0/-12)
mysql-test/suite/rpl/r/rpl_stop_slave.result (+0/-46)
mysql-test/suite/rpl/r/rpl_temp_table_mix_row.result (+0/-111)
mysql-test/suite/rpl/t/rpl_bug58546.test (+69/-0)
mysql-test/suite/rpl/t/rpl_create_tmp_table_if_not_exists.test (+2/-1)
mysql-test/suite/rpl/t/rpl_mix_drop_temp-slave.opt (+2/-0)
mysql-test/suite/rpl/t/rpl_mix_drop_temp.test (+6/-0)
mysql-test/suite/rpl/t/rpl_mix_rewrt_db-slave.opt (+1/-0)
mysql-test/suite/rpl/t/rpl_mix_rewrt_db.test (+7/-0)
mysql-test/suite/rpl/t/rpl_row_reset_slave.test (+2/-2)
mysql-test/suite/rpl/t/rpl_stm_drop_temp.test (+6/-0)
mysql-test/suite/rpl/t/rpl_stm_reset_slave.test (+1/-1)
mysql-test/suite/rpl/t/rpl_stm_rewrt_db.test (+7/-0)
mysql-test/suite/rpl/t/rpl_stop_slave.test (+8/-88)
mysql-test/suite/rpl/t/rpl_temp_table_mix_row.test (+0/-210)
mysql-test/suite/rpl/t/rpl_trunc_temp.test (+3/-2)
sql/sql_class.cc (+38/-15)
sql/sql_class.h (+3/-18)
sql/sql_table.cc (+14/-1)
sql/sql_truncate.cc (+8/-0)
- Laurynas Biveinis (community): Approve
-
Diff: 2912 lines (+978/-685)49 files modifiedmysql-test/extra/binlog_tests/drop_temp_table.test (+1/-0)
mysql-test/extra/binlog_tests/tmp_table.test (+0/-1)
mysql-test/extra/rpl_tests/rpl_drop_temp.test (+0/-4)
mysql-test/extra/rpl_tests/rpl_implicit_commit_binlog.test (+40/-15)
mysql-test/extra/rpl_tests/rpl_innodb.test (+6/-1)
mysql-test/extra/rpl_tests/rpl_rewrt_db.test (+1/-3)
mysql-test/suite/binlog/r/binlog_database.result (+1/-2)
mysql-test/suite/binlog/r/binlog_format_switch_in_tmp_table.result (+0/-78)
mysql-test/suite/binlog/r/binlog_mix_drop_tmp_tbl.result (+56/-0)
mysql-test/suite/binlog/r/binlog_mix_tmp_table.result (+44/-0)
mysql-test/suite/binlog/r/binlog_row_tmp_table.result (+44/-0)
mysql-test/suite/binlog/r/binlog_stm_binlog.result (+8/-8)
mysql-test/suite/binlog/t/binlog_format_switch_in_tmp_table.test (+0/-76)
mysql-test/suite/binlog/t/binlog_mix_drop_tmp_tbl.test (+4/-0)
mysql-test/suite/binlog/t/binlog_mix_tmp_table.test (+2/-0)
mysql-test/suite/binlog/t/binlog_row_tmp_table.test (+2/-0)
mysql-test/suite/binlog/t/binlog_stm_drop_tmp_tbl.test (+1/-2)
mysql-test/suite/binlog/t/binlog_stm_tmp_table.test (+2/-0)
mysql-test/suite/rpl/r/rpl_bug58546.result (+47/-0)
mysql-test/suite/rpl/r/rpl_gtid_empty_transaction.result (+2/-2)
mysql-test/suite/rpl/r/rpl_mix_drop_temp.result (+43/-0)
mysql-test/suite/rpl/r/rpl_mix_innodb.result (+138/-0)
mysql-test/suite/rpl/r/rpl_mix_rewrt_db.result (+206/-0)
mysql-test/suite/rpl/r/rpl_mixed_drop_create_temp_table.result (+128/-168)
mysql-test/suite/rpl/r/rpl_mixed_implicit_commit_binlog.result (+3/-7)
mysql-test/suite/rpl/r/rpl_mixed_mixing_engines.result (+0/-66)
mysql-test/suite/rpl/r/rpl_non_direct_mixed_mixing_engines.result (+0/-66)
mysql-test/suite/rpl/r/rpl_stm_innodb.result (+2/-1)
mysql-test/suite/rpl/r/rpl_stop_slave.result (+0/-47)
mysql-test/suite/rpl/r/rpl_temp_table_mix_row.result (+3/-6)
mysql-test/suite/rpl/t/rpl_bug58546.test (+69/-0)
mysql-test/suite/rpl/t/rpl_create_tmp_table_if_not_exists.test (+2/-1)
mysql-test/suite/rpl/t/rpl_gtid_empty_transaction.test (+4/-4)
mysql-test/suite/rpl/t/rpl_mix_drop_temp-slave.opt (+2/-0)
mysql-test/suite/rpl/t/rpl_mix_drop_temp.test (+7/-0)
mysql-test/suite/rpl/t/rpl_mix_innodb.test (+11/-0)
mysql-test/suite/rpl/t/rpl_mix_rewrt_db-slave.opt (+1/-0)
mysql-test/suite/rpl/t/rpl_mix_rewrt_db.test (+7/-0)
mysql-test/suite/rpl/t/rpl_row_reset_slave.test (+2/-2)
mysql-test/suite/rpl/t/rpl_stm_drop_temp.test (+7/-0)
mysql-test/suite/rpl/t/rpl_stm_innodb.test (+1/-1)
mysql-test/suite/rpl/t/rpl_stm_reset_slave.test (+1/-1)
mysql-test/suite/rpl/t/rpl_stm_rewrt_db.test (+7/-0)
mysql-test/suite/rpl/t/rpl_stop_slave.test (+8/-88)
mysql-test/suite/rpl/t/rpl_trunc_temp.test (+3/-2)
sql/binlog.cc (+35/-13)
sql/sql_class.h (+3/-18)
sql/sql_table.cc (+17/-2)
sql/sql_truncate.cc (+7/-0)
Not repeatable with PS 5.1.73, its logging as a STATEMENT for all queries with binlog- format= MIXED.
nil@Dell- XPS:~/sandboxes /rsandbox_ Percona- Server- 5_1_73/ master/ data$ mysqlbinlog -v mysql-bin.000002 PSEUDO_ SLAVE_MODE= 1*/; max_insert_ delayed_ threads= 0*/; _TYPE=@ @COMPLETION_ TYPE,COMPLETION _TYPE=0* /;
/*!50530 SET @@SESSION.
/*!40019 SET @@session.
/*!50003 SET @OLD_COMPLETION
DELIMITER /*!*/;
....
# at 266 1401948125/ *!*/; 1401948130/ *!*/; 1401948130/ *!*/; 1401948135/ *!*/; 1401948140/ *!*/; 1401948145/ *!*/; 1401948145/ *!*/; 1401948145/ *!*/; 1401948193/ *!*/; 1401948193/ *!*/; 1401948203/ *!*/; 1401948203/ *!*/; TYPE=@OLD_ COMPLETION_ TYPE*/; PSEUDO_ SLAVE_MODE= 0*/; XPS:~/sandboxes /rsandbox_ Percona- Server- 5_1_73/ master/ data$
#140605 11:32:05 server id 1 end_log_pos 497 Query thread_id=1 exec_time=0 error_code=0
use `test`/*!*/;
SET TIMESTAMP=
CREATE TABLE `t2` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`c` char(32) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=1018 DEFAULT CHARSET=latin1
/*!*/;
# at 497
#140605 11:32:10 server id 1 end_log_pos 565 Query thread_id=1 exec_time=0 error_code=0
SET TIMESTAMP=
BEGIN
/*!*/;
# at 565
#140605 11:32:10 server id 1 end_log_pos 715 Query thread_id=1 exec_time=0 error_code=0
SET TIMESTAMP=
INSERT INTO `t2` VALUES (1, 'dummy'), (2, 'foo'), (3, 'ping'), (4, 'ding'), (5, 'ring')
/*!*/;
# at 715
#140605 11:32:10 server id 1 end_log_pos 742 Xid = 16
COMMIT/*!*/;
# at 742
#140605 11:32:15 server id 1 end_log_pos 899 Query thread_id=1 exec_time=0 error_code=0
SET TIMESTAMP=
create temporary table t2_temp(`id` int(11) NOT NULL, `c` char(32) DEFAULT NULL) ENGINE=InnoDB
/*!*/;
# at 899
#140605 11:32:20 server id 1 end_log_pos 994 Query thread_id=1 exec_time=0 error_code=0
SET TIMESTAMP=
create index idx1 on t2_temp(id)
/*!*/;
# at 994
#140605 11:32:25 server id 1 end_log_pos 1062 Query thread_id=1 exec_time=0 error_code=0
SET TIMESTAMP=
BEGIN
/*!*/;
# at 1062
#140605 11:32:25 server id 1 end_log_pos 1177 Query thread_id=1 exec_time=0 error_code=0
SET TIMESTAMP=
insert into t2_temp values(4, 'hello'), (5, 'world')
/*!*/;
# at 1177
#140605 11:32:25 server id 1 end_log_pos 1246 Query thread_id=1 exec_time=0 error_code=0
SET TIMESTAMP=
COMMIT
/*!*/;
# at 1246
#140605 11:33:13 server id 1 end_log_pos 1314 Query thread_id=1 exec_time=0 error_code=0
SET TIMESTAMP=
BEGIN
/*!*/;
# at 1314
#140605 11:33:13 server id 1 end_log_pos 1446 Query thread_id=1 exec_time=0 error_code=0
SET TIMESTAMP=
update t2, t2_temp set t2.c='updated' where t2.id=t2_temp.id
/*!*/;
# at 1446
#140605 11:33:13 server id 1 end_log_pos 1473 Xid = 22
COMMIT/*!*/;
# at 1473
#140605 11:33:23 server id 1 end_log_pos 1541 Query thread_id=1 exec_time=0 error_code=0
SET TIMESTAMP=
BEGIN
/*!*/;
# at 1541
#140605 11:33:23 server id 1 end_log_pos 1645 Query thread_id=1 exec_time=0 error_code=0
SET TIMESTAMP=
insert into t2 values(6, 'simple_insert')
/*!*/;
# at 1645
#140605 11:33:23 server id 1 end_log_pos 1672 Xid = 23
COMMIT/*!*/;
DELIMITER ;
# End of log file
ROLLBACK /* added by mysqlbinlog */;
/*!50003 SET COMPLETION_
/*!50530 SET @@SESSION.
nil@Dell-
------- ------- ------- ----- On slave-- ------- ------- ------- ---
nil@Dell- XPS:~/sa. ..