MySQL二进制日志logging格式 – 磁盘填充

我有一个configuration了二进制日志logging的MySQL服务器实例。 我不做任何复制,但是二进制日志是我们恢复计划的一部分 – 能够重放自上次完全备份以来的所有事务。

不久之前,在一个已经运行了几个星期的系统上发现MySQL错误日志已经增长到超过5 GB的不规则大小。 查看日志,几乎每一行都写入了一条关于“写入二进制日志的不安全语句”的警告。

现在,我不控制使用数据库的应用程序,所以我无法尝试使这些语句“安全”。 所以,作为一个“修复”,我将binlog_formatconfiguration为MIXED ,而不是STATEMENT 。 这告诉MySQL在可能的情况下使用STATEMENT日志logging,但是回退到ROW日志logging带有不安全的语句。 这样做已成功地将错误日志的大小保持为可pipe理的大小。

然而,现在二进制日志的增长速度比以前快了很多(我今天在几个小时内看到了3GB的日志文件),大概是因为现在系统正在写入日志中的每一行都受到影响(“不安全“语句),对于影响大量行的语句,你可以得到图片。

所以,我发现自己在一个困难的地方。 如果我使用STATEMENT格式,二进制日志是可以pipe理的,但是在错误日志中会出现一些疯狂的警告。 如果我使用MIXED格式,那么错误日志是好的,但是二进制日志的增长速度足以在一天之内填满分区。

这让我想起了这个问题:这些“不安全”的言论究竟是怎么回事呢? 就像我说的,我没有任何复制,所以我不需要担心一台服务器与另一台服务器完全相同。 我只需要确保在需要从备份恢复的情况下,所有的数据都在那里。 “不安全”语句的日志logging会导致数据丢失,还是会出现某些行的顺序不同(可能还有不同的主键ID)的情况? 如果这不是一个大问题,那么我可以在错误日志中禁用警告(虽然这看起来很笨拙)。

否则,我可能会被迫彻底取消二进制日志logging,只能依靠恢复计划的潜在过期完整备份。

有什么build议在这种情况下?

基于行的复制格式实际上使用比基于语句更多的磁盘空间。 这很简单,因为在binlog中,您将拥有所有插入/更新的数据,而不仅仅是语句。 所以,如果一个语句说插入100行,如果binlog_format = STATEMENT将只插入一个语句,但是如果是ROW实际上将包含所有条目。

所以为了节省磁盘空间,你必须恢复到基于STATEMENT。 进入混合模式mysql会尝试写入一个STATEMENT到二进制日志中,但是在不安全的语句将会恢复到基于ROW的情况下。 在你的情况下,它看起来像你有许多不安全的陈述,所以你最终得到基于ROW的二进制日志。

你可以做一些事情

  • 将其保留为ROW并执行清理工作,将在一段时间后清除日志,这需要计算适合您的系统的内容。 在你删除日志之前,你应该把它们复制到别的地方,这样你就不会丢失它。

  • 通过第二个系统实现复制,并在主服务器上再次进行清理工作(确保从服务器同步,否则可能会丢失数据)

  • 仔细看看可能不安全的表述,这可能需要与应用程序的开发人员协作。