速览
本文将从以下方面介绍数据库 MongoDB 4.4、5.0、6.0、7.0版本:
- MongoDB4.4 新特性
- 隐蔽索引(Hidden Indexes)
- 重界说分片键(Refinable Shard Keys)
- 复合哈希分片键(Compound Hashed Shard Keys)
- 对冲读(Hedged Reads)
- 同步建索引(Simultaneous Indexing)
- 复制读请求(Mirrored Reads)
- 基于时间保存Oplog(Time-Based Oplog Retention)
- MongoDB5.0 新特性
- 原生时间序列平台
- 在线数据重新分片
- Write Concern默认Majority级别
- 连担当理优化
- 长时间运行的快照查询
- 新版MongoDB Shell
- 可恢复的索引创建任务
- MongoDB6.0 新特性
- 可查询加密(Queryable Encryption)
- 集群同步(Cluster-to-Cluster Sync)
- 时序集合(Time Series Collection)
- 变动流(Change Streams)
- 聚合(Aggregation)
- 查询(Query)
- 弹性
- 安全性
- MongoDB7.0 新特性
- 支持分片元数据划一性校验
- 支持采样查询与分析分片键(analyzeShardKey)
- 自动合并(AutoMerger)
- MongoDB7.0 优化项
- 其他优化
- 安全性
- 聚合(Aggregation)
- 时序集合(Time-Series Collection)
- 分片(Sharding)
引言
在数据库技术日新月异的今天,MongoDB作为领先的NoSQL数据库之一,持续地推出新版本以满足不停变化的企业需求和技术寻衅。从MongoDB 4.4至7.0,每一版都融入了创新特性,旨在提升性能、扩展性、安全性和易用性,同时也反映了行业趋势和用户反馈。本文旨在全面分析这些版本中的关键新特性,不仅是为了记录技术演进的历史,更是为了赋能数据库管理员、开发者和架构师,使他们能够充分理解并使用这些新功能,从而优化数据管理和应用性能。
MongoDB 4.4版本新特性
隐蔽索引
MongoDB 4.4版本中新增了隐蔽索引,众所周知数据库维护太多的索引会导致写性能降落,但是往往业务上的复杂性导致了运维人员不敢轻易去删除一个潜在的低效率索引,担心误删除会带来业务性能的抖动,而重修索引的代价也非常大。
为了办理上述题目。该功能支持通过collMod下令隐蔽现有的索引,保证该索引在后续的查询中不会被使用。在观察一段时间后,确定业务没有非常即可以放心删除该索引。
- db.runCommand( {
- collMod: 'testcoll',
- index: {
- keyPattern: 'key_1',
- hidden: false
- }
- } )
复制代码 重界说分片键
MongoDB4.4版本中,您可以通过refineCollectionShardKey下令给现有的Shard Key增长一个或多个Suffix Field来改善现有的文档在Chunk上的分布题目。例如在上面描述的订单业务场景中,通过refineCollectionShardKey下令把Shard key更改为{customer_id:1, order_id:1},即可避免单一分片上的访问热门题目。
并且,refineCollectionShardKey下令的性能开销非常低,仅更改Config Server节点上的元数据,不需要任何情势的数据迁移,数据的打散仍旧在后续正常的Chunk自动分裂和迁移的流程中渐渐进行。别的,Shard Key需要有对应的Index来支撑,因此refineCollectionShardKey下令要求提前创建新Shard Key所对应的Index。
由于并不是全部的文档都存在新增的Suffix Field,因此在4.4版本中隐式支持了Missing Shard Key功能,即新插入的文档可以不包罗指定的Shard Key Field。但是由于很容易产生Jumbo Chunk,因此并不建议使用。
- db.adminCommand( {
- refineCollectionShardKey: "test.orders",
- key: { customer_id: 1, order_id: 1 }
- } )
复制代码 复合哈希分片键
在最新的4.4版本中参加了复合哈希索引,即您可以在复合索引中指定单个哈希字段,位置不限,可以作为前缀,也可以作为后缀,进而也就提供了对复合哈希片键的支持。
- sh.shardCollection(
- "examples.compoundHashedCollection",
- { "region_id" : 1, "city_id": 1, field1" : "hashed" }
- )
- sh.shardCollection(
- "examples.compoundHashedCollection",
- { "_id" : "hashed", "fieldA" : 1}
- )
复制代码 对冲读
页面的相应速度和经济损失直接挂钩。Google有一个研究报告表明,假如网页的加载时间高出3秒,用户的跳出率会增长50%。针对这个题目,MongoDB在4.4版本中提供了Hedged Reads功能,即在分片集群场景下,mongos节点会把一个读请求同时发送给某个分片的两个副本集成员,然后选择最快的返回结果回复客户端,来淘汰业务上的P95(指过去十秒内95%的请求延迟均在规定范围内)和P99延迟(指过去十秒内99%的请求延迟均在规定范围内)。
Hedged Reads功能作为Read Preference参数的一部门来提供, 因此可以在Operation粒度上进行设置,当Read Preference指定为nearest时,系统默认启用Hedged Reads功能,当指定为primary时,不支持Hedged Reads功能,当指定为其他时,需要显式地指定hedgeOptions才可以启用Hedged Reads。如下所示:
- db.collection.find({ }).readPref(
- "secondary", // mode
- [ { "datacenter": "B" }, { } ], // tag set
- { enabled: true } // hedge options
- )
- 此外,Hedged Reads也需要mongos开启支持,配置readHedgingMode参数为on,使mongos开启该功能支持。
- 参考代码:
- db.adminCommand( { setParameter: 1, readHedgingMode: "on" } )
复制代码 同步建索引
4.4 之前的版本中,索引的创建需要在主库中完成之后,才会到备库上实行。备库上的创建动作在不同的版本中,由于创建机制和创建方式的不同,对备库Oplog的影响也大有不同。
但即使在4.2版本中统一了前背景索引创建机制,使用了相当细粒度的加锁机制(只在索引创建的开始和竣事阶段对集合加独占锁),也会由于索引创建本身的CPU、IO性能开销导致复制延迟,或是由于一些特别操纵,例如使用collMod下令修改集合元信息,而导致Oplog的应用阻塞,乃至会由于主库历史Oplog被覆盖而进入Recovering状态。
在4.4版本中,主库和备库上的索引创建操纵是同时进行的,如许可以大幅淘汰上述情况所带来的主备延迟,即使在索引创建过程中,也可以保证备库访问到最新的数据。
别的,新的索引创建机制规定,只有在大多数具备投票权限节点返回成功后,索引才会真正生效。以是,也可以减轻在读写分离场景下由于索引不同而导致的性能差异。
复制读请求
在4.4版本中,MongoDB针对上述题目实现了Mirrored Reads功能,即主节点会按一定的比例把读流量复制到备库上实行,来帮助备库预热缓存。这是一个非阻塞实行(Fire and Forgot)的举动,不会对主库的性能产生任何实质性的影响,但是备库负载会有一定程度的上升。
流量复制的比例是可动态设置的,通过mirrorReads参数设置,默认复制1%的流量。
- db.adminCommand( { setParameter: 1, mirrorReads: { samplingRate: 0.10 } } )
- 此外,还可以通过db.serverStatus( { mirroredReads: 1 } )来查看Mirrored Reads相关的统计信息,如下所示:
- SECONDARY> db.serverStatus( { mirroredReads: 1 } ).mirroredReads
- { "seen" : NumberLong(2), "sent" : NumberLong(0) }
复制代码 基于时间保存Oplog
在4.4版本中,MongoDB支持通过storage.oplogMinRetentionHours参数界说需要保存的Oplog时长,也可以通过replSetResizeOplog下令在线修改这个值,参考代码如下:
- // First, show current configured value
- db.getSiblingDB("admin").serverStatus().oplogTruncation.oplogMinRetentionHours
- // Modify
- db.adminCommand({
- "replSetResizeOplog" : 1,
- "minRetentionHours" : 2
- })
复制代码 MongoDB 5.0版本新特性
原生时间序列平台
- 时间序列集合:MongoDB 5.0允许创建高度优化和压缩的时间序列集合,自动存储带有时间戳的数据,淘汰存储需求和I/O操纵,提升性能和可扩展性。
- 自动管理:时间序列集合能够自动处理数据的动态时间分区,适应不同的收罗频率,并能处理无序到达的丈量值。
- 简化开发:时间序列集合的创建和管理简化了开发流程,使开发者能够快速构建针对时间序列特性的高性能应用模型。
- 集成与流处理:通过MongoDB Connector for Apache Kafka,可以直接从Kafka主题中创建时间序列集合,实现数据的实时处理、聚合和写入。
- 智能索引与查询:时间序列集合自动创建时间排序的聚集索引,淘汰查询延迟,同时扩展了查询API,支持窗口函数和时间运算符,如移动均匀、累积总和、指数移动均匀等。
- 统一的数据平台:时间序列集合可以与常规MongoDB集合共存于同一数据库中,无需使用专用的时间序列数据库,低沉了维护多个数据库的本钱和复杂性。
创建时间序列数据集合的下令示例:
- db.createCollection("collection_name",{ timeseries: { timeField: "timestamp" } } )
复制代码 在线数据重新分片
数据库版本
| 特点
| 实现方法
| MongoDB 5.0从前
| 重新分片过程复杂且需要手动分片。
| 方法一:先dump整个集合,然后用新的分片键把数据库重新加载到一个新的集合中。
由于这是一个需要离线处理的过程,因此您的应用步伐在重新加载完成之前需要中断停服较长时间。例如:在一个三分片的集群上dump和重新加载一个10 TB以上的集合大概需要几天时间。
方法二:新建一个分片集群并重新设定集合的分片键,然后通过定制迁移方式,将旧分片集群中需要重新分片的集合,按新的分片键写入到新的分片集群中。
该过程中需要您自行处理查询路由和迁移逻辑、不停查抄迁移进度,以确保全部数据迁移成功。
定制迁移是高度复杂的、劳动密集型的、有风险的任务,而且耗时很长。例如:某个MongoDB用户花了三个月才完成100亿个document的迁移。
| MongoDB 5.0开始
| 运行reshardCollection下令即可启动重新分片。
重新分片的过程高效。
并不是简单地重新平衡数据,而是在背景将全部当前集合的数据复制并重新写入新集合,同时与应用步伐新的写入保持同步。
重新分片是完全自动化的。
将重新分片耗费的时间从几周或几个月压缩到几分钟或几小时,避免了冗长繁杂的手动数据迁移。
通过使用在线重新分片,可以方便地在开发或测试环境中评估不同分片键的效果,也可以在您需要时修改分片键。
| 您可以在业务运行(数据不停增长)的情况下,按需改变集合的分片键(Shard key),而不需要数据库停机或在数据集合中进行复杂的迁移。您只需要在MongoDB Shell中运行reshardCollection下令,选择您需要重新分片的数据库和集合,指定新的分片键即可。
reshardCollection: "<database>.<collection>", key: <shardkey>
阐明
<database>:需要重新分片的数据库名称。
<collection>:需要重新分片的集合名称。
<shardkey>:分片键的名称。
当您调用reshardCollection下令时,MongoDB会克隆现有集合,然后将现有集合中全部oplog应用到新集合中,当全部oplog被使用后,MongoDB会自动切换到新集合,并在背景删除旧集合。
| Write Concern默认Majority级别
从MongoDB 5.0开始,Write Concern默认级别为majority,仅当写入操纵被应用到Primary节点(主节点)且被持久化到大多数副本节点的日志中的时间,才会提交并返回成功,“开箱即用”地提供了更强的数据可靠性保障。
阐明
Write Concern是完全可调的,您可以自界说设置Write Concern,以平衡应用步伐对数据库性能和数据持久性的要求
连担当理优化
默认情况下,一个客户端毗连对应后端MongoDB服务器上的一个线程(net.serviceExecutor设置为synchronous)。创建、切换和烧毁线程都是消耗较大的操纵,当毗连数过多时,线程会占用MongoDB服务器较多的资源。
毗连数较多或创建毗连失控的情况称为“毗连风暴”,产生该情况的原因大概是多方面的,且常常是在服务已经受到影响的情况下发生。
针对这些情况,MongoDB 5.0接纳了以下步伐:
- 限定在任何时间驱动步伐尝试创建的毗连数量,以简单有效的方式防止数据库服务器过载。
- 淘汰驱动步伐监控毗连池时的查抄频率,给无相应或过载的服务器节点一个缓冲和恢复的机会。
- 驱动步伐将工作负载导向具有最健康毗连池的更快的服务器,而不是从可用的服务器中随机选择。
以上步伐,加上之前版本在mongos查询路由层的改进,进一步提升了MongoDB遭受高并发负载的本领。
长时间运行的快照查询
长时间运行的快照查询增长了应用步伐的通用性和弹性。您可以通过该功能运行默认时间为5分钟的查询(或将其调整为自界说持续时间),同时保持与实局势件性数据库划一的快照隔离,也可以在Secondary节点(从节点)上进行快照查询,从而在单个集群中运行不同的工作负载,并将其扩展到不同的分片上。
MongoDB通过底层存储引擎中一个名为Durable history的项目实现了长期运行的快照查询,该项目早在MongoDB 4.4中就已实现。Durable history将存储自查询开始以来全部变化的字段值的快照。通过使用Durable history,查询可以保持快照隔离,即使在数据发生变化的情况下,Durable history也有助于低沉存储引擎的缓存压力,使得业务可以在高写入负载的场景下实现更高的查询吞吐量。
新版MongoDB Shell
为了提供更好的用户体验,MongoDB 5.0从头开始重新设计了MongoDB Shell(mongosh),以提供一个更当代化的下令行体验,以及增强可用性的功能和强大的脚本环境。新版MongoDB Shell已经成为MongoDB平台的默认Shell。新版MongoDB Shell引入了语法高亮、智能自动完成、上下文帮助和有用的错误信息,为您创造一个直观、互动的体验。
可恢复的索引创建任务
MongoDB 5.0支持将正在进行中的索引创建任务在节点重新启动后自动会恢复至原来的位置,淘汰计划中维护动尴尬刁难业务的影响。例如:重新启动或升级数据库节点时,您不需要担心当前正在进行的大集合索引创建任务失效。
MongoDB 6.0版本新特性
可查询加密
紧张
可查询加密功能现在是预览(Preview)版本,不建议直接在生产环境使用。预览(Preview)版本的更多信息,请拜见MongoDB Releases Queryable Encryption Preview。
MongoDB 6.0新推出可查询加密功能,允许用户从客户端加密敏感数据,将其作为完全随机的加密数据存储在数据库服务器端,并对加密数据进行丰富的查询。
可查询加密只允许在客户端检察敏感数据的明文,在查询到达服务器端时会同时包罗从KMS获取的加密密钥,然后在服务器端以密文进行查询并返回,末了在客户端使用密钥解密后以明文出现。
可查询加密的特点如下:
- 从客户端加密敏感数据,只有客户端拥有加密密钥。
- 数据在整个生命周期(传输、存储、使用、审计和备份)中都是加密的。
- 客户端可以直接对加密数据进行丰富的查询(包罗等值匹配、范围、前后缀或子字符串等查询类型)。
- 强大的数据隐私保护本领,只有能访问客户端的应用步伐和加密密钥的授权用户才华看到明文数据。
- 更轻量化的应用步伐开发,涉及敏感数据的开发者无需考虑太多安全、合规的事变,数据库会直接提供综合加密办理方案。
- 低沉敏感数据上云的安全顾虑。
集群同步
无论是数据的同构同步(Mongo-to-Mongo)还是异构同步(Others-to-Mongo & Mongo-to-Others)都是MongoDB生态中的一部门,开源MongoDB推出了多种工具,比如mongoimport、mongoexport、mongodump和mongorestore等,但是这些工具并没有很好的规划数据同步。
MongoDB 6.0推出了新的同步工具mongosync,它能支持跨实例数据同步(两个MongoDB实例间连续且单向的数据同步)。用户还可以实时控制和监控整个同步过程,按需启动、停止、恢复乃至反转同步。
时序集合
分别从索引、查询以及排序多个方面增强了时序集合。
- 引入二级和复合索引,以改善读取性能。
- 引入针对时空数据的地理位置索引(Geo-Indexing),将地理信息添加到时序数据,有助于更好地分析涉及间隔和位置的场景。
场景示例:跟踪夏日冷链运输车的温度变化情况、监测特定航线上的货运船燃料消耗。
- 优化对时序数据的last point查询,不再需要扫描整个集合后才华查询到末了一个数据点。
- 优化对时序数据的排序,通逾期间以及元数据字段上的聚簇索引(Clustered Index)和二级索引(Secondary Index)更高效地完成排序操纵。
变动流
阐明
MongoDB 6.0之前的版本仅支持检察变动后的视图,从MongoDB 6.0版本开始,支持检察变动前后的视图。前后视图的更多信息,请拜见Change Streams with Document Pre- and Post-Images。
- 支持create、createIndexes、modify和shardCollection等DDL语句,更多信息,请拜见Change Events。
- Change Events新增wallTime字段,时间戳支持多种转换和展示算子(包罗$toDate、$tsSeconds和tsIncrement)以方便业务消费。
聚合
聚合功能允许用户处理多个文档并返回计算结果。通过将多个操纵符组合到聚合管道中,用户可以构建出足够复杂的数据处理管道以提取数据并进行分析。MongoDB 6.0在原有聚合功能的基础上,推出了如下新特性以及优化项:
- 分片集群实例支持$lookup和$graphLookup。
- 改进$lookup对JOINS的支持。
- 改进$graphLookup对图遍历的支持。
- 提升$lookup性能,部门场景中性能提升可达百倍。
查询
新增$maxN、$topN、$minN、$bottomN、$lastN和$sortArray等操纵符。通过操纵符可以将更多的计算从业务层下沉到数据库中,使得业务层更加轻量化。
弹性
MongoDB 6.0在原有弹性的基础上,推出了如下新特性以及优化项:
- 将数据块(Chunk)规格的默认值从64 MB调整为128 MB,有效低沉了数据迁移频率以及网络和路由层的开销。
- 支持configureCollectionBalancing下令,此下令支持的功能如下:
- 支持为不同的分片表设置不同的数据块规格。
示例:数据规模特别大的分片表,将数据块规格调整到256 MB。数据规模相对较小但盼望在分片上分布更匀称的分片表,将数据块规格调整到64 MB或32 MB。
您可以通过configureCollectionBalancing下令设置自动整理磁盘碎片,设置自动整理后您无需再自动使用compact下令来整理磁盘空间碎片,即可有效控制磁盘空间使用率
安全性
MongoDB 6.0在原有安全性的基础上,对客户端字段级加密(CSFLE, Client-Side Field-Level Encryption)功能进行了优化。CSFLE将支持任何符合密钥管理互通协议(KMIP,Key Management Interoperability Protocol)的密钥管理提供商,即除了基于KeyFile的当地密钥管理外,MongoDB支持通过KMIP与第三方密钥管理设备集成,为用户提供更安全的保障。
MongoDB 7.0版本新特性
支持分片元数据划一性校验
MongoDB 7.0版本中新增了checkMetadataConsistency下令,以查抄不同分片中元数据不划一的情况,示例如下。
示例1:
- // Command
- db.runCommand( {
- checkMetadataConsistency: 1,
- checkIndexes: true
- } )
- 示例2:
- //mongosh
- db.checkMetadataConsistency()
- db.collection.checkMetadataConsistency()
- sh.checkMetadataConsistency()
- 您可以在日常运维中增加该巡检项,尽早发现可能不一致的风险。更多信息请参见checkMetadataConsistency。
复制代码 支持采样查询与分析分片键
支持基于采样查询(Sampled queries)的结果来分析集合的分片键是否合理,可以帮助您更好地设计Schema以及分片键、更合理使用分片架构。核心下令analyzeShardKey的语法如下:
- db.adminCommand(
- {
- analyzeShardKey: <string>,
- key: <shardKey>,
- keyCharacteristics: <bool>,
- readWriteDistribution: <bool>,
- sampleRate: <double>,
- sampleSize: <int>
- }
- )
复制代码 阐明
尽管该下令并不会阻塞集合上的读写操纵,但为了低沉对业务的影响,建议配套使用secondary或secondaryPreferred模式的Read preference实行。mongos默认为secondaryPreferred模式。
更多信息请参考analyShardKey与configureQueryAnalyzer。
自动合并
MongoDB 7.0为自动均衡器(Balancer)实现了一个新的自动合并器(AutoMerger),当数据或索引分布不均衡、存在过多分片或进行数据迁移时,自动合并器会集并Chunks,以均衡数据并进步性能。MongoDB 7.0默认开启该功能,您也可以通过Balancer运动窗口的控制该功能。
之前版本引入用于单个集合数据均衡的configureCollectionBalancing下令也支持了AutoMerge:
- db.adminCommand(
- {
- configureCollectionBalancing: "<db>.<collection>",
- chunkSize: <num>,
- defragmentCollection: <bool>,
- enableAutoMerger: <bool>
- }
- )
- 除此之外,您也可以通过mergeAllChunksOnShard命令将一个分片上所有可合并的Chunk(或Range)进行手动合并:
- db.adminCommand( { mergeAllChunksOnShard: "db.coll", shard: "Shard0" } )
复制代码 分片
除了上文提到过的AutoMerger以外,还有以下优化项:
- 支持通过参数rangeDeleterHighPriority设置删除孤儿文档是否具备更高的优先级。通常业务的删除往往具有更高的优先级, 以是该参数默认为false。
- 不再支持用于记录目录缓存革新举动的operationsBlockedByRefresh监控指标,原由于基于mongos每个使用集合路由信息的操纵都会增长该计数器的次数。
- 新增关于Resharding的监控指标。
- addShard下令不再支持maxSize选项。
- 调整config.settings集合的chunksize时,增长了合理性校验,将值限定在[1,1024]。
- MongoDB在6.0.3版本后对Balancer计谋进行多少调整:
- Balancer不再依据分片间Chunks数量的差异,而是依据分片间数据量的差异进行均衡。
- 将Chunk的逻辑概念转为Range。
- 自动分裂(auto-splitting)只会在跨分片移动时发生。
- 检察集合分片信息
下面的SQL将"myDB"更换为所需要查询的DB名称即可 var dbName = "myDB";
- db.getSiblingDB(dbName).getCollectionNames().forEach(function(collName) { print("————————————————————————"); print("Collection: " + collName); db.getSiblingDB(dbName).getCollection(collName).getShardDistribution();});
复制代码 安全性
- 支持KMIP 1.0和1.1。
- 支持OpenSSL 3.0以及OpenSSL FIPS。
聚合
新增了以下操纵符,支持位计算和百分位数:
字段名
| 描述
| $bitAnd
| 返回Int或Long类型数值的按位与运算的结果。
| $bitNot
| 返回Int或Long类型数值的按位取反运算结果。
| $bitOr
| 返回Int或Long类型数值的按位或运算的结果。
| $bitXor
| 返回Int或Long类型数值的按位异或运算的结果。
| $median
| 返回近似中位数,相当于50百分位数。
| $percentile
| 返回指定的百分位数。
| 时序集合
- 移除了之前版本对于时序集合DELETE下令的操纵限定。除了不能在多文档变乱中使用干系删除下令外,当前DELETE下令再无其他限定。
- COMPACT下令支持时序集合。
其他优化
- 慢日志新增了catalogCacheIndexLookupDurationMillis等字段,更多信息请拜见log messages for slow queries。
- 支持动态调整存储引擎变乱并发度,之前默认是128,从MongoDB 7.0起,MongoDB会自动动态调整该并发度,更多信息请拜见Concurrent Storage Engine Transactions。
- currentOp新增了关于query sampling的全新字段,更多信息请拜见currentop-metrics。
- 支持复合通配符索引,更多信息请拜见Compound Wildcard Indexes。
- 新增$changeStreamSplitLargeEvent算子支持对高出16 MB的超大变动变乱(change events)进行切分,更多信息请拜见Large Change Stream Events。
- 优化基于Slot查询实行引擎的性能。
- 新增Chunk迁移的指标,更多信息请拜见New Sharding Statistics for Chunk Migrations。
- 支持通过USER_ROLES系统变量来获取当前User的脚色。
- 新增analyzeShardKey、balancer、queryAnalyzers干系的全局参数。
- serverStatus的返回结果新增更多字段,更多信息请拜见serverStatus Output Change。
公众号内直接回复加群也可以,扫码加群也可以,觉得帖子写的不错,点点关注,点点赞,多多转载,请多多支持。
免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。 |