乐趣区

关于mongodb:使用WT工具恢复MongoDB数据

家喻户晓 MongoDB 的底层存储是由 WiredTiger 负责的,其数据文件也是.wt 格局。既然如此,咱们就有可能不通过 MongoDB 服务,而是间接用 wt 工具从数据文件中复原数据。尽管咱们通常举荐生产环境肯定要配置复制集,然而很无奈,技术社区曾经数次有人因为单机运行,最初硬盘损坏等起因导致无奈启动。wt 工具作为最初一根稻草,能够在放弃医治前再尝试解救一下。

编译

wt 工具能够运行于 Linux 和 Windows 上。因为各自的操作系统和 MongoDB 版本不同,可能产生较多的组合。在应用时应该依据本人状况编译适宜的版本。上面以 CentOS 7 为例演示编译过程。

1. 装置操作系统依赖

sudo yum install -y epel-release libtool automake snappy snappy-devel lz4 lz4-devel zstd zstd-devel libzstd-devel zlib zlib-devel git make vim-common

2. 筹备源码

git clone https://github.com/wiredtiger/wiredtiger.git

依据所应用的 MongoDB 版本,应该抉择正确的 wt 分支。例如我以后应用的 MongoDB 4.4.1,那么同样应该抉择 WiredTiger 的相应 tagmongodb-4.4.1

> git tag | grep 4.4.1
mongodb-4.4.1
mongodb-4.4.1-rc0
mongodb-4.4.1-rc1
mongodb-4.4.1-rc2
mongodb-4.4.1-rc3
mongodb-4.4.10
mongodb-4.4.10-rc0
mongodb-4.4.11-rc0
> git checkout tags/mongodb-4.4.1 -b v4.4.1

3. 编译源码

sh autogen.sh
./configure --disable-shared --with-builtins=lz4,snappy,zlib,zstd
make -j $(nproc)
make install

简略起见咱们应用了 –disable-shared 来将动态链接库间接打包到执行文件中,这样能够防止很多后续的麻烦,代价是生成的执行文件较大。

编辑数据

如果有幸 dbpath 中的其余文件没有失落,包含:

WiredTiger*

要复原的汇合的 collection-xxx.wt

与要复原汇合相干的 index 文件

则能够间接应用 wt 工具复原数据了:

wt dump file:collection-10--2280053313118266952.wt

不过,如果所有货色都还在的话,为什么还要用 wt 来复原呢?所以我置信大部分人到这里都是跑不上来的。所以来看下一步,当你丢到只剩个裤衩子的时候该怎么办。

数据恢复

wt 读取数据的根本前提条件是要有元数据,也就是 WiredTiger* 那堆文件。那咱们就来尝试结构这些文件:

mkdir temp
cd temp
touch WiredTiger WiredTiger.lock
wt list

为了简略起见,后续步骤咱们没有应用 wt 来实现,而是应用 MongoDB:

mongod --dbpath ./
启动另一个窗口,应用 mongo shell 连贯到以后实例:

mongo
任意创立一个汇合,咱们将把数据恢复到这个汇合中:

db.dump.insert({x: 1});
db.dump.stats().wiredTiger.uri
# statistics:table:collection-7-666354062479792805

collection-7-666354062479792805.wt 即咱们要应用的指标文件名。此时应:

进行 mongod(间接 ctrl-c)

应用咱们要复原的文件笼罩上述文件

cp collection-10--2280053313118266952.wt collection-7-666354062479792805.wt

让 wt 帮咱们修复文件:


wt salvage file:collection-7-666354062479792805.wt

重启 mongod 过程:

mongod --dbpath ./
再次应用 shell 连贯到 MongoDB,在 dump 汇合中即可找到咱们要复原的数据。

留神此时汇合数据尽管恢复正常,但如果你 count() 就会发现返回后果是 1。不必放心,这个问题很容易修复:

db.dump.validate({full: true});
上面该怎么办大家心里有数了吗?

对于作者:张耀星

MongoDB 大中华区首席征询参谋,供职于 MongoDB 售后服务团队 5 年 +,领有近 10 年 MongoDB 应用教训。

退出移动版