Python学习笔记(十四)—hashlib模块

天涯浪子 提交于 2020-03-25 08:48:23

hashlib模块,主要用于加密相关的操作,在python3的版本里,代替了md5和sha模块。Python的hashlib提供了常见的摘要算法,主要提供 SHA1, SHA224, SHA256, SHA384, SHA512 ,MD5 算法。

什么是摘要算法呢?摘要算法又称哈希算法、散列算法。它通过一个函数,把任意长度的数据转换为一个长度固定的数据串(通常用16进制的字符串表示)。

举例说明:

你写了一篇文章,内容是一个字符串'how to use python hashlib - by Michael',并附上这篇文章的摘要是'2d73d4f15c0db7f5ecb321b6a65e5d6d'。如果有人篡改了你的文章,并发表为'how to use python hashlib - by Bob',你可以一下子指出Bob篡改了你的文章,因为根据'how to use python hashlib - by Bob'计算出的摘要不同于原始文章的摘要。

可见,摘要算法就是通过摘要函数f()对任意长度的数据data计算出固定长度的摘要digest,目的是为了发现原始数据是否被人篡改过。

摘要算法之所以能指出数据是否被篡改过,就是因为摘要函数是一个单向函数,计算f(data)很容易,但通过digest反推data却非常困难。而且,对原始数据做一个bit的修改,都会导致计算出的摘要完全不同。

MD5加密:

import hashlib
md5 = hashlib.md5()
md5.update('123456test'.encode())
print(md5.hexdigest())  #输出16进制格式的hash值
print(md5.digest())  #输出2进制格式的hash值

#上面也可以写成
import  hashlib
res = hashlib.md5('123456'.encode())
res.update('test'.encode()) #如果数据量很大,可以分块多次调用update(),最后计算的结果是一样的
print(res.hexdigest())
print(res.digest())

#最简便的写法是:
import hashlib
res = hashlib.md5('123456test'.encode())
print(res.hexdigest())
print(res.digest())

运行结果:

5a2e54ee57e5b7273b9a8fed78c1ebd8
b"Z.T\xeeW\xe5\xb7';\x9a\x8f\xedx\xc1\xeb\xd8"
5a2e54ee57e5b7273b9a8fed78c1ebd8
b"Z.T\xeeW\xe5\xb7';\x9a\x8f\xedx\xc1\xeb\xd8"
5a2e54ee57e5b7273b9a8fed78c1ebd8
b"Z.T\xeeW\xe5\xb7';\x9a\x8f\xedx\xc1\xeb\xd8"

MD5是最常见的摘要算法,速度很快,生成结果是固定的128 bit字节,通常用一个32位的16进制字符串表示。也可以用二进制的类型来表示。

另一种常见的摘要算法是SHA1,调用SHA1和调用MD5完全类似:

sha1加密:

import hashlib
res = hashlib.sha1('123456test'.encode())
print(res.hexdigest())
print(res.digest())

#也可以分开多次追加
import hashlib
sha_1 = hashlib.sha1()
sha_1.update('123456'.encode())
sha_1.update('test'.encode())
print(sha_1.hexdigest())
print(sha_1.digest())

运行结果:
b2478239cd7e68e8052398d8eb87d385bf962085
b'\xb2G\x829\xcd~h\xe8\x05#\x98\xd8\xeb\x87\xd3\x85\xbf\x96 \x85'
b2478239cd7e68e8052398d8eb87d385bf962085
b'\xb2G\x829\xcd~h\xe8\x05#\x98\xd8\xeb\x87\xd3\x85\xbf\x96 \x85'

比SHA1更安全的算法是SHA256和SHA512,不过越安全的算法不仅越慢,而且摘要长度更长。其使用方式和上面两种使用方式一致

注意:有没有可能两个不同的数据通过某个摘要算法得到了相同的摘要?完全有可能,因为任何摘要算法都是把无限多的数据集合映射到一个有限的集合中。这种情况称为碰撞,比如Bob试图根据你的摘要反推出一篇文章'how to learn hashlib in python - by Bob',并且这篇文章的摘要恰好和你的文章完全一致,这种情况也并非不可能出现,但是非常非常困难。

加盐

加盐的意思就是在本该加密的数据上边在新添加点其他的数据生成新的MD5加密秘钥,增加密码安全度。那么为什么需要加盐呢?

举例:考虑这么个情况,很多用户喜欢用123456888888password这些简单的口令,于是,黑客可以事先计算出这些常用口令的MD5值,得到一个反推表;然后拿这些反推表中的数据去逐个匹配用户的密码,俗称‘撞库’。

这样,无需破解,只需要对比数据库的MD5,黑客就获得了使用常用口令的用户账号。

#加密函数方法
def my_md5(s:str,salt = None):
    '''
    :param s: 需要传入的加密数据
    :param salt: 加密数据+额外的补充数据(加盐)
    :return: 返回计算结果
    '''
    s = str(s)
    if salt:
        s = s + salt
    m = hashlib.md5(s.encode())
    # print(m)
    return m.hexdigest()
print(my_md5('123456test')) #不加盐使用
print(my_md5('123456test','666')) #加盐使用


运行结果:
5a2e54ee57e5b7273b9a8fed78c1ebd8
e3d1a3c15fa02fc88c929b8c18261fad

总结:

摘要算法在很多地方都有广泛的应用。要注意摘要算法不是加密算法,不能用于加密(因为无法通过摘要反推明文),只能用于防篡改,但是它的单向计算特性决定了可以在不存储明文口令的情况下验证用户口令。

一个简单的例子:比较用户登录时候的密码是否正确(密码在数据库中不能以明文进行保存,因为如果数据库泄露,所有用户的口令就落入黑客的手里。此外,网站运维人员是可以访问数据库的,也就是能获取到所有用户的口令)

参考链接:

https://www.liaoxuefeng.com/wiki/1016959663602400/1017686752491744

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!