ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

网易云音乐RSA和AES加密解析

2021-02-12 16:57:04  阅读:603  来源: 互联网

标签:AES 加密 16 text random RSA str


这几天爬网易云音乐的VIP歌曲来着,思路一个星期前就好了代码也早就写好了,直到现在猜跑起来,挺心烦的,一个报错让我搞了好几天,但是收获还是有的

AttributeError: 'bytes' object has no attribute 'encode'

这个后面说,先说正事

网易云音乐加密思路

1.生成一个16位的随机字符串

def make_random():
    str = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789'
    random_str = ''
    for i in range(16) :
        index = random.randint(0, len(str) - 1)
        random_str += str[index]
    return random_str

2.AES加密两次生成params
3.RSA加密一次生成encSecKey
4.requests携带params和encSecKey俩个参数获取id列表或者歌曲下载url

AES加密

为什么是AES和RSA加密呢,我下一篇文章说,博客写好了补上链接
这是我当时的思路在这里插入图片描述

注意事项
打印一下第一次加密的密文,是b’巴拉巴拉’,这说明是bytes类型的,
在这里插入图片描述
而传入的明文应该是str类型,所以要转码一下,`

 fin_str1 =  str(inti_str1,encoding='utf-8')
 print(type(fin_str1))
     >>>str
   

最后类型成了str类型,就okk了,要不会出现最前面的报错
AES加密完整代码

from Crypto.Cipher import AES
from binascii import b2a_hex, a2b_hex
import json,random
def make_random():
    str = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789'
    random_str = ''
    for i in range(16) :
        index = random.randint(0, len(str) - 1)
        random_str += str[index]
    return random_str
class PrpCrypt(object):

    def __init__(self):
        # self.key = key.encode('utf-8')
        self.mode = AES.MODE_CBC

    # 加密函数,若是text不足16位就用空格补足为16位,
    # 若是大于16当时不是16的倍数,那就补足为16的倍数。
    def encrypt(self, key,text):
        text = text.encode('utf-8')
        cryptor = AES.new(key, self.mode, b'0000000000000000')
        # 这里密钥key 长度必须为16(AES-128),
        # 24(AES-192),或者32 (AES-256)Bytes 长度
        # 目前AES-128 足够目前使用
        length = 16
        count = len(text)
        if count < length:
            add = (length - count)
            # \0 backspace
            # text = text + ('\0' * add)
            text = text + ('\0' * add).encode('utf-8')
        elif count > length:
            add = (length - (count % length))
            # text = text + ('\0' * add)
            text = text + ('\0' * add).encode('utf-8')
        self.ciphertext = cryptor.encrypt(text)
        # 由于AES加密时候获得的字符串不必定是ascii字符集的,输出到终端或者保存时候可能存在问题
        # 因此这里统一把加密后的字符串转化为16进制字符串
        return b2a_hex(self.ciphertext)

    # 解密后,去掉补足的空格用strip() 去掉
    def decrypt(self, text):
        cryptor = AES.new(self.key, self.mode, b'0000000000000000')
        plain_text = cryptor.decrypt(a2b_hex(text))
        # return plain_text.rstrip('\0')
        return bytes.decode(plain_text).rstrip('\0')

def make_params() :
    # song_name = input('要下载歌曲的名字:')
    song_name = "单车"
    text = {"hlpretag": "<span class=s-fc7>", "hlposttag": "</span>", "s": song_name, "type": "1", "offset": "0",
            "total": "true", "limit": "50", "csrf_token": ""}
    text = json.dumps(text)

    pc = PrpCrypt()  # 初始化密钥
    inti_key = '0CoJUm6Qyw8W8jud'
    fin_str = inti_key.encode('utf-8')
    e = pc.encrypt(fin_str,text)  # 加密
    # d = pc.decrypt(e)  # 解密
    # print("第一次加密结果:", e)
    inti_str1 = e
    fin_str1 =  str(inti_str1,encoding='utf-8')
    # print(type(fin_str1))
    # >>>str
    random_str = make_random().encode('utf-8')
    params = pc.encrypt(random_str,fin_str1)
    # print(params)
    # # fin_str = inti_str[]
    # # fin_str = fin_str[-1:]
    # # f = pc.encrypt(fin_str)
    # print(inti_str)
    # print(fin_str)
    # # print("解密:", d)
    return params

if __name__ == '__main__':
     params = make_params()

RSA加密

这个呢,我个人觉得比AES难一点,因为它有密钥和明钥,不过这次不需要了解这么多,看了一晚上加解密过程看的我懵了
加密过程自行百度,反正就是很安全,加密过程需要用到几个函数
pow(x,y)函数 返回 x的y 次的值
hexlify(a,16)就是把a转换成16进制
需要引入一个模块from binascii import hexlify

def make_encSecKey(text):
        text = text[::-1]
        modulus = '00e0b509f6259df8642dbc35662901477df22677ec152b5ff68ace615bb7b725152b3ab17a876aea8a5aa76d2e417629ec4ee341f56135fccf695280104e0312ecbda92557c93870114af6c9d05c4f7f0c3685b7a46bee255932575cce10b424d813cfe4875d3e82047b97ddef52741d546b8e289dc6935b3ece0462db0a22b8e7'
        pub_key = '010001'
        rs = pow(int(hexlify(text.encode('utf-8')), 16), int(pub_key, 16), int(modulus, 16))
        return format(rs, 'x').zfill(256)
if __name__ == '__main__':
    random_str = make_random()
    encSecKey = make_encSecKey(random_str)
    print(encSecKey)

在这里插入图片描述

总结一下哇

这次算是学python以来第一次真正的学习,因为第一是根本没有人可以问,全靠百度和一行一行的print
其次就是最开始的那个报错让我欲仙欲死,看了俩个通宵网上的各种解决方法也无济于事,我甚至用谷歌翻译把外网的帖子都看了,实在是无人可求,我一行一行的print结果,然后再一行一行的print(type(巴拉巴拉))最后才明白是第一次加密的结果是bytes,懂了,下次就这样调试,下一篇文章是爬取下载网易云音乐VIP歌曲,写了好几天了,要结尾了,这一关快要过去了,一山放过一山拦,期待下一个爬虫项目

标签:AES,加密,16,text,random,RSA,str
来源: https://blog.csdn.net/weixin_50847719/article/details/113795115

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有