MongoDB oplog操作日志详解(新手必看)
MongoDB 数据库的操作日志(oplog)是一种特殊的固定大小集合,用于滚动记录对数据库中存储数据的所有修改操作。如果写入操作未修改任何数据或失败,则不会创建操作日志条目。
与普通固定大小集合不同,操作日志可能会增长到超过配置的大小限制,从而避免删除 majority commit point(多数提交点)。
MongoDB 会对主节点应用数据库操作,并在主节点的操作日志中记录这些操作。然后,从节点成员会在异步流程中复制并应用这些操作。在 local.oplog.rs 集合中,所有副本集成员均包含此操作日志的副本,从而可以维持数据库的当前状态。
为了便于复制,所有副本集成员都会向所有其他成员发送 ping 消息,以确认彼此的状态。任何从节点都可以从其他成员导入操作日志条目。操作日志中的每个操作都是幂等的,即无论对目标数据集应用一次还是多次,操作日志的操作都会产生相同的结果。
默认的操作日志大小具有以下限制:
在大多数情况下,默认的操作日志大小是足够使用的。如果操作日志占可用磁盘空间的 5%,并在 24 小时的运行中被填满,那么从节点可以长达 24 小时停止从操作日志复制条目,并且不会由于过时太久而导致无法继续复制。然而,大多数副本集的操作量要低得多,它们的操作日志可以容纳更多的操作。
在 mongod 创建操作日志之前,可以使用 oplogSizeMB 选项指定其大小。首次启动副本集成员后,使用 replSetResizeOplog 管理命令更改操作日志大小。我们可以使用 replSetResizeOplog 选项动态调整操作日志的大小,而无须重启 mongod 进程。
默认情况下,MongoDB 不设置最小操作日志保留期,并自动从最旧的条目开始截断操作日志,以维持配置的操作日志最大的大小。
要在启动 mongod 时配置操作日志最短保留期,可执行以下任一操作:
要在正在运行的 mongod 上配置最短操作日志的保留期,可以使用 replSetResizeOplog 选项。在 mongod 运行时设置最短操作日志的保留期,会覆盖启动时设置的任何值。另外,必须更新相应配置文件设置或命令行选项的值,才能在服务器重启后继续保持这些更改。
相反,如果应用程序主要执行读取操作,并且仅执行少量写入操作,则一个较小的操作日志可能已经足够。
在特殊情况下,如要复制延迟和流量控制,操作日志更新可能会依据所需的性能时间进行延迟。使用来自从节点成员的 db.getReplicationInfo() 和复制状态输出,评估当前的复制状态并确定是否存在任何意外出现的复制延迟。
管理员可以限制主节点应用写入的速率,目标是 majority committed 选项延迟保持在可配置的 flowControlTargetLagSeconds 最大值以下。在默认情况下,流量控制设置为 enabled。
与普通固定大小集合不同,操作日志可能会增长到超过配置的大小限制,从而避免删除 majority commit point(多数提交点)。
MongoDB 会对主节点应用数据库操作,并在主节点的操作日志中记录这些操作。然后,从节点成员会在异步流程中复制并应用这些操作。在 local.oplog.rs 集合中,所有副本集成员均包含此操作日志的副本,从而可以维持数据库的当前状态。
为了便于复制,所有副本集成员都会向所有其他成员发送 ping 消息,以确认彼此的状态。任何从节点都可以从其他成员导入操作日志条目。操作日志中的每个操作都是幂等的,即无论对目标数据集应用一次还是多次,操作日志的操作都会产生相同的结果。
操作日志大小
当 MongoDB 数据库首次启动副本集节点时,如果未指定操作日志大小,MongoDB 会创建默认大小的操作日志。默认的操作日志大小具有以下限制:
- 默认最小操作日志大小为 990MB。如果 5% 的可用磁盘空间或物理内存(以存储引擎为准)小于 990MB,则默认的操作日志大小为 990MB;
- 默认最大的操作日志大小为 50GB。如果 5% 的可用磁盘空间或物理内存(根据存储引擎而定)大于 50GB,则默认操作日志大小为 50GB。
在大多数情况下,默认的操作日志大小是足够使用的。如果操作日志占可用磁盘空间的 5%,并在 24 小时的运行中被填满,那么从节点可以长达 24 小时停止从操作日志复制条目,并且不会由于过时太久而导致无法继续复制。然而,大多数副本集的操作量要低得多,它们的操作日志可以容纳更多的操作。
在 mongod 创建操作日志之前,可以使用 oplogSizeMB 选项指定其大小。首次启动副本集成员后,使用 replSetResizeOplog 管理命令更改操作日志大小。我们可以使用 replSetResizeOplog 选项动态调整操作日志的大小,而无须重启 mongod 进程。
最短操作日志保留期
在 MongoDB 数据库中,可以指定保留操作日志条目的最小小时数。在此期间,mongod 仅在以下两个条件都满足时才会删除操作日志条目:- 操作日志已达到最大配置大小;
- 操作日志条目早于根据主机系统时钟配置的小时数。
默认情况下,MongoDB 不设置最小操作日志保留期,并自动从最旧的条目开始截断操作日志,以维持配置的操作日志最大的大小。
要在启动 mongod 时配置操作日志最短保留期,可执行以下任一操作:
- 将 storage.oplogMinRetentionHours 设置添加到 mongod 配置文件中;
- 添加 --oplogMinRetentionHours 命令行选项。
要在正在运行的 mongod 上配置最短操作日志的保留期,可以使用 replSetResizeOplog 选项。在 mongod 运行时设置最短操作日志的保留期,会覆盖启动时设置的任何值。另外,必须更新相应配置文件设置或命令行选项的值,才能在服务器重启后继续保持这些更改。
可能需要更大操作日志的工作负载
在 MongoDB 数据库中,如果预计副本集的工作负载类似于以下模式(场景)之一,那么可能需要创建一个比默认值更大的操作日志:- 同时更新多个文档:为保持幂等性,操作日志必须将多次更新转换为单次操作。这会使用大量的操作日志空间,而数据大小或磁盘用量并未相应增长;
- 删除的数据量等于插入的数据量:如果删除的数据量与插入的数据量大致相同,则数据库的磁盘使用量不会显著上升,但操作日志却可能会变得很大;
- 大量就地更新:如果工作负载的很大一部分是不会增加文档大小的更新操作,则数据库会记录大量操作,但不会更改磁盘上的数据量。
相反,如果应用程序主要执行读取操作,并且仅执行少量写入操作,则一个较小的操作日志可能已经足够。
操作日志状态
在 MongoDB 数据库中,要查看操作日志的状态,包括操作的大小和时间范围,可以执行 rs.printReplicationInfo() 方法。在特殊情况下,如要复制延迟和流量控制,操作日志更新可能会依据所需的性能时间进行延迟。使用来自从节点成员的 db.getReplicationInfo() 和复制状态输出,评估当前的复制状态并确定是否存在任何意外出现的复制延迟。
管理员可以限制主节点应用写入的速率,目标是 majority committed 选项延迟保持在可配置的 flowControlTargetLagSeconds 最大值以下。在默认情况下,流量控制设置为 enabled。