MongoDB实战-复制(Part1复制概述和使用场景)

来源:互联网 发布:淘宝远程付款靠谱吗 编辑:程序博客网 时间:2024/06/07 14:41

    复制(replication)是大多数数据库管理系统的重要功能,因为故障是不可避免的。如果希望生产数据在故障之后也能保持可用状态,无必要确保生产数据库被部署在多台服务器上。在发生故障时,复制能提供高可用性与灾难恢复能力。

复制概述

    复制就是在多台服务器上分布并管理数据库服务器。MongoDB提供了两种复制风格:主从复制和副本集。两种方式都是在一个主节点进行写操作(写入的数据被异步地同步到所有的从节点上),并从从节点上读取数据。

    主从复制和副本集使用了相同的复制机制,但是副本集还能保证自动故障转移:如果主节点由于某些原因下线了,可能的话,会自动将一个从节点提升为主节点。副本集还提供了其他增强,比如更易于恢复和更高级的部署拓扑。出于这些原因,现在已经没什么有说服力的理由使用简单的主从复制了。副本集也因此是生产部署环境推荐的复制策略;

1.为什么复制很重要

    所有数据库都对其运行环境中的故障很敏感,而复制提供了一种抵御故障的机制。这里所指的故障包含哪些?

(1) 应用程序与数据库之间的网络连接丢失

(2) 计划停机,但服务器没有按照预定计划重新上线。任何机构的服务器都一定会安排偶尔停一下机,而其停机结果不太好预测。一次简单的重启至少能让数据库服务器下线几分钟,但问题是重启完成之后又会发生什么。新安装的软件或硬件经常会让操作系统无法正常启动。

(3) 断电。虽然大多数现代化数据中心都提供了冗余电源,但无法避免数据中心内部用户的错误、大范围局部暂时电视用电或者停电造成数据库服务器关闭

(4) 数据库服务器硬盘故障。硬盘通常都只有几年的平均无故障时间,他比你想象的更容易出故障。

      除了抵御外部故障,复制对于MongoDB的耐久性来说也很重要。如果运行时没有开启Journaling日志。遇到非正常关闭,无法保证MongoDB数据文件不受破坏。没有Journaling日志,就必须时刻运行复制,这才能保证一个节点以外关闭时能有一份数据文件的正确副本。

     当然,就算开启了Journaling日志,也应该使用复制,毕竟你追求高可用性和快速故障转移。此时Journaling日志会迅速完成恢复,因此只需简单地回放Journaling日志就能让故障节点重新上线。相比从现有副本重新同步(resyncing)或手动复制副本数据文件,这要快的多。

    无论是否开启了Journaling日志,MongoDB的复制功能都会大大增强整个数据库的可靠性,因此强烈推荐使用该功能。

2. 复制的使用场景

    复制可以帮助进行冗余、故障准仪、维护以及负载均衡。

    复制主要用来做冗余。本质上要保证复制节点与主节点保持同步。这些副本可以和主节点位于同一数据中心里,也可以分布在不同地理位置用于容灾。因为复制是异步的,任何节点间的网络延迟和分区(partition)都不会影响主节点的性能。作为另一种冗余的形式复制节点也可以与主节点保持一定的延时,万一用户无意间删除了一个集合,或者应用程序不知怎么的破坏了数据库,这还能提供一些防御措施。一般情况下,这些操作都会被立即复制;延时副本让管理员有时间做出反应,也许还能挽救他们的数据。

    有一点很重要:虽然他们是一种冗余,但副本不是备份的替代品。备份是数据库在过去某个特定时间的快照,但副本总是最新的。在一些情况下,数据集过大让备份显得不切实际,但通常来说,备份是种明智的做法,就算用了复制也推荐备份。

    复制的另外一个使用场景时故障转移。希望系统高可用,但仅在拥有冗余节点,并且在紧急情况下能切换到这些节点时,才能实现高可用。MongoDB的副本集通常都能方便地自动实现这种切换。

    除了提供冗余和故障转移,复制还可以简化维护工作,它允许你在主节点以外的节点上执行开销很大的操作。例如:通常都会在从节点上进行备份,不给主节点带来额外的负载,避免停机。另一个例子是构建大索引,因为构建的索引的开销很大,可以先从某个从节点上构建索引,然后主从切换,再在新的从节点上构建索引。

    最后,复制能够让你在副本间均衡读负载。赋予那些读负载占绝对比重的应用程序而言,这是扩展MongoDB最简答的途径。话虽如此,出现如下场景时,请不要用从节点来扩展读操作。

(1)所分配的硬件硬件无法给定的负载,如果使用的工作集远远大于给定内存,那么向从节点发送随机读请求仍然可能造成大量的磁盘访问,导致慢查询。

(2)读写比例超过50%。此处的问题是主节点上的所有写操作最终也会写入从节点,把读操作导向正在处理大量写入从节点有时会减缓复制过程,并不会提高吞吐量。

(3) 应用程序要求一致性读。从节点的复制是异步进行的,因此无法保证一定能读到主节点上最新写入的数据。在某些极端情况下,从节点可能延迟几个小时。

   因此,你能通过复制来均衡读负载,但仅限于特定场景。如果需要进行扩展,又出现了以上某种情况,那么你需要不同的策略,包括分片、升级硬件或者两者兼而有之。