叶思斯,林志达,郭献彬,曹小明
(1.中国南方电网数字电网研究院有限公司,广东广州 510663;2.中国南方电网有限责任公司,广东广州 510670)
随着互联网行业的进一步发展,数据呈爆炸式增长趋势。大数据已经逐渐成为社会发展的重要组成部分,而社会也逐步迈入了大数据发展的时代[1]。但是随着数据量的逐渐增多,传统的储存方式已经无法适应当今的发展需求[2]。在此背景下,研究者开始寻求新兴的数据处理以及存储技术,其中,云存储技术作为一种通用型强、可靠性高等优势已经逐渐成为了大规模数据存储的重要技术之一[3]。所谓云存储技术是指一种基于云计算技术的新兴存储技术,当云计算技术可以和云存储技术相互转化,当云计算系统需要进行大量的数据存储以及管理工作时,云计算系统就可以转换为云存储技术。云储存技术也可以被看作为一种数据服务技术[4]。在实际应用中,云存储技术研究由于起步较晚,发展不够成熟,在使用方面往往存在着安全性较差、带宽限制以及数据管理等方面的问题[5]。这些问题严重制约了云储存技术的发展。而现阶段,针对云储存相关技术的设计与优化已经成为了互联网领域研究的热点问题,引发了研究者广泛关注。
NoSQL是近年来发展较快的一种云存储数据库类型,与传统数据库不同,NoSQL数据库不需要遵循基本要求,其数据存储方式也更加灵活[6]。其中MongoDB是NoSQL中功能最为丰富也是应用最长的数据库之一。MongoDB主要是面向文档的一种数据库类型,可以支持BSON格式的数据,数据存储模式自由、结构松散[7]。MongoDB应用优势显著,具有部署性强、性能高以及使用简便等优点。其语言查询功能强大,可实现关系数据库中绝大部分的查询功能,同时MongoDB也可以支持建立数据索引功能。
本研究基于MongoDB的基本理论与概念,提出了基于片键类型优化、数据查询优化以及数据存储优化3个方面的MongoDB分片集群系统优化方案。为检测优化效果,研究分别检测了在不同分片环境下的MongoDB数据插入性能以及数据查询性能,明确了优化效果。
本研究中的MongoDB分片集群部署构成示意图如图1所示。
图1 MongoDB分片集群部署示意图Fig.1 Schematic diagram of MongoDB sharding cluster deployment
由图1可知,在本研究中MongoDB分片集群主要由Mongos、config server、mongod以及monitor等主要模块组成[8]。其中,Mongos是整个MongoDB分片集群中的路由服务器。通过Mongos可以使MongoDB分片集群中的客户端以及服务端进行连接。用户发送的请求将通过Mongos发送至不同的服务器中。为进一步提高MongoDB的稳定性以及可靠性,在本研究中使用集群的方式对Mongos进行搭建。config server是存储数据分片以及数据块中具体信息的主要结构,当MongoDB运行时,config server负责将相关信息提供给Mongos,保证了Mongos的可靠性。同时,config server也可以扩展为集群。Mongod主要负责MongoDB的实际操作,包括数据块的存储、数据的查询、数据的插入以及数据的实例化等操作。而monitor在MongoDB分片集群中主要起到数据监控的作用。通过monitor可以监控系统的负载均衡状态、数据操作频率以及读写基本耗时等内容。
本研究主要从片键类型、数据查询以及数据存储3个方面对MongoDB进行系统优化分析。具体优化内容如下。
1.2.1 片键类型优化
片键是分片集群中最常用的索引,当设定MongoDB中的某个索引为片键时,分片集群会根据片键的设定来对数据进行划分[9]。同时在进行分片后,片键直接决定了数据的存放情况。因此片键的选择十分重要,不恰当的片键往往会使系统的性能降低,无法适应较高的访问量;而恰当的片键则可以进一步提高系统的性能,确保系统良好运行[10]。
常用的片键类型主要分为小基数片键、升序片键以及Hash片键等。本研究中小基数片键的数量有限,在实际使用时往往会产生众多体积较大且难以移动的数据块。升序片键则主要是以ID字段作为片键,在没使用升序片键时可以将最新产生的数据集中起来,可以大幅度提高数据的读取性能[11]。Hash片键是一种基于范围的分片形式,其主要优点为存储和读取的操作都均匀分布,并且消除了数据块过大的问题[12]。
基于实际需求和考虑,本研究选取了资源标签作为组合片键中的搜索键。同时,本文使用时段键来控制数据的局部化,时段键数目的取值需要保证在足够大的同时又不超出系统所能承受的最佳处理范围。本研究使用{Month:1,Label:1}的组合片键形式。其中Month字段作为主片键,表示资源上传的时间,Labe字段作为第二片键,表示系统资源。在设定中,系统运行超过两年时,即n>24,在这一范围内既可以保证数据的局部化又可以使每个时间段对应多个数据块。
1.2.2 数据查询优化
数据查询优化主要包括两方面的内容,分别是查询数据优化以及搜索键优化。在某些情况下,MongoDB会将查询后的结果分配到可能的几个分片内,随后将执行后的结果信息汇总起来反馈给客户端[13]。这种工作模式极容易造成资源的消耗,同时也增加了操作的使用时间。在本研究中主要采用sort()来排序查询数据,以片键中的第一个字段为排序依据,随后系统按照事先排序好的顺序进行查询,再将执行结果反馈给用户,降低反应时间以及资源占用程度。
搜索键的优化主要以时段键以及搜索键作为片键,该组合方式可以使同类型的数据集中在较少的分片上,有利于数据的查询以及下载操作。同时,本文将用户的ID作为搜索键的一部分,自动添加进搜索键的标签内容中,解决了用户在查询和读取本人的数据时系统查询负荷过大的问题。
1.2.3 数据存储优化
在MongoDB空间不足时需要自动申请相应的硬盘空间,申请空间的大小为64 M、128 M以及256 M并逐渐上升,最高申请上限为2G。但是在该种自动分片的机制下容易导致内存以及硬盘的占用。其示意图如图2所示。
图2 数据存储次序Fig.2 Data storage sequence
已知共有Shard01、Shard02以及Shard03 3个片,其负载分别为400、300以及700。假设此时需要插入一组新的数据,由于其数据储存是按照时间顺序进行排列的,因此当写入新数据时首先会写入到Shard03片中,此时则会导致shard03负载过高,而Shard01和Shard02负载过低,造成资源的浪费。因此在实际应用中常常需要使用数据均衡算法进行优化。而在MongoDB的优化算法中常常根据数据量的大小来统计负载的方式。此种方法在实际运行过程中存在诸多问题,实际应用效果较差。
为解决此问题,基于数据被查询的概率来进行系统的数据存储优化。该方案利用FODO算法思想进行实验数据存储优化,首先利用数据被查询的概率来计算查询负载,随后将所有存储对象按照查询负载由小到大派别,假设集群中的某一分片被删除,该片中的数据块就会以被查询的概率来决定存储的位置,进而提高查询的速度。
本研究利用FODO算法进行优化的步骤如下。
首先,计算出第i个数据块被访问的概率,公式如下所示:
其中,P为第i个数据块被查询的次数和全体数据被查询的次数的比值。由式(1)可以看出,对所有数据块而言,其分母均相同。因此P可以通过单位时间内数据块的查询次数排序来代替。
因此,在数据文档中添加查询的频率键F,其表达式为
其中,F表示第i个数据块被查询的频率。
在实际应用中发现,部分数据在不同的时间段查询的频率也不尽相同,为确保数据查询的时效性,需要统计最近一段时间的查询频率,而本研究通过调整资源可知,将时间段的长度设置为一个月是最佳的选择,因此将式(2)中的时间段长度设置为1个月,则该公式可以被改写为
又因为式(3)中的t为固定值,因此可以进一步简化式(3),即可得出一个月内的查询次数C,公式如下所示:
其中,Fit为第i个数据块在t时间段内的查询总数。
所有数据块的值的总和如下所示:
当开启新节点时,可以与链表中的其他对象所对应的C值进行对比,从而实现排序操作。在均衡器进行数据迁移时也可以根据数据块中对应的C值进行统计,分析存储对象的查询负载,决定数据点存储次序,从而实现数据的存储优化。
本研究主要测试环境如表1所示。
表1 实验测试环境Tab.1 Experimental test environment
2.1.1 3个不同分片环境下的插入分析
本研究主要讨论了升序片键、Hash片键以及优化片键这3种分片环境下MongoDB数据库的相关性能,具体讨论了在150万条数据插入时,数据的分布规律以及数据的写入速度,具体内容如图3-5所示。
由图3可知,在升序分片的环境下,数据插入后的分片差距过大,分布极不均衡。其中,Shard01的插入数据占比为81.94%,而Shard03的插入数据占比仅为18.06%,在Shard02区域甚至出现了没有数据输入的情况。而在Hash分片以及优化分片的情况下均可使数据较为均匀地分布在各个区域内。其中,在Hash片键的环境下,Shard01-Shard03的插入数据分布占比分别为30.42%、37.94%以及31.64%;而在优化片键的环境下Shard01-Shard03的插入数据分布占比分别为32.45%、35.34%以及32.21%;优化分片的效果略好于Hash分片。产生这种现象的主要原因是在升序分片中,当数据插入时往往会在最新的片上进行,造成数据分布不均。而优化分片拥有升序分片与Hash分片的优点,在保证数据确定分布的情况下又可以避免数据过度集中。
图3 升序片键数据插入性能分析Fig.3 Performance analysis of ascending slice key data insertion
图4 Hash片键数据插入性能分析Fig.4 Hash key data insertion performance analysis
图5 优化片键数据插入性能分析Fig.5 Optimized slice key data insertion performance analysis
在3种分片环境下,数据写入速度也有着较大的区别,当数据量分别在100万-700万条时,在升序片键环境下,数据写入速度为7000条/秒至9000条/秒。而在Hash片键以及优化片键的环境下,插入速度则在3000条/秒至4000条/秒之间。结果显示在升序分片的环境下,数据插入的速度最快。
2.1.2 插入方式测试
同时,本研究还分析了在优化片键分片的条件下,不同数据插入方式对MongoDB性能的影响,以插入所需时间作为评判依据,主要分析了批量插入以及逐条插入这两种数据插入方式的影响。具体结果如图6所示。
由图6可知,在数据量分别为100万条至700万条时,数据逐条插入以及数据批量插入时所需的时间基本相同,差距不大。结果表明,在该条件下插入方式的不同并不会影响MongoDB数据库的相关性能。
图6 逐条插入与批量插入的性能分析Fig.6 Performance analysis of strip insert and batch insert
本研究同时分析了在3种不同分片环境下数据查询的相关性能,本文以查询速度作为查询评价指标。具体结果如图7所示,其中图7(a)-7(c)分别为升序片键、Hash片键以及优化片键的数据查询速度结果。
由图7可知,当数据量分别为100万-700万条时,在升序片键的环境下,数据查询速度在4000条/秒至6000条/秒之间;在Hash片键的环境下,数据查询速度最小,基本维持在1000条/秒左右。而在优化片键的环境下,数据查询速度最大,在1万条/秒至1.2万条/秒之间。结果表明,在优化片键的环境下,MongoDB的查询性能最好。
本研究主要探讨了MongoDB集群的系统优化以及相关的测试研究。主要分析了在升序片键、Hash片键以及优化片键3种不同分片条件下数据的插入性能以及数据的查询性能。可得出如下结论:(1)在插入数据分布规律测试中,升序分片中数据分布差距较大,Shard01插入数据占比为81.94%,Shard03的插入数据占比仅为18.06%,而在Shard02区域无数据插入。(2)在Hash分片以及优化分片环境下数据分布较为均匀,其中,优化分片环境下速度分布最为均匀,3个区域的数据分布占比均在33%左右。(3)数据插入速度则是升序分片下速度最快,Hash分片以及优化分片的数据插入速度基本一致。同时,研究还表明,逐条插入以及批量插入这两种插入方式对MongoDB的数据插入所需时间并无明显影响。数据查询结果表明,在数据量分别为100万-700万条时,在优化片键的环境下,数据查询速度范围为1万条/秒至1.2万条/秒之间。在优化片键环境下查询速度最大,查询性能最好。综合上述结果可知,在优化后的分片环境下数据插入性能以及数据查询性能较高,使用本研究的优化方案可以有效地提高MongoDB集群的相关性能,从而提高MongoDB集群的使用效果。