今天心血来潮,想把AES加密的内容做一个总结,方便日后观看查阅。
学艺不精,如有错误,欢迎各位老师批评指正!
AES简介
AES是目前广泛应用的对称加密算法,主要用于保护电子数据。
- 对称加密:加密与解密使用相同的密钥
- 块加密算法:AES将数据分成固定大小的块(128位),并对每个数据块进行加密
- 密钥长度:AES支持三种密钥长度:128位、192位和256位。密钥的长度越长,数据加密就越安全。
如上图所示:这个就是AES加密与解密的基本逻辑。在爬虫的学习中我们只需要知道AES的工作流程,而它内部的加密逻辑并不在我们的学习范围之内。
下面对上面流程图进行解释说明:
明文:等待被加密的数据。
密钥:目标网站对数据加密和解密时所使用的密码,这个密钥是前端与后端协商之后的结果,不会通过网络进行传输,在写网络爬虫时,需要获取到密钥即可对数据进行加解密的操作。
加密函数/解密函数:C=E(K, P)
,C代表明文/密文,E代表加密/解密函数,K代表密钥,P代表密文/明文。其实需要加密或解密的话,需要创建AES函数,将待加密/解密的数据以及密钥传入即可实现加解密的过程。
AES有以下几种模式:
1、电子密码本模式(ECB)
- 特点:每个块独立加密,相同的明文块会被加密成相同的数据
- 优点:容易实现
- 缺点:安全性差,容易遭到攻击譬如(频率分析),不推荐用于实际应用
2、密码块链接模式(CBC)
- 特点:每个块的加密结果依赖于前一个块,第一块与初始向量异或。
- 优点:比ECB更加的安全,因为相同的明文块不会加密成相同的数据。
- 缺点:加密过程不能并行,必须等待上一个明文块结束后才能继续下一个。
3、计数器模式(CTR)
- 特点:将一个计数器的值(通常是一个递增的值)与密钥进行加密,然后与明文异或。
- 优点:支持并行加密和解密,速度块,且安全性较高。
- 缺点:如果同一个密钥被使用多次而不及时更改的话,依然还是会有危险。
4、加密分组链接模式(CFB)
- 特点:将前一个明文块加密后与当前的明文异或。
- 优点:适用于流式数据,可以处理不完整的输入数据
- 缺点:与CBC类似,解密过程依赖于前一个密文块
5、输出反馈模式(OFB)
- 特点:将初始向量(IV)与密钥进行加密,然后将结果与明文异或。每次输出后,将前一次的加密结果作为下一次的输入
- 优点:支持并行加密和解密,速度块,且安全性较高。
- 缺点:如果同一个密钥被使用多次而不及时更改的话,依然还是会有危险。
加密模式CBC
CBC加密模式是目前网站用于传输文件或者是传输数据比较常见的加密模式,它的安全性比EBC要高上许多,由于它的每一块的加密结果都依赖于前一块的加密块,并且为了避免数据重复,在第一块的使用中需要添加初始向量iv。
下面我来写一个CBC加密模式的demo,给大家做一个参考:
加密
from Crypto.Cipher import AES
from Crypto.Util.Padding import pad, unpad
import base64
# AES加密函数
def encrypt(text, key):
# 使用静态iv,在实际开发中大多使用随机生成
iv = b'this is an iv456' # 16字节的iv值
# 创建AES对象
cipher = AES.new(key, AES.MODE_CBC, iv)
# 填充明文并加密
cipher_text = cipher.encrypt(pad(plain_text.encode(), AES.block_size))
# 返回密文
return base64.b64encode(cipher_text).decode('utf-8')
if __name__ == '__main__':
key = b'this is a key123' # 16字节密钥
# 明文
plain_text = 'hello'
# 加密
cipher_text = encrypt(plain_text, key)
print('密文: ', cipher_text)
注:一个字节是8位,一个英文字母和一个空格就是一个字节
运行结果如下:
yVuSCyVMjJjFzBvQ1TatEQ==
解密
def decrypt(cipher_text, key):
# 解码密文
decode_data = base64.b64decode(cipher_text)
# 使用相同的iv
iv = b'this is an iv456' # 16字节的iv值
# 创建AES对象
cipher = AES.new(key, AES.MODE_CBC, iv)
# 解密并去除填充
plain_text = unpad(cipher.decrypt(decode_data), AES.block_size)
return plain_text.decode()
if __name__ == '__main__':
key = b'this is a key123' # 16字节密钥
plain_text = decrypt(cipher_text, key)
print('明文:', plain_text)
运行结果如下:
hello
大家认真去看上述两份代码,就会发现对称加密模式的加密与加密每一步都是一一对应的,我对代码的每一个作用都做了详细的说明,因此操作起来并不会有太大的难度。
另外注意,CBC模式的加密与解密时使用的iv和key是一样的。
加密模式EBC
EBC模式的加密安全性较低,在实际开发过程中慎用!
加密
from Crypto.Cipher import AES
from Crypto.Util.Padding import pad, unpad
import base64
# 加密
def encrypt(plain_text, key):
# 创建AES对象,使用EBC模式
cipher = AES.new(key, AES.MODE_ECB)
# 填充明文并加密
cipher_text = cipher.encrypt(pad(plain_text.encode(), AES.block_size))
# 返回密文的base64编码
return base64.b64encode(cipher_text).decode()
if __name__ == '__main__':
key = b'this is a key123'
plain_text = 'hello'
ciphter_text = encrypt(plain_text, key)
print('密文:', ciphter_text)
运行结果如下:
密文: KcAGhxWuObJj30hBZY+buA==
解密
def decrypt(cipher_text, key):
# 解码密文
decode_data = base64.b64decode(cipher_text)
# 创建AES对象,使用EBC模式
cipher = AES.new(key, AES.MODE_ECB)
# 去除填充
plain_text = unpad(cipher.decrypt(decode_data), AES.block_size)
return plain_text.decode()
if __name__ == '__main__':
key = b'this is a key123'
decrypt_text = decrypt(cipher_text, key)
print('明文:', decrypt_text)
运行结果如下:
明文: hello
小节
除了上述讲解的两种加密模式之外,我还介绍了其余的加密模式,不过CBC和EBC的加密是最常见的,其余的加密模式在遇到了可以自行搜索解决就好。
实战案例
目标地址:aHR0cHM6Ly9qenNjLm1vaHVyZC5nb3YuY24vZGF0YS9jb21wYW55
从数据中无法看出是什么加密,猜测就是由CryptoJS模块加密生成,因而可以在全局搜索CryptoJS
、decrypt
这类关键字,或者搜索加密算法中常常用到的偏移量iv
、模式mode
、填充方式padding
等,现在也可以比较明显的发现,此类数据是XHR中的json数据被加密,也可以直接搜索JSON.parse
。
发现app.7c192126.js文件比较可疑,当然也不一定就是它,先进去分析看看
这里可以看到有一个返回数据,可以打个断点看看,返回的数据是什么
可以明显看到e
就是解密后的数据,那么var e = JSON.parse(b(t.data));
这行代码不容小觑。
下面直接跟进b
函数,很明显可以看到是AES的加密
f = d.a.enc.Utf8.parse("jo8j9wGw%6HbxfFn")
m = d.a.enc.Utf8.parse("0123456789ABCDEF");
function b(t) {
var e = d.a.enc.Hex.parse(t)
, n = d.a.enc.Base64.stringify(e)
, a = d.a.AES.decrypt(n, f, {
iv: m,
mode: d.a.mode.CBC,
padding: d.a.pad.Pkcs7
})
, r = a.toString(d.a.enc.Utf8);
return r.toString()
从中可以发现加密模式为CBC
,填充方式是Pkcs7
,另外偏移量m,f在b函数的上方,往上滑动一些些就能看到。
到这里已经分析完毕了,代码就不再提供了。
欢迎关注:小志Codings
今天的文章到这里就结束了,如果各位老师有任何意见和建议,请不吝赐教。
路漫漫其修远兮,吾将上下而求索。