MongoDB 的数据可靠性,单机可靠性有望在1.8版本后增强
这几天在 MongoDB 的各个讨论区上又开始了关于 MongoDB 单机数据可靠性的讨论,原因是一位不太靠谱的同学在使用单台 MongoDB 做存储时丢失了他所有的数据。最后原因基本确定是因为此同学在停服务时暴力的使用了Kill -9 操作,但关于MongoDB 单机数据可靠性的问题又被提出了台面上,而这一次,MongoDB 官方也给出了一个与以往不同的态度。
下面是这次讨论的导火线
此哥们在twitter上抱怨他存在 MongoDB 里的数据全丢了,启动时加了repair也无法恢复。
这是他在Group 里的求助。
最后原因是这位仁兄暴力的执行了Kill -9 操作。为什么不能执行Kill -9?
这和 MongoDB 的存储方式有关,MongoDB 使用 mmap 的方式进行数据文件管理,也就是说写操作基本是在内存中进行的,写操作会被阶段性地flush到磁盘,而不是立刻写到磁盘的(默认是60秒,由 syncdelay 设定)。而在数据未开始flush前(比如在离上一次flush 59 秒时),我们如果执行 Kill -9 操作,则在这59秒内的写操作将全部丢失。但庆幸的是我们只是丢了这59秒内的这一部分数据。
而如果在我们进行flush 操作的时候执行Kill -9操作,则会造成数据文件错乱,一部分是新数据一部分是旧数据,那我们的所有数据可能就都不能恢复了。上面这位同学应该就是遇到了这种情况。
如何避免这种灾难?
当然首先是不要执行Kill -9,但是Kill -9其实只是相当于人为模拟了一次故障,如果真的出现断电,宕机等事故(暂不包括磁盘物理损坏),那还是会丢失数据的。
第二是通过replication 使用 一个slave,或者用replica set 来避免单结点数据丢失。
也就是说MongoDB 的单机可靠性无法保证了?没错!这正是MongoDb 的设计哲学。具体可以参见这里。
MongoDB 团队的反应
但是这一次MongoDB 并没有像之前一样横眉冷对千夫指,很快地,在 MongoDB 1.7 版本的最新分支上,就出现了一个新的数据可靠性选项(–dur)的支持。并且在数据文件修复工具上也有了一些改进。
如果在启动MongoDB时加上–dur 则MongoDB 会在进行写操作前记一份日志,这和在其他一些数据库中的binlog 类似,在MongoDB 数据文件损坏的情况下,可以使用此日志来进行恢复。据说其对性能的影响不大。
具体这一特性是否会合并到主干中,是否会成为默认选项,让我们拭目以待吧。
参考文章:MongoDB, Data Durability and Improvements coming in 1.8