前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Python接口自动化之通过RSA加解密

Python接口自动化之通过RSA加解密

作者头像
ITester软件测试小栈
发布2022-03-10 15:40:42
2K0
发布2022-03-10 15:40:42
举报
文章被收录于专栏:全栈测试全栈测试

Hi,大家好。在之前的文章:Python实现各种加密,接口加解密不再难,介绍了Base64、MD5、Sha1、Secret、RSA等几种加密方式,今天结合项目具体介绍RSA加密。

一 RSA算法加密简介

1 介绍

RSA加密算法是一种非对称加密算法,加密的秘钥是由公钥和私钥两部分组成秘钥对,公钥用来加密消息,私钥用来对消息进行解密,公钥是公开的,私钥则是用户自己保留的,由于公钥是公开的,那么任何人只要获取到公钥,都可以使用公钥来加密发送伪造内容。

出于安全性考虑,在发送消息之前我们可以使用RSA来签名,签名使用私钥来进行签名,使用公钥来进行验签,通过签名我们可以确保用户身份的唯一性,从而提高安全性。

2 加密与签名的关系? 加密和签名都是为了安全性考虑,但略有不同。简单的说,加密是为了防止信息被泄露,而签名是为了防止信息被篡改。

(1) 加密

Task 1:Boss要给CoCo发送一条消息,分配保密的工作任务。

RSA的加密过程如下:

1.CoCo生成一对密钥(公钥和私钥),私钥不公开,CoCo自己保留。公钥为公开的,任何人可以获取。

2.CoCo传递自己的公钥给Boss,用CoCo的公钥对消息进行加密。

3.CoCo接收到Boss加密的消息,利用CoCo自己的私钥对消息进行解密。

在这个过程中,只有2次传递过程,第一次是CoCo传递公钥给Boss,第二次是Boss加密消息给CoCo,即使都被敌方截获,也没有危险性,因为只有CoCo的私钥才能对消息进行解密,防止了消息内容的泄露。

(2) 签名

Task 2:CoCo收到Boss发的消息后,需要进行回复“收到”。

RSA签名的过程如下:

1.CoCo生成一对密钥(公钥和私钥),私钥不公开,CoCo自己保留。公钥为公开的,任何人可以获取。

2.CoCo用自己的私钥对消息加签,形成签名,并将加签的消息和消息本身一起传递给Boss。

3.Boss收到消息后,在获取CoCo的公钥进行验签,如果验签出来的内容与消息本身一致,证明消息是CoCo回复的。

在这个过程中,只有2次传递过程,第一次是CoCo传递加签的消息和消息本身给Boss,第二次是Boss获取CoCo的公钥,即使都被敌方截获,也没有危险性,因为只有CoCo的私钥才能对消息进行签名,即使知道了消息内容,也无法伪造带签名的回复给Boss,防止了消息内容的篡改。

综合两个场景会发现,第一个场景虽然被截获的消息没有泄露,但是可以利用截获的公钥,将假指令进行加密,然后传递给CoCo。第二个场景虽然截获的消息不能被篡改,但是消息的内容可以利用公钥验签来获得,并不能防止泄露。

所以在实际应用中,要根据情况使用,也可以同时使用加密和签名,比如CoCo和Boss都有一套自己的公钥和私钥,当CoCo要给Boss发送消息时,先用Boss的公钥对消息加密,再对加密的消息使用CoCo的私钥加签名,达到既不泄露也不被篡改,更能保证消息的安全性。

即:公钥加密、私钥解密、私钥签名、公钥验签。

二 Python实现RSA加解密

接下来我们使用 Python 来实现 RSA 加密与签名,使用的第三方库是Crypto

1 生成密钥对

创建RSA密钥,步骤如下:

1、从 Crypto.PublicKey 包中导入 RSA,创建一个密码;

2、生成1024/2048位的RSA 密钥;

3、调用 RSA 密钥实例的 exportKey 方法,传入密码、使用的 PKCS 标准以及加密方案这三个参数;

4、将私钥写入磁盘的文件;

5、使用方法链调用 publickey 和 exportKey 方法生成公钥,写入磁盘上的文件。

示例代码如下:

私钥如下

公钥如下

2 公钥加密和私钥解密 (1) 公钥加密

结果如下所示:

代码语言:javascript
复制
luLmeQPdOIgDLDmCvuIK4QmQg6QXxDhvQ1igNVgURfjij/lNC7bqbWznELaGWy3ZnYWvyJoy2YY8RbjVaYSqwL37/Eta9tR+0/RCcMWK1iXOInAxwHiukvHy3itWhYbu2lQcSljBjoF3/IEEGnh7+MF3MoECIlGVlBR9s6jg5ZU=

(2) 私钥解密

代码语言:javascript
复制
import base64
from Crypto.PublicKey import RSA
from Crypto.Cipher import PKCS1_v1_5

def decrypt(en_data):
    '''
    en_data:加密过后的数据,传进来是一个字符串
    '''
    # base64解码
    msg = base64.b64decode(en_data)
    # 获取私钥
    privatekey = open('private.pem').read()
    rsakey = RSA.importKey(privatekey)
    # 进行解密
    cipher = PKCS1_v1_5.new(rsakey)
    data= cipher.decrypt(msg, 'DecryptError')
    # 解密出来的是字节码格式,decode转换为字符串
    return data.decode()

if __name__ == '__main__':
    en_data="luLmeQPdOIgDLDmCvuIK4QmQg6QXxDhvQ1igNVgURfjij/lNC7bqbWznELaGWy3ZnYWvyJoy2YY8RbjVaYSqwL37/Eta9tR+0/RCcMWK1iXOInAxwHiukvHy3itWhYbu2lQcSljBjoF3/IEEGnh7+MF3MoECIlGVlBR9s6jg5ZU="
    print(decrypt(en_data))

结果如下所示:

代码语言:javascript
复制
ITester软件测试小栈

3 私钥签名与公钥验签

(1) 私钥签名

结果如下所示:

代码语言:javascript
复制
Eb7mtvQGHCuzOR475TPRCR95Qg4GK1Nhbdw2je83JBxPfD0WiZ1Di/vXgQ8eH9fmh5z80epATF0IGT3Lm4DJTgHq+apuvhtjYNKv4wnz7c5seTuqWXTEjA6h/PomqW/yMC5/cbPr7w+aYEpV+2E+NKc/brUS1e6+pN4vHkaOXwM=

(2) 公钥验签

代码语言:javascript
复制
from Crypto.Hash import SHA
from Crypto.Signature import PKCS1_v1_5 as Sig_pk
from Crypto.PublicKey import RSA
import base64

def verify(data,sign) -> bool:
    '''
    :param msg: 明文数据,签名之前的数据
    :param sign:接收到的sign签名
    :return:
    '''
    # base64解码
    data = base64.b64decode(sign)
    # 获取公钥
    key = open('public.pem').read()
    rsakey = RSA.importKey(key)
    # 将签名之前的内容进行hash处理
    sha_name = SHA.new(sign.encode("utf-8"))
    # 验证签名
    signer = Sig_pk.new(rsakey)
    res= signer.verify(sha_name, sign)
    # 验证通过返回True   不通过返回False
    return res

if __name__ == '__main__':
    # 签名之前的内容
    data= "CoCo"
    # 签名数据
    sign="X3Gg+wd7UDh4X8ra+PGCyZFUrG+6jDeQt6ajMA0EjwoDwxlddLzYoS4dtjQ2q5WCcRhxcp8fjEyoPXBmJE9rMKDjEIeE/VO0sskbJiO65fU8hgcqdWdgbVqRryhOw+Kih+I6RIeNRYnOB8GkGD8Qca+n9JlOELcxLRdLo3vx6dw="
    print(verify(data, sign)) 

结果如下所示:

代码语言:javascript
复制
False

三 结合项目实现RSA加解密

需求:接口需要时间戳及token前50位鉴权,通过RSA公钥加密得到签名字符串。

1 RSA封装

rsa封装可在ITester软件测试小栈微信公众号后台回复“rsa”,进行领取。

2 结合项目实现

(1) 处理鉴权信息

生成token前50位并与时间戳进行拼接:

代码语言:javascript
复制
from time import time
def generator_sign(token):
    # 获取token的前50位
    token_50 = token[:50]
    # 生成时间戳
    timestamp = int(time())
    # print(timestamp)
    # 接拼token前50位和时间戳
    msg = token_50 + str(timestamp)
    print(msg)
    # 进行RSA加密
    sign = rsaEncrypt(msg)
    return sign,timestamp

(2) 配置请求信息

请求URL与请求头存放在配置文件,以下示例存放在.ini文件:

代码语言:javascript
复制
[server]
url=http://ITester.com/xxx
auth_type=xxx.itester

(3) 处理请求

发起请求时进行判断,如果auth_type为配置文件指定的类型并且token不为空,则带上加密的鉴权信息。(requests_handler.py 其他代码略)

代码语言:javascript
复制
    if conf.get("server","auth_type") == "xxx.itester" and token is not None:
        from Common.handle_rsa import generator_sign
        sign,timestamp = generator_sign(token)
        data["sign"] = sign
        data["timestamp"] = timestamp

总结:今天主要介绍了RSA加解密,RSA广泛用于加密与解密,还有数字签名通信领域。使用Publick/Private秘钥算法中, 加密主要用对方的公钥,解密用自己的私钥,签名用自己的私钥,验签用对方的公钥。

本文参与 腾讯云自媒体分享计划,分享自微信公众号。
原始发表:2022-02-17,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 ITester软件测试小栈 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • Task 1:Boss要给CoCo发送一条消息,分配保密的工作任务。
  • Task 2:CoCo收到Boss发的消息后,需要进行回复“收到”。
  • 结果如下所示:
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档