MySQL MASTER TO MASTER 复制在数据库级别工作,但不使用 Spring / Hibernate 的应用程序级别

MySQL MASTER TO MASTER replication working at DB level but not application level using Spring / Hibernate

我们正在使用 MySQL 和 MASTER TO MASTER 复制。

当我们直接使用 MySQL 监视器输入 SQL 语句时(即在 table 上执行 INSERT 或 DELETE),它会起作用(即复制到另一个数据库)。这已经通过两种方式进行了测试,即在每个数据库上查看它们是否都复制到另一个数据库(并且它们确实如此)。

但是,当我们使用我们的 Web 应用程序使用 Spring / Hibernate 来持久化数据时,它会正确保存到当前连接的数据库中,但不会复制到另一个数据库中!我不会认为这是可能的!

我查看了我能找到的日志文件: /var/log/mysqld.log 但看不到任何错误。

我该如何进一步调查?
我可以改进日志记录以使其更详细吗? 这有可能以某种方式实际绕过复制吗?我不这么认为,但我刚刚 运行 一系列测试来证明这一点。

事实证明,通过在 server.xml 的数据源 TAG 中为 Liberty WebSphere Appserver 指定数据库名称,它停止了复制!?

删除了 databaseName 属性,一切正常!

<dataSource id="athlete" jndiName="jdbc/myJNDIName">
    <jdbcDriver libraryRef="MySqlLib"/>
    **<properties databaseName="mydb"** 
    user="myuser" password="password" serverName="myserver" portNumber="3306"/>
</dataSource>

真正的原因是关于 STATEMENT 与基于 ROW 的二进制日志记录 - 我们使用的是基于语句的日志记录 - 已切换到基于 ROW 的日志记录,它现在工作正常。

如果使用基于语句的复制(5.1.71 的默认设置),如果为会话分配的数据库与正在复制的数据库不同,它将不会复制到另一个数据库。

https://dev.mysql.com/doc/refman/5.1/en/replication-options-slave.html#option_mysqld_replicate-do-db

<< 基于语句的复制。告诉从 SQL 线程将复制限制为默认数据库(即由 USE 选择的数据库)为 db_name 的语句。

>

答案是我们有基于 STATEMENT 的复制而不是基于 ROW 的复制!

Link 下面解释了基于 STATEMENT 的复制(默认和我们正在使用的)和基于 ROW 的复制 https://dev.mysql.com/doc/refman/5.1/en/replication-options-slave.html#option_mysqld_replicate-do-db

mysql> show variables like 'binlog_format';
+---------------+-----------+
| Variable_name | Value     |
+---------------+-----------+
| binlog_format | STATEMENT |
+---------------+-----------+

mysql> SET GLOBAL binlog_format = 'ROW';

/etc/my.cnf

#Setup binary logging
log_bin=/var/log/mysql/mysql-bin.log
binlog_do_db=MY_DATABASE
binlog-format=ROW