python加密解密库cryptography使用openSSL生成的密匙加密解密


Posted in Python onFebruary 11, 2020

密匙使用步骤一般是:

    1. 私匙签名,发送签名后的数据, 公匙验证。

    2.公匙加密,发送加密后的数据,私匙解密。

一般使用情景是通过 openssl 生成密匙后再操作的。Linux下生成密匙也很简单。

yum 安装 openssl

yum -y install openssl

生成三个密匙文件。

rsa_private_key.pem 私匙文件

rsa_private_key_pkcs8.pem  pkcs8格式私匙, 

rsa_public_key.pem 公匙

openssl genrsa -out rsa_private_key.pem  1024 

openssl pkcs8 -topk8 -inform PEM -in rsa_private_key.pem -outform PEM -nocrypt -out rsa_private_key_pkcs8.pem 

openssl rsa -in rsa_private_key.pem -pubout -out rsa_public_key.pem

导入私匙:

序列化密钥可以选择使用密码在磁盘上进行加密。在这个例子中,我们加载了一个未加密的密钥,因此我们没有提供密码。如果密钥被加密,我们可以传递一个bytes对象作为 password参数。

from cryptography.hazmat.backends import default_backend
from cryptography.hazmat.primitives import serialization
 
# 已有sar私匙, 导入
with open('Key.pem', 'rb') as key_file:
  private_key = serialization.load_pem_private_key(
    key_file.read(),
    password=None,
    backend=default_backend()
  )

签名:

私钥可用于签署消息。这允许任何拥有公钥的人验证该消息是由拥有相应私钥的人创建的。RSA签名需要特定的散列函数,并使用填充。以下是message使用RSA 进行签名的示例,带有安全散列函数和填充:

from cryptography.hazmat.backends import default_backend
from cryptography.hazmat.primitives import serialization
from cryptography.hazmat.primitives import hashes
from cryptography.hazmat.primitives.asymmetric import padding
 
# 已有sar私匙, 导入
with open('Key.pem', 'rb') as key_file:
  private_key = serialization.load_pem_private_key(
    key_file.read(),
    password=None,
    backend=default_backend()
  )
 
message = b"aaaa, bbbb, cccc"
 
# 签名操作
signature = private_key.sign(
  message,
  padding.PSS(
    mgf=padding.MGF1(hashes.SHA256()),
    salt_length=padding.PSS.MAX_LENGTH
  ),
  hashes.SHA256()
)
print('签名后数据: ', signature)

有效的签名填充是 PSS和 PKCS1v15.PSS 是任何新协议或应用的推荐选择,PKCS1v15 只应用于支持传统协议。

如果您的数据太大而无法在单个调用中传递,则可以分别对其进行散列并使用该值 Prehashed。

from cryptography.hazmat.backends import default_backend
from cryptography.hazmat.primitives import serialization
from cryptography.hazmat.primitives import hashes
from cryptography.hazmat.primitives.asymmetric import padding
from cryptography.hazmat.primitives.asymmetric import utils
 
# 已有sar私匙, 导入
with open('Key.pem', 'rb') as key_file:
  private_key = serialization.load_pem_private_key(
    key_file.read(),
    password=None,
    backend=default_backend()
  )
 
# 如果您的数据太大而无法在单个调用中传递,则可以分别对其进行散列并使用该值 Prehashed。
 
 
chosen_hash = hashes.SHA256()
hasher = hashes.Hash(chosen_hash, default_backend())
hasher.update(b"data &")
hasher.update(b"more data")
digest = hasher.finalize()
sig = private_key.sign(
  digest,
  padding.PSS(
    mgf=padding.MGF1(hashes.SHA256()),
    salt_length=padding.PSS.MAX_LENGTH
  ),
  utils.Prehashed(chosen_hash)
)
print('签名后数据: ', sig)

验证:

from cryptography.hazmat.backends import default_backend
from cryptography.hazmat.primitives import serialization
from cryptography.hazmat.primitives import hashes
from cryptography.hazmat.primitives.asymmetric import padding
 
# 已有sar私匙, 导入
with open('Key.pem', 'rb') as key_file:
  private_key = serialization.load_pem_private_key(
    key_file.read(),
    password=None,
    backend=default_backend()
  )
 
message = b"123 xiao"
 
# 签名
signature = private_key.sign(
  # 原始数据
  message,
  padding.PSS(
    mgf=padding.MGF1(hashes.SHA256()),
    salt_length=padding.PSS.MAX_LENGTH
  ),
  hashes.SHA256()
)
print('签名后的数据: ', signature)
 
 
# 公匙导入
with open('Key_pub.pem', 'rb') as key_file:
  public_key = serialization.load_pem_public_key(
    key_file.read(),
    backend=default_backend()
  )
  
  
# 签名数据与原始数据不对,抛出异常
# 如果验证不匹配,verify()会引发 InvalidSignature异常。
public_key.verify(
  # 签名数据
  signature,
  # 原始数据
  message,
  padding.PSS(
    mgf=padding.MGF1(hashes.SHA256()),
    salt_length=padding.PSS.MAX_LENGTH
  ),
  hashes.SHA256()
)

如果您的数据太大而无法在单个调用中传递,则可以分别对其进行散列并使用该值 Prehashed。

from cryptography.hazmat.backends import default_backend
from cryptography.hazmat.primitives import serialization
from cryptography.hazmat.primitives import hashes
from cryptography.hazmat.primitives.asymmetric import padding
from cryptography.hazmat.primitives.asymmetric import utils
 
# 已有sar私匙, 导入
with open('Key.pem', 'rb') as key_file:
  private_key = serialization.load_pem_private_key(
    key_file.read(),
    password=None,
    backend=default_backend()
  )
 
chosen_hash = hashes.SHA256()
hasher = hashes.Hash(chosen_hash, default_backend())
hasher.update(b'data &')
hasher.update(b'more data')
digest = hasher.finalize()
sig = private_key.sign(
  digest,
  padding.PSS(
    mgf=padding.MGF1(hashes.SHA256()),
    salt_length=padding.PSS.MAX_LENGTH
  ),
  utils.Prehashed(chosen_hash)
)
print('签名后的数据: ', sig)
 
 
# 公匙导入
with open('Key_pub.pem', 'rb') as key_file:
  public_key = serialization.load_pem_public_key(
    key_file.read(),
    backend=default_backend()
  )
 
 
# 如果您的数据太大而无法在单个调用中传递,则可以分别对其进行散列并使用该值 Prehashed。
public_key.verify(
  sig,
  digest,
  padding.PSS(
    mgf=padding.MGF1(hashes.SHA256()),
    salt_length=padding.PSS.MAX_LENGTH
  ),
  utils.Prehashed(chosen_hash)
)

公匙,加密:

因为是使用进行加密的RSA加密有趣的是 公共密钥,这意味着任何人都可以对数据进行加密。数据然后使用私钥解密。

from cryptography.hazmat.backends import default_backend
from cryptography.hazmat.primitives import serialization
from cryptography.hazmat.primitives import hashes
from cryptography.hazmat.primitives.asymmetric import padding
 
 
# 公匙导入
with open('Key_pub.pem', 'rb') as key_file:
  public_key = serialization.load_pem_public_key(
    key_file.read(),
    backend=default_backend()
  )
 
 
message = b'test data'
ciphertext = public_key.encrypt(
  message,
  padding.OAEP(
    mgf=padding.MGF1(algorithm=hashes.SHA256()),
    algorithm=hashes.SHA256(),
    label=None
  )
)
print('加密数据: ', ciphertext)

私匙解密公私加密的信息:

from cryptography.hazmat.backends import default_backend
from cryptography.hazmat.primitives import serialization
from cryptography.hazmat.primitives import hashes
from cryptography.hazmat.primitives.asymmetric import padding
 
 
# 已有sar私匙, 导入
with open('Key.pem', 'rb') as key_file:
  private_key = serialization.load_pem_private_key(
    key_file.read(),
    password=None,
    backend=default_backend()
  )
  
 
plaintext = private_key.decrypt(
  # 加密的信息
  ciphertext,
  padding.OAEP(
    mgf=padding.MGF1(algorithm=hashes.SHA256()),
    algorithm=hashes.SHA256(),
    label=None
  )
)
 
print('解密数据: ', plaintext)

完整的公匙加密,私匙解密获取信息。

from cryptography.hazmat.backends import default_backend
from cryptography.hazmat.primitives import serialization
from cryptography.hazmat.primitives import hashes
from cryptography.hazmat.primitives.asymmetric import padding
 
 
# 公匙导入
with open('Key_pub.pem', 'rb') as key_file:
  public_key = serialization.load_pem_public_key(
    key_file.read(),
    backend=default_backend()
  )
 
 
message = b'test data'
ciphertext = public_key.encrypt(
  message,
  padding.OAEP(
    mgf=padding.MGF1(algorithm=hashes.SHA256()),
    algorithm=hashes.SHA256(),
    label=None
  )
)
print('加密数据: ', ciphertext)
 
 
# 已有sar私匙, 导入
with open('Key.pem', 'rb') as key_file:
  private_key = serialization.load_pem_private_key(
    key_file.read(),
    password=None,
    backend=default_backend()
  )
  
 
plaintext = private_key.decrypt(
  # 加密的信息
  ciphertext,
  padding.OAEP(
    mgf=padding.MGF1(algorithm=hashes.SHA256()),
    algorithm=hashes.SHA256(),
    label=None
  )
)
 
print('解密数据: ', plaintext)

更多关于python加密解密库cryptography的使用方法请查看下面的相关链接

Python 相关文章推荐
python 判断自定义对象类型
Mar 21 Python
python实现的登陆Discuz!论坛通用代码分享
Jul 11 Python
Python反射的用法实例分析
Feb 11 Python
Python实现基于PIL和tesseract的验证码识别功能示例
Jul 11 Python
从请求到响应过程中django都做了哪些处理
Aug 01 Python
Python正则表达式指南 推荐
Oct 09 Python
Python函数基础实例详解【函数嵌套,命名空间,函数对象,闭包函数等】
Mar 30 Python
python 自动轨迹绘制的实例代码
Jul 05 Python
Python任务自动化工具tox使用教程
Mar 17 Python
python读取配置文件方式(ini、yaml、xml)
Apr 09 Python
使用SQLAlchemy操作数据库表过程解析
Jun 10 Python
对象析构函数__del__在Python中何时使用
Mar 22 Python
如何通过python实现全排列
Feb 11 #Python
Python3加密解密库Crypto的RSA加解密和签名/验签实现方法实例
Feb 11 #Python
python 遗传算法求函数极值的实现代码
Feb 11 #Python
在django中使用apscheduler 执行计划任务的实现方法
Feb 11 #Python
django在保存图像的同时压缩图像示例代码详解
Feb 11 #Python
Python中包的用法及安装
Feb 11 #Python
使用Python实现牛顿法求极值
Feb 10 #Python
You might like
造势之举?韩国总统候选人发布《星际争霸》地图
2017/04/22 星际争霸
QQ互联一键登录审核不通过的解决方案
2014/09/10 PHP
php实现图片按比例截取的方法
2017/02/06 PHP
YII中Ueditor富文本编辑器文件和图片上传的配置图文教程
2017/03/15 PHP
Laravel框架使用Seeder实现自动填充数据功能
2018/06/13 PHP
PHP PDO数据库操作预处理与注意事项
2019/03/16 PHP
php获取小程序码的实现代码(B类接口)
2020/06/13 PHP
window.open被浏览器拦截后的自定义提示效果代码
2007/11/19 Javascript
开发插件的两个方法jquery.fn.extend与jquery.extend
2013/11/21 Javascript
JavaScript的jQuery库插件的简要开发指南
2015/08/12 Javascript
JavaScript数据操作_浅谈原始值和引用值的操作本质
2016/08/23 Javascript
jQuery快速实现商品数量加减的方法
2017/02/06 Javascript
BootStrap Select清除选中的状态恢复默认状态
2017/06/20 Javascript
利用Ionic2 + angular4实现一个地区选择组件
2017/07/27 Javascript
vue-router项目实战总结篇
2018/02/11 Javascript
vue仿element实现分页器效果
2018/09/13 Javascript
jQuery实现点击图标div循环放大缩小功能
2018/09/30 jQuery
jQuery zTree插件使用简单教程
2019/08/16 jQuery
Vue前端项目部署IIS的实现
2020/01/06 Javascript
javascript的hashCode函数实现代码小结
2020/08/11 Javascript
[53:10]2018DOTA2亚洲邀请赛 4.6 淘汰赛 VP vs VG 第一场
2018/04/11 DOTA
python daemon守护进程实现
2016/08/27 Python
python批量添加zabbix Screens的两个脚本分享
2017/01/16 Python
Python实现统计给定字符串中重复模式最高子串功能示例
2018/05/16 Python
python+opencv实现霍夫变换检测直线
2020/10/23 Python
python中实现控制小数点位数的方法
2019/01/24 Python
Python sklearn库实现PCA教程(以鸢尾花分类为例)
2020/02/24 Python
python GUI库图形界面开发之PyQt5布局控件QHBoxLayout详细使用方法与实例
2020/03/06 Python
Jupyter notebook运行Spark+Scala教程
2020/04/10 Python
艺校音乐专业自我鉴定范文
2014/03/01 职场文书
企业文化演讲稿
2014/05/20 职场文书
机械设备与数控技术专业求职信
2014/08/10 职场文书
项目经理岗位职责
2015/01/31 职场文书
费用申请报告范文
2015/05/15 职场文书
教师节联欢会主持词
2015/07/04 职场文书
2016党员学习心得体会范文
2016/01/23 职场文书