如何为 MongoDB 选择 MMAPV1、WiredTiger 或 In-Memory StorageEngine?

How to choose from MMAPV1, WiredTiger or In-Memory StorageEngine for MongoDB?

在MongoDb Documentation 3.2 我看到他们支持3个存储引擎, MMAPV1,WiredTiger,In-Memory,到底选哪个很纠结。

我从描述中感觉 WiredTigerMMAPV1 好,但在其他来源中,他们说 MMAPV1 更适合大量读取......而 WiredTiger 更适合大量写入...... .

在选择一个而不是另一个时是否有一些限制? 有人可以提出一些最佳做法,例如

当我有这种类型的应用程序时,通常最好是这个,否则选择其他...

这是个人经验,但请查看此博客条目,它很好地解释了不同类型的引擎: Mongo Blog v3

Comparing the MongoDB WiredTiger and MMAPv1 storage engines.Higher Performance & Efficiency Between 7x and 10x Greater Write Performance MongoDB 3.0 provides more granular document-level concurrency control, delivering between 7x and 10x greater throughput for most write-intensive applications, while maintaining predictable low latency.

对我来说选择非常简单,我需要文档级锁,这使得 WiredTiger 成为理想选择,我们没有 mongo 的企业版,因此​​在内存引擎中不可用。 MMAPv1 Btree 是将内存映射到硬盘驱动器的非常基本的技术,效率不高。

The MMAP storage engine uses a process called “record allocation” to grab disk space for document storage. All records are contiguously located on disk, and when a document becomes larger than the allocated record, it must allocate a new record. New allocations require moving a document and updating all indexes that refer to the document, which takes more time than in-place updates and leads to storage fragmentation. Furthermore, MMAPv1 in it’s current iterations usually leads to high space utilization on your filesystem due to over-allocation of record space and it’s lack of support for compression. As mentioned previously, a storage engine’s locking scheme is one of the most important factors in overall database performance. MMAPv1 has collection-level locking – meaning only one insert, update or delete operation can use a collection at a time. This type of locking scheme creates a very common scenario in concurrent workloads, where update/delete/insert operations are always waiting for the operation(s) in front of them to complete. Furthermore, oftentimes those operations are flowing in more quickly than they can be completed in serial fashion by the storage engine. To put it in context, imagine a giant supermarket on Sunday afternoon that only has one checkout line open: plenty of customers, but low throughput!

每个人都有不同的要求,但在大多数情况下,WiredTiger 将是理想的选择,因为它在文档级别而不是集合级别进行原子操作具有很大的优势,您根本无法击败它。

更多读取而不是大量写入

如果阅读是您的主要关注点,这里是解决该问题的一种方法。

您可以通过以下方式调整 Mongo 驱动程序 Read Preference Modes

  1. 设置副本集,比如 1 个主副本和 3 个副副本。
  2. 将写入关注设置为 majority 这将使 写得慢一点(权衡)。
  3. 将阅读首选项设置为次要。

当你有很多读取时,这个设置会执行得很好,但作为权衡,写入会更慢。但是读取数据的吞吐量会很大。

如果您有其他问题,我希望这对您有所帮助,请将其添加为评论,我会尝试在此答案中解决。

您还可以检查 MMAPv1 vs WiredTiger 回顾并注意他是如何改变主意从 MMAPv1 到 WiredTiger 的。卖家正在锁定您无法超越的性能。

For new projects, I use WiredTiger now. Since a migration from a compressed to an uncompressed WiredTiger storage is rather easy, I tend to start with compression to enhance the CPU utilization ("get more bang for the buck"). Should the compression have a noticeable impact on performance or UX, I migrate to uncompressed WiredTiger.

MongoDB 数据库分析器

确定数据库需求的最佳方法是使用 MongoDB profiler 在其上设置测试集群和 运行 应用程序 与大多数数据库分析器一样,MongoDB 分析器可以配置为仅写入有关花费时间超过给定阈值的查询的分析信息。因此,一旦您了解了慢速查询,您就可以弄清楚它是读取还是写入,或者 cpu 还是 ram,然后从那里开始。

您应该使用由内存和 WiredTiger 存储引擎组成的副本集。并且你应该以这样一种方式对你的 MongoDB 进行分片,即内存中存储引擎应该访问最频繁的数据,其余的使用 WiredTiger 存储引擎。

在 2014 年收购 WiredTiger 后,MongoDB 引入了这个存储引擎作为他们的 default storage engine from version 3.2。此后,他们自己开始鼓励用户使用 WiredTiger,因为它比 MMAPV1 具有以下优点:

  • WiredTiger 使用文档级并发,而 MMAPV1 使用集合级锁定。这意味着多个用户可以使用 WiredTiger 而不是使用 MMAPV1 同时写入一个集合。
  • 由于 WiredTiger 管理自己的内存,因此它可以使用压缩,而 MMPAV1 没有任何此类功能。
  • WiredTiger 不允许任何就地更新。因此,最终它回收了不再使用的space。

到目前为止,我发现 MMPAV1 相对于 WiredTiger 的唯一优势是:

  • WiredTiger 在 Solaris 平台上不可用,而 MMPAV1 可用。
  • 即使在仅使用单个元素更新大文档时,WiredTiger 也会重写整个文档,从而使其速度变慢。

因此,您在选择存储引擎时始终可以将 MMPAV1 排除在外。现在让我们来谈谈内存存储引擎。从 MongoDB 企业版 3.2.6 开始,in-memory storage engine 是 64 位版本中普遍可用性 (GA) 的一部分。

与存储引擎相比,它有以下优点:

  • 与 WiredTiger 类似,内存存储引擎也允许文档级并发。
  • 内存存储引擎比其他引擎快很多。

    By avoiding disk I/O, the in-memory storage engine allows for more predictable latency of database operations.

但是这个存储引擎也有很多缺点:

  • The in-memory storage engine does not persist data after process shutdown.

  • 如果您的数据集太大,那么内存引擎不是一个好的选择。

    In-memory storage engine requires that all its data (including oplog if mongod is part of replica set, etc.) fit into the specified --inMemorySizeGB command-line option or storage.inMemory.engineConfig.inMemorySizeGB setting.

查看 MongoDB 手册,例如 Deployment Architectures 使用内存存储引擎。