加密解密
md5加密,单项加密,使用哈希函数,极小概率出现加密不同的值后出现相同的值,这称为哈希碰撞
加密又分单向加密
单向加密一般是不可逆的,如md5加密,base64加密,sha加密
双向加密是可逆的,这里有加密算法,密钥,加密算法一般是两个函数,一个用来加密,一个用来解密,密钥就是着两个函数的参数,
一般这两个函数有关联性
这里又可以细分,
对称加密(双方各持一个密钥),由于是一对一密钥,若加密来往不同的数据较多,就会造成密钥过多
DES加密,AES加密
非对称加密(公钥和私钥):缺点是加密解密慢,优点是可同时用公钥加密和多人通信,解密只需要采用私钥就可以
RSA加密
签名验证
本质上这也可以算是非对称加密的一种,
数字签名一般由两部分组成,分别是签名信息和信息验证。
发送方持有的能代表自己身份的私钥来生成签名信息,然后又接收方持有的私钥对应生成的公钥来验证发送方是否为合法的信息发送者。
报错字段
AES加密报错
# 报错字段
return msg + b'\0'*to_add
# 报错信息
TypeError: must be str, not bytes
#解答
msg = cipher.encrypt(fill_text(text.encode())) # 我这里加密的原文起初没encode()
# 报错信息
ValueError: Data must be aligned to block boundary in ECB mode
md5_function
# 具有不可逆向解密的特性
# 可用于密码验证和数据完整性的验证
# 使用时,将新注册用户的密码通过md5加密后存储到数据库中
# 当用户注册时,通过验证MD5来检查用户输入密码的正确性
import hashlib
class User:
def __init__(self,username,password):
self.username = username
md5 = hashlib.md5(password.encode())
self.password = md5.hexdigest()
def check_password(self,password):
md5 = hashlib.md5(password.encode())
if md5.hexdigest() == self.password:
return '密码正确'
else:
return '密码错误'
user = User('admin','admin')
# 加密后的密码 21232f297a57a5a743894a0e4a801fc3
print('加密后的密码',user.password) # 类可以这样提取出它的类变量,需要在__init__函数中传入参数
print(user.check_password('12345')) # 密码错误
print(user.check_password('admin')) # 密码正确
MD5
import hashlib
message = 'hello world'
md5 = hashlib.md5(message.encode()) # 别忘了encode编码
print(md5)
import hashlib
message = 'hello world'
md5 = hashlib.md5(message.encode()) # 别忘了encode编码
# print(md5) # <md5 HASH object @ 0x0000022A2B1E13A0>
# 加密后的数据打印出来有2项
print(md5.hexdigest()) # <md5 HASH object @ 0x0000022A2B1E13A0>
# 5eb63bbbe01eeed093cb22bb8f5acdc3
SHA
import hashlib
message = 'hello world'
sha = hashlib.sha1(message.encode())
print(sha.hexdigest()) # 2aae6c35c94fcfb415dbe95f408b9ce91ee846ed;比md5的位数看起来长
双重md5
import hashlib
def md5(content):
return hashlib.md5(content.encode()).hexdigest()
message = 'hello world'
print(message) # hello world
print(md5(message))# 5eb63bbbe01eeed093cb22bb8f5acdc3
print(md5(md5(message))) # 有点递归的味道c0b0ef2d0f76f0133b83a9b82c1c7326
双向加密
# AES加密比DES加密更难破解
# 加密步骤
###AES加密的密钥是16个字节或者更多,也就是128位,分成16组,每个分组内不断进行着如下操作
####替换字节,行移位,列移位,轮密钥加密;不断重复迭代多次
from Crypto.Cipher import AES
from Crypto import Random
# 补全16位,必须是16的倍数
def fill_text(msg):
to_add = 0
if len(msg) % 16 != 0:
to_add = 16 -len(msg) % 8
return msg + b'\0'*to_add
# AES的key必须是16,24,或者32位长度
key = b'12345678'
# iv = Random.new().read(AES.block_size)
cipher = AES.new(fill_text(key),AES.MODE_ECB) # ,iv不需要该变量
# 原文
text = 'hello world'
# 加密
msg = cipher.encrypt(fill_text(text.encode())) # 我这里加密的原文起初没encode()
print('加密后:',msg)
# 解密
text1 = cipher.decrypt(fill_text(msg))
print('解密后:',text1)
DES
# 需要安装第三方库 PyCryptodome
# DES的密钥长度为8字节(全长为64位,实际参与运算的为56位,分8组,每一组最后一位位奇偶校验位,用于校验错误)
# 介绍加密过程
###64位,分成8组,与明文按照一定规则进行数据置换和移位,解密同样也是对加密的密文传入密钥进行数据置换和移位
##重要的参数:Key加密解密时所用的密钥,Data数据原文,Mode工作模式(分为加密和解密两者模式)
# DES密钥简单 容易被破解
from Crypto.Cipher import DES
from Crypto import Random
# 补全8位,必须是8位的倍数
def full_text(msg):
to_add = 0
if len(msg) % 8 != 0:
to_add = 8 - len(msg) % 8
return msg + b'\0'*to_add
key = b'12345678'
# iv = Random.new().read(DES.block_size) # 这个版本不需要iv
cipher = DES.new(key,DES.MODE_ECB) #,iv TypeError: IV is not meaningful for the ECB mode
text = 'hello 世界'
msg = cipher.encrypt(full_text(text.encode()))
print('加密后的字节码:',msg)
text1 = cipher.decrypt(msg)
print('解密后的文本',text1.decode())
RSA
# 需要安装第三方库 PyCryptodome
# 非对称加密RSA
from Crypto.Cipher import PKCS1_OAEP
from Crypto.PublicKey import RSA
from Crypto import Random
random_generator = Random.new().read
# 生成RSA密钥对
new_rsa = RSA.generate(1024,random_generator)
# 导出私钥用户可以保存下来多次使用
private_pem = new_rsa.export_key()
print('private key:')
print(private_pem)
# 导出公钥用户可以保存下来多次使用
public_pem = new_rsa.public_key().export_key()
print('public key:')
print(public_pem)
#编写函数
def encrypt(pub_key,msg):
rsa = RSA.importKey(pub_key)
cipher = PKCS1_OAEP.new(rsa)
return cipher.encrypt(msg)
def decrypt(priv_key,msg):
rsa = RSA.importKey(priv_key)
cipher = PKCS1_OAEP.new(rsa)
return cipher.decrypt(msg)
text = 'hello 世界'
print('原文:',text)
msg = encrypt(public_pem,text.encode())
print('加密后的字节码:',msg)
text1 = decrypt(private_pem,msg)
print('解密后的字节码:',text1)
print('解密后的文字:',text1.decode())
加盐base64
介绍
加盐是指用户在上传密码到服务器时候,在密码中加入其他成分
(系统的时间戳,随意生成的哈希值),用来增加密码的复杂度
可以把加盐后的密码在通过加密算法进行加密。
# 可以减少数据占用的%33空间
import base64
message = 'hello world'
msg = base64.b64encode(message.encode())
print(message,msg) # hello world b'aGVsbG8gd29ybGQ='
# 解码
text = base64.b64decode(msg)
print(text.decode()) # hello world
努力拼搏吧,不要害怕,不要去规划,不要迷茫。但你一定要在路上一直的走下去,尽管可能停滞不前,但也要走。