壹、介绍

在曾经做某个项目的开发时,采用FTP传输文件,但是有时会出现网络抖动及其他意外情况(例如被人为剪切),导致接收端接收了损坏文件,但是却不自知,而导致接下来的流程报错。

那怎样去避免这种情况呢?

我们做了几种文件校验的机制,例如包大小、包签名,而在Linux中,有个简单的命令就可以实现这个功能:md5sum。

md5sum可以用来生成文件的md5码,跟随文件一起发给接收端,接收端接收文件后验证发送过来的md5码与当前文件生成的md5码是否一致,就可以判断文件是否完整,有没有损坏、被篡改。

MD5算法常常被用来验证网络文件传输的完整性,防止文件被人篡改。MD5全称是报文摘要算法(Message-Digest Algorithm 5),此算法对任意长度的信息逐位进行计算,产生一个二进制长度为128位(十六进制长度就是32位)的“指纹”(或称“报文摘要”),不同的文件产生相同的报文摘要的可能性是非常非常之小的。

一般来说,安装了Linux后,就会有md5sum这个工具,直接在命令行终端直接运行。

贰、命令

语法

md5sum[选项][文件]

选项

-b或--binary:  把输入文件作为二进制文件看待。
-t或--text:    把输入的文件作为文本文件看待(默认)。
-c或--check:   用来从文件中读取md5信息检查文件的一致性。(不细说了参见info)
--status:      这个选项和check一起使用,在check的时候,不输出,而是根据返回值表示检查结果。
-w或--warn:    在check的时候,检查输入的md5信息又没有非法的行,如果有则输出相应信息。

注意

md5sum命令可以用来显示或检查 MD5(128-bit) 校验和。

若没有文件选项,或者文件处为”-“,则从标准输入读取。

校验和会按照RFC 1321 规范生成。当进行检查时,给出的输入格式应该和程序的输出样板格式相同。

默认的输出模式时输出一行校验和的校验结果,并有一个字符来表示文件类型(“*“代表二进制,” “代表纯文本),并同时显示每个文件的名称。

叁、示例

准备

我们先随便准备几个示例文件 1.txt、2.txt、ymm2.txt、ymm3.txt,内容随意

[root@yaomm ~]# cat 1.txt 
我是姚毛毛,这是《Linux常用命令》4
[root@yaomm ~]# cat 2.txt 
我是姚毛毛,这是《Linux常用命令》
我是姚毛毛,这是《Linux常用命令》2
我是姚毛毛,这是《Linux常用命令》3
我是姚毛毛,这是《Linux常用命令》3
我是姚毛毛,这是《Linux常用命令》4
我是姚毛毛,这是《Linux常用命令》5
我是姚毛毛,这是《Linux常用命令》4
我是姚毛毛,这是《Linux常用命令》4
[root@yaomm ~]# cat ymm2.txt
我是姚毛毛,这是《Linux常用命令》
我是姚毛毛,这是《Linux常用命令》2
我是姚毛毛,这是《Linux常用命令》3
我是姚毛毛,这是《Linux常用命令》3
我是姚毛毛,这是《Linux常用命令》4
我是姚毛毛,这是《Linux常用命令》5
我是姚毛毛,这是《Linux常用命令》4
我是姚毛毛,这是《Linux常用命令》5
我是姚毛毛,这是《Linux常用命令》5
我是姚毛毛,这是《Linux常用命令》5
我是姚毛毛,这是《Linux常用命令》5
[root@yaomm ~]# cat ymm3.txt 
11123
111234

命令

md5sum -b [文件]以二进制方式读取,生成md5码

[root@yaomm ~]# md5sum -b ymm2.txt ## 以二进制方式读取,生成md5码文件
40b5f9f01a0410cdb6d3b69cee62df45 *ymm2.txt ## 命令结果

md5sum [文件]无参方式生成md5码,等同-b

[root@yaomm ~]# md5sum ymm2.txt ## 效果与 -b 相同
40b5f9f01a0410cdb6d3b69cee62df45  ymm2.txt

存储md5校验文件,使用 md5sum -c [文件] 进行校验

[root@yaomm ~]# md5sum ymm2.txt > ymm2.md5
[root@yaomm ~]# md5sum -c ymm2.md5
ymm2.txt: OK

md5sum *.txt > list.md5 批量生成md5码文件,批量校验

[root@yaomm ~]# md5sum *.txt > list.md5
[root@yaomm ~]# cat list.md5
80ff50c1f45db4c4b104ef4bd07b9d9e  1.txt
8fea821f48194e38d9220528762e5f96  2.txt
40b5f9f01a0410cdb6d3b69cee62df45  ymm2.txt
2cb6f4f5f8432208ea168d9519b2df40  ymm3.txt
[root@yaomm ~]# md5sum -c list.md5
1.txt: OK
2.txt: OK
ymm2.txt: OK
ymm3.txt: OK

修改源文件,再重新使用md5文件校验

[root@yaomm ~]# echo '追加内容,改变md5' >> ymm2.txt 
[root@yaomm ~]# md5sum -c list.md5
1.txt: OK
2.txt: OK
ymm2.txt: FAILED
ymm3.txt: OK
md5sum: WARNING: 1 computed checksum did NOT match

若没有文件选项,则从标准输入读取

[root@yaomm ~]# echo '我是姚毛毛' | md5sum
b4d1ffab9db62c65896a7365bb8cb766  -

将刚才echo输出的我是姚毛毛放入文本文件中,我们再看看md5码是不是一致的

[root@yaomm ~]# echo '我是姚毛毛' > ymm4.txt
[root@yaomm ~]# md5sum ymm4.txt
b4d1ffab9db62c65896a7365bb8cb766  ymm4.txt

可以看到是一毛一样的

tips

怎么只提取md5sum输出的md5码,而不要文件名呢?

Linux下多种方法都可以,这里说两个简单的命令,一个是cut,一个是awk

示例1:cat list.md5 | cut -d" " -f1

[root@yaomm ~]# cat list.md5 | cut -d" " -f1
80ff50c1f45db4c4b104ef4bd07b9d9e
8fea821f48194e38d9220528762e5f96
40b5f9f01a0410cdb6d3b69cee62df45
2cb6f4f5f8432208ea168d9519b2df40

示例2:cat list.md5 | awk '{print $1}'

[root@yaomm ~]# cat list.md5 | awk '{print $1}'
80ff50c1f45db4c4b104ef4bd07b9d9e
8fea821f48194e38d9220528762e5f96
40b5f9f01a0410cdb6d3b69cee62df45
2cb6f4f5f8432208ea168d9519b2df40

如果有多个字段需要提取的时候,使用awk会较为方便

肆、参考文档: