bash 脚本意外删除了数据库,请救援

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/55323391/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-18 17:06:58  来源:igfitidea点击:

Deleted database accidentally by a bash script, rescue please

bashfilesystemsubuntu-14.04data-recoverydisaster-recovery

提问by SoftTimur

My developer committed a huge mistake and we cannot find our mongo database anyone in the server. Rescue please!!!

我的开发人员犯了一个巨大的错误,我们在服务器中找不到任何人的 mongo 数据库。求救!!!

He logged into the server, and saved the following shell under ~/crontab/mongod_back.sh:

他登录到服务器,并将以下 shell 保存在~/crontab/mongod_back.sh

enter image description here

在此处输入图片说明

And then he run ./mongod_back.sh, then there were lots of permission denied, then he did Ctrl+C. Then the server shut down automatically.

然后他跑了./mongod_back.sh,然后有很多,然后他跑permission deniedCtrl+C。然后服务器自动关闭。

He tried to restart the server, then he got an grub error:

他试图重新启动服务器,然后他收到一个 grub 错误:

enter image description here

在此处输入图片说明

He then contacted AliCloud, the engineer connected the disk to another working server, so that he could check the disk. Then, he realized that some folders have gone, including /data/where the mongodb is!!!

随后他联系了阿里云,工程师将磁盘连接到另一台正常工作的服务器,以便他可以检查磁盘。然后,他发现有些文件夹不见了,包括/data/mongodb在哪里!!!

1) We just don't understand how the bash could destroy the disk including /data/;

1)我们只是不明白bash如何破坏磁盘,包括/data/

2) And of course, is it possible to get the /data/back?

2)当然,有没有可能/data/拿回?

PS: he did not take a snapshot of the disk before.

PS:他之前没有对磁盘进行快照。

回答by Socowi

Question 1

问题 1

1) We just don't understand how the bash could destroy the disk including /data/;

1)我们只是不明白bash如何破坏包括/data/在内的磁盘;

Reason: $OUT_DIRwas unset

原因:$OUT_DIR未设置

In bashand shcomments are written as # comment, not // comment.
The following line will have the following effects

bashsh评论被写成# comment,而不是// comment
以下行将产生以下效果

someVariable=someValue // not a comment
  • Assign someValueto variable someVariable, but only for that one line. After that line the variable will go back to its old value, which is null in this case.
  • Execute the "command" // not a comment, that is the program //with the parameters not, a, and comment. Since //is just a directory (the same as /) this will cause an error message and nothing more.
  • 分配someValue给变量someVariable,但仅限于那一行。在该行之后,变量将返回其旧值,在本例中为 null。
  • 执行“命令” // not a comment,也就是该程序//与参数notacomment。由于//只是一个目录(与 相同/),这将导致错误消息,仅此而已。

Right now this behavior might seem strange, but you may have already used it in well known idioms like IFS= read -r lineor LC_ALL=C sort.

现在这种行为可能看起来很奇怪,但您可能已经在众所周知的习语中使用过它,例如IFS= read -r lineLC_ALL=C sort

Looking at your script the following lines probably caused the problem:

查看您的脚本,以下几行可能导致了问题:

OUT_DIR=/data/backup/mongodb/tmp // ...
...
rm -rf $OUT_DIR/*

I'm sorry to bring this to you, but you basically executed rm -rf /*since $OUT_DIRexpanded to the empty string.

很抱歉把这个带给你,但你基本上执行了rm -rf /*因为$OUT_DIR扩展到空字符串。

Potential Risk On Other Systems

其他系统的潜在风险

Even if $OUT_DIRwasn't empty the effect couldhave been the same since there is a //"comment" after rm. Consider the command

即使$OUT_DIR不为空的效果可能是一样,因为有一个//“注释”之后rm。考虑命令

rm -rf some // thing

This is supposed to delete the three files/directories some, //, and thing. As already pointed out //is the same directory as /.

这应该删除这三个文件/目录some//thing。正如已经指出的那样///.

However, mostimplementations of rmon Linux have a guard for this case and won't delete /so easily. On Ubuntu you will get the following warning (don't try this at home. Would suck if your rmdiffers.)

然而,Linux 上的大多数实现rm都有针对这种情况的保护,不会/那么容易删除。在 Ubuntu 上,您将收到以下警告(不要在家里尝试。如果您rm不同,会很糟糕。

$ rm -rf //
rm: it is dangerous to operate recursively on '//' (same as '/')
rm: use --no-preserve-root to override this failsafe

Question 2

问题2

2) And of cause, is it possible to get the /data/ back?

2)当然,是否有可能取回 /data/ ?

This is off-topic for StackOverflow. However, you can find manyanswerstothisquestiononotherstackexchangesites.

这是 StackOverflow 的题外话。但是,你可以找到很多答案这个问题其他stackexchange网站

There are recovery tools you can try, but there is no guarantee that you can restore your data if you don't have a backup.

您可以尝试使用一些恢复工具,但如果您没有备份,则无法保证您可以恢复数据。

回答by choroba

Switching between languages can be tricky! //is not a comment starter in shell, it's #. All the commands with these "comments" were parsed wrongly and skipped:

在语言之间切换可能很棘手!//不是 shell 中的注释启动器,它是#. 所有带有这些“注释”的命令都被错误地解析并跳过:

$ VAR=whatever // comment
bash: //: Is a directory
[$?=126]
$ echo "($VAR)"
()

Therefore, OUT_DIR=...was ignored and $OUT_DIRwas empty. It's easy to guess what

因此,OUT_DIR=...被忽略并$OUT_DIR为空。很容易猜到是什么

rm -rf $OUT_DIR/*

then did. It was basically equivalent to

然后做了。它基本上相当于

rm -rf /*

Use your backups to restore the database.

使用您的备份来恢复数据库。

回答by user11275761

I can read the Chinese wordings in comment field, from line 10, the user wants to create a temp folder but used cd, so if /data/backup/mongodb/tmpdoes not exist in the first place, then $OUT_DIR is empty or null, after that line 11 became rm -rf /*.

我可以在注释字段中读取中文措辞,从第 10 行开始,用户想要创建一个临时文件夹但使用了cd,因此如果/data/backup/mongodb/tmp首先不存在,则 $OUT_DIR 为空或 null,在第 11 行变为rm -rf /*.