我们将讨论在大规模数据下实现高性能,需要在许多重要维度上进行考虑的关键因素,其中包括:
我们在此介绍的最佳实践并非巨细无遗,但本系列中的一些建议还是非常有用的,无论你是:
我们从两个关键的考虑因素开始,它们是本系列其余部分中所讨论的性能最佳实践的基础。首先,我们将介绍模式设计和一些重要的资料,之后会讨论如何为应用程序最常访问的数据和索引来调整内存大小,也就是我们所说的“工作集”。
性能优化的第一步是了解应用程序的查询模式,以便于设计数据模型并选择合适的索引。根据应用程序的查询模式调整数据模型会让查询更加高效,提高插入及更新操作的吞吐量,并更有效地将工作负载分散到分片集群中。
MongoDB具有灵活的模式,但这并不意味着你可以忽略模式设计!尽管你可以随时对模式进行修改,但在项目开始时应用模式设计最佳实践可以避免以后潜在的重构工作。
JSON文档的一个主要优点是可以根据应用程序的需要灵活地对数据进行建模。由于文档能够嵌套数组和子文档,这使得它在对数据间的复杂关系进行建模时非常强大。同样也可以对平面、表格和列式结构、简单的键值对、文本、地理空间和时间序列数据,或是连接图形数据结构的节点和边进行建模。应用程序的查询模式决定了什么是最佳的模式设计。
在设计数据模型时,首先需要做的决定之一是如何对数据间的关系进行建模。决定何时应该使用内嵌文档,何时应该在不同集合中的文档之间建立引用,是特定于应用程序的。然而,在做模式设计时,有一些一般性的考虑可以来指导决策。
可以很自然地想到,具有一对一关系的数据可以嵌入到单个文档中。具有一对多关系的数据,如果其中“多”的一方总是与其父文档一起出现,或是会在其父文档的上下文中被查看,也最好通过内嵌来实现。因为这些数据总是被一起访问的,所以将它们存储在同一个文档中是最佳策略。
由于这种数据的局部性,内嵌方式通常为读操作提供了更好的性能,因为它能够在一个数据库内部操作中请求和检索相关数据,而不是对存储在不同集合中的文档进行查找。内嵌数据模型还可以在单个原子写入操作中更新相关数据,因为单个文档的写入是事务性的。
然而,并非所有的一对一和一对多关系都适合嵌入到单个文档中。在下列情况下,应该在不同集合中的文档间使用引用:
引用可以帮助解决上面提到的问题,并且通常在多对多关系建模时使用。但是,应用程序需要进行后续的查询来解析引用。这需要额外的服务器往返请求,或者需要使用MongoDB聚合管道中的$lookup操作符来执行“连接”操作。
数据建模是一个扩展性很强的话题,之前有很多文章对其进行了讨论。为了帮助你做出正确的决策,以下是一些值得查阅的关键资源摘要:
当开发了一个初始的数据模型并开始用一些应用程序的示例数据对其进行填充,就可以对其进行检查了。
MongoDB Compass是一个免费的MongoDB图形用户界面。你可以使用Compass做很多事情,它是我们在这个博客系列中会经常使用到的工具。它最有用的特性之一是模式可视化,能够以直方图的方式显示文档字段、数据类型和值。正如你将在本系列后面看到的,还可以直接从Compass的用户界面对查询计划和索引覆盖情况进行可视化浏览。
图1:在MongoDB Compass中对模式进行可视化展示
在图1中,我们检查存储在restaurants
集合中文档的模式。对于采样出的文档,Compass会显示字段在每个文档中出现的频率、它们包含的值范围和数据类型,以及categories数组中的元素个数。Compass文档中有更多关于如何分析模式的详细信息。
可以将Compass连接到自己管理的MongoDB实例或MongoDB Atlas上的云数据库。还可以使用数据浏览或“集合”视图直接从Atlas的用户界面查看文档结构。
探索和试验数据建模的最佳方法是在完全托管的Atlas云服务上启动MongoDB。
我们的文档将指导你如何在所选地区和云提供商中创建免费的MongoDB数据库集群。你还可以加载我们的样例数据集,这种方式可以使你很容易地熟悉文档模型。
除了数据建模,性能优化的第二个主要考虑因素就是工作集大小的调整。
与大多数数据库一样,当应用程序的工作集(索引和最常访问的数据)可适配进内存中时,MongoDB的性能最好。RAM大小是实例大小调整的最重要因素;如果RAM不足,其他优化可能无法显著提高数据库的性能。如果性价比比单纯的性能更重要,那么使用快速的固态硬盘来对RAM做一些适当的补偿是一个可行的设计选择。你应该通过测试来寻找工作负载和SLA的最佳平衡。
当应用程序的工作集适配进RAM时,从磁盘中进行读取的频率会很低。你可以使用我们本系列的下一篇关于查询分析的文章中介绍的工具对此进行分析。
如果工作集超过了所选实例大小或服务器的RAM,请考虑迁移到具有更多内存的实例,或者对数据库进行跨多个服务器的分区(分片)。
无论是在Atlas上运行MongoDB还是自己管理MongoDB,将工作集调整到合适的大小都是没错的。
在MongoDB Atlas中,对计算和存储的规模缩放非常简单。你可以勾选群集分档自动缩放,它将根据应用程序需求的变化来调整计算容量。
Atlas中的集群分档自动缩放在定义的时间段内监视CPU和内存利用率,并在配置的限制范围内扩展或收缩实例大小。由于所有缩放事件都以滚动的方式执行,因此对应用程序没有影响。在编写本文时,自动缩放是一个beta版特性。如果想自己控制缩放事件,那么只需在Atlas用户界面上单击几下,或者通过API进行调用就可以了。
这是性能最佳实践系列的第一篇文章。下一篇会介绍查询模式和分析。
原文:
Performance Best Practices: MongoDB Data Modeling and Memory Sizing
译者:牟天垒 MongoDB中文社区翻译委员
本文分享自 Mongoing中文社区 微信公众号,前往查看
如有侵权,请联系 cloudcommunity@tencent.com 删除。
本文参与 腾讯云自媒体同步曝光计划 ,欢迎热爱写作的你一起参与!