2011-11-25 77 views
11

我想要实现的是有一个/etc/init.d脚本,它可以更可靠地启动Mongodb,即使它发生故障 - 它应该尝试进行自动修复,以防系统处于锁定状态。在生产中重新启动/自动修复Mongodb

是的,我可以自己编写这个脚本,但我认为有人在那里肯定已经做到了。

我注意到,在服务器出现故障后,Mongodb处于不通过/etc/init.d/mongod脚本重启的状态。很明显,锁文件需要被删除,并且需要先使用--repair选项启动,并且在成功重启之前首先更正--dbpath。在某些情况下,还需要将db文件的所有权更改为运行mongodb的用户。另外一个问题是,标准的/etc/init.d/mongod脚本在这种情况下不报告失败,而是在“OK”状态下返回快乐和错误地报告Mongod已经启动,尽管事实并非如此。

$ sudo /etc/init.d/mongod start 
Starting mongod: forked process: 9220 
all output going to: /data/mongo/log/mongod.log 
                  [ OK ] 
$ sudo /etc/init.d/mongod status 
mongod dead but subsys locked 

该操作系统是CentOS或Fedora。

有没有人修改过/etc/init.d脚本或指向这些脚本的指针,这些脚本会在这种情况下自动尝试修复?或者还有另外一个工具可以作为Mongod的看门狗吗?

任何意见,为什么它可能是一个坏主意,试图自动修复mongodb?

$ sudo /etc/init.d/mongod status 
mongod dead but subsys locked 

$ sudo ls -l /var/lib/mongo/mongod.lock 
-rw-r--r--. 1 mongod mongod 5 Nov 19 11:52 /var/lib/mongo/mongod.lock 


$ sudo tail -50 /data/mongo/log/mongod.log 
************** 
old lock file: /data/mongo/db/mongod.lock. probably means unclean shutdown 
recommend removing file and running --repair 
see: http://dochub.mongodb.org/core/repair for more information 
************* 
Sat Nov 19 11:55:44 exception in initAndListen std::exception: old lock file, terminating 
Sat Nov 19 11:55:44 dbexit: 

Sat Nov 19 11:55:44 shutdown: going to close listening sockets... 
Sat Nov 19 11:55:44 shutdown: going to flush oplog... 
Sat Nov 19 11:55:44 shutdown: going to close sockets... 
Sat Nov 19 11:55:44 shutdown: waiting for fs preallocator... 
Sat Nov 19 11:55:44 shutdown: closing all files... 
Sat Nov 19 11:55:44  closeAllFiles() finished 

Sat Nov 19 11:55:44 dbexit: really exiting now 

回答

4

所以首先要提到的是日志。日记有效地被称为“快速修复”。默认情况下,日记功能在2.0以上,默认情况下会执行“修复”。

因此,如果您的磁盘可以处理额外的日志记录吞吐量,这可能会解决您的问题。

任何意见,为什么它可能是一个坏主意尝试自动修复mongodb?

自动修复MongoDB的#1问题只是时间问题之一。

如果你有一个200GB的数据库,系统将修复时需要做到以下几点:

  1. 分配文件〜200GB(你有没有驱动器空间?)
  2. 阅读全部从现有文件中的数据到内存(200GB read
  3. 检查每个文档的有效性,并把它写回新文件(200GB write
  4. 重新创建所有索引(200GB reads + large number of writes
  5. 冲洗一切磁盘

如果你看一下我的笔记这是驱动颠簸严重金额进行修复。

但大多数生产安装正在运行副本集。在这种情况下,您可以从备份恢复而不是修复。从备份恢复只会写入数据一次,这是一个您应该已经拥有的过程。

尽管init.d脚本返回OK,您的系统监控应该会告诉您数据库没有启动。

+0

感谢您的详细解答。日记看起来像是要走的路。他们在哪个版本中引入了日记功能? – Tilo

+2

日志记录是在1.8+版本中引入的,只需在配置文件中设置“journal = true”即可。在2.0+日志记录默认情况下处于活动状态。请注意,日记不是“免费的”。它不适用于32位,它将使用额外的RAM,额外的磁盘空间和额外的IO。如果你做了很多就地更新(如计数器),这可能很重要。因此,在盲目推进生产之前,请测试日志模式。 –

+0

很好的回答!虽然它不是一个真正的脚本:)日记可能会诀窍。 32位对我来说不是问题。我会尝试日记!谢谢你的帮助! – Tilo

1

只想指出日记确实工作在32位版本。但是,它在32位默认情况下不会启用。

+0

这是正确的,日志记录是[禁用默认情况下](http://www.mongodb.org/display/DOCS/Journaling#Journaling-32bitnuances%3F)在32位版本,可以启用..但请注意,启用将减少可用于数据库的(已经有限的)内存量。有许多[32位版本的限制](http://www.mongodb.org/display/DOCS/32+bit),您应该始终使用64位进行制作。 – Stennie

+0

你绝对有你的答案错字... 32位和32位? ;) – Tilo

+0

Tilo,对不起,如果我的措辞因重复“32位”而变得尴尬。日记功能在32位版本中运行,但默认情况下不启用。 – user483263