前言
好長時間沒有更新了,但是要有始有終,這個系列必須完成。
- C#、Golang、Python、Java(Android)之間Des、Rsa加解密互通系列之前言
- C#、Golang、Python、Java(Android)之間Des、Rsa加解密互通系列之C#
- C#、Golang、Python、Java(Android)之間Des、Rsa加解密互通系列之Golang
- C#、Golang、Python、Java(Android)之間Des、Rsa加解密互通系列之Python
- C#、Golang、Python、Java(Android)之間Des、Rsa加解密互通系列之Java(Android)
代碼
Des對稱加密工具類
# -*- coding: utf-8 -*-
# 依賴包 pip install pyDes
import base64
import pyDes
class DesHelper(object):
'''
Des對稱加密工具類
:param data:
:param app_key:
:return:
'''
def encrypt(self, data, key, iv):
'''
Des對稱加密
:param data: 需要加密的內容
:param key: 加密key 8 位
:param iv: 偏移向量 8位
:return:
'''
k = pyDes.des(key, pyDes.CBC, iv, pad=None, padmode=pyDes.PAD_PKCS5)
d = k.encrypt(data)
d = base64.b64encode(d)
return d
def decrypt(self, encData, key, iv):
'''
Des對稱解密
:param encData: 加密後的密文
:param key: 解密key 8位
:param iv: 偏移向量 8位
:return:
'''
k = pyDes.des(key, pyDes.CBC, iv, pad=None, padmode=pyDes.PAD_PKCS5)
data = base64.b64decode(encData)
d = k.decrypt(data)
return d
def tripleEncrypt(self, data, key, iv):
'''
3D Des對稱加密
:param data: 需要加密的內容
:param key: 加密key 24位
:param iv: 偏移向量 8位
:return:
'''
k = pyDes.triple_des(key, pyDes.CBC, iv, pad=None, padmode=pyDes.PAD_PKCS5)
d = k.encrypt(data)
d = base64.b64encode(d)
return d
def tripleDecrypt(self, encData, key, iv):
'''
3D Des對稱解密
:param encData: 加密後的密文
:param key: 解密key 24位
:param iv: 偏移向量 8位
:return:
'''
k = pyDes.triple_des(key, pyDes.CBC, iv, pad=None, padmode=pyDes.PAD_PKCS5)
data = base64.b64decode(encData)
d = k.decrypt(data)
return d
if __name__ == '__main__':
h = DesHelper()
# 加解密key
key = 'ajglslslajglslslajglslsl'
iv = 'kie8dkjd'
# 原文
data = 'abcdsdfasdfawe3234234234'
print('原文:',data)
print('******** 分隔線 **********')
# 對稱加密密文
encData = h.encrypt(data,key[0:8],iv)
print('密文:',encData)
# 對稱解密結果
decData = h.decrypt(encData,key[0:8],iv)
print('解密:',decData)
print('******** 分隔線 **********')
encData = h.tripleEncrypt(data, key, iv)
print('密文:', encData)
# 對稱解密結果
decData = h.tripleDecrypt(encData, key, iv)
print('解密:', decData)
Rsa密鑰對生成工具類
# -*- coding: utf-8 -*-
# 依賴包 pip install pycryptodome
# 如果仍然報沒有Module可以嘗試將 python安裝目錄下site-packages的子文件夾crypto改成Crypto
from Crypto import Random
from Crypto.PublicKey import RSA
# 利用僞隨機數來生成私鑰和公鑰
random_generator = Random.new().read
keys = RSA.generate(1024, random_generator)
private_pem = keys.exportKey()
f = open('private_key.pem', 'w')
f.write(private_pem.decode('utf-8'))
f.close()
public_pem = keys.publickey().exportKey()
f = open('public_key.pem', 'w')
f.write(public_pem.decode('utf-8'))
f.close()
Rsa加密、解密、簽名、驗籤工具類
# -*- coding: utf-8 -*-
# 依賴包 pip install pycryptodome
# 如果仍然報沒有Module可以嘗試將 python安裝目錄下site-packages的子文件夾crypto改成Crypto
import Crypto.Cipher as Cipher
from Crypto.PublicKey import RSA
from Crypto.Cipher import PKCS1_v1_5 as PKCS1_v1_5_cipper
from Crypto.Signature import PKCS1_v1_5 as PKCS1_v1_5_sign
from Crypto.Hash import SHA1
import base64
class RsaHelper(object):
"""RSA加解密簽名類
"""
def __init__(self, ciper_lib=PKCS1_v1_5_cipper, sign_lib=PKCS1_v1_5_sign, hash_lib=SHA1,
pub_file=None, pri_file=None, pub_skey=None, pri_skey=None, pub_key=None, pri_key=None,
reversed_size=11):
# 加解密庫
self.ciper_lib = ciper_lib
self.sign_lib = sign_lib
self.hash_lib = hash_lib
# 公鑰密鑰
if pub_key:
self.pub_key = pub_key
elif pub_skey:
self.pub_key = RSA.importKey(pub_skey)
elif pub_file:
self.pub_key = RSA.importKey(open(pub_file).read())
if pri_key:
self.pri_key = pri_key
elif pri_skey:
self.pri_key = RSA.importKey(pri_skey)
elif pri_file:
self.pri_key = RSA.importKey(open(pri_file).read())
# 分塊保留長度
self.block_reversed_size = reversed_size
# 根據key長度計算分塊大小
def get_block_size(self, rsa_key):
try:
# RSA僅支持限定長度內的數據的加解密,需要分塊
# 分塊大小
reserve_size = self.block_reversed_size
key_size = rsa_key.size_in_bits()
if (key_size % 8) != 0:
raise RuntimeError('RSA 密鑰長度非法')
# 密鑰用來解密,解密不需要預留長度
if rsa_key.has_private():
reserve_size = 0
bs = int(key_size / 8) - reserve_size
except Exception as err:
print('計算加解密數據塊大小出錯', rsa_key, err)
return bs
# 返回塊數據
def block_data(self, data, rsa_key):
bs = self.get_block_size(rsa_key)
for i in range(0, len(data), bs):
yield data[i:i + bs]
# 加密
def enc_bytes(self, data, key=None):
text = b''
try:
rsa_key = self.pub_key
if key:
rsa_key = key
cipher = self.ciper_lib.new(rsa_key)
for dat in self.block_data(data, rsa_key):
cur_text = cipher.encrypt(dat)
text += cur_text
except Exception as err:
print('RSA加密失敗', data, err)
return text
# 解密
def dec_bytes(self, data, key=None):
text = b''
try:
rsa_key = self.pri_key
if key:
rsa_key = key
cipher = self.ciper_lib.new(rsa_key)
for dat in self.block_data(data, rsa_key):
if type(self.ciper_lib) == Cipher.PKCS1_v1_5:
cur_text = cipher.decrypt(dat)
else:
cur_text = cipher.decrypt(dat, '解密異常')
text += cur_text
except Exception as err:
print('RSA解密失敗', data, err)
return text
# RSA簽名
def sign_bytes(self, data, key=None):
signature = ''
try:
rsa_key = self.pri_key
if key:
rsa_key = key
h = self.hash_lib.new(data)
signature = self.sign_lib.new(rsa_key).sign(h)
except Exception as err:
print('RSA簽名失敗', '', err)
return signature
# RSA簽名驗證
def sign_verify(self, data, sig, key=None):
try:
rsa_key = self.pub_key
if key:
rsa_key = key
h = self.hash_lib.new(data)
self.sign_lib.new(rsa_key).verify(h, sig)
ret = True
except (ValueError, TypeError):
ret = False
return ret
# 讀取標準的rsa公私鑰pem文件
def load_rsa_file(self,fn):
key = None
try:
key = RSA.importKey(open(fn).read())
except Exception as err:
print('導入rsa的KEY文件出錯', fn, err)
return key
# 標準字符串密鑰轉rsa格式密鑰
def rsa_key_str2std(self,skey):
ret = None
try:
ret = RSA.importKey(skey)
except Exception as err:
print('字符串密鑰轉rsa格式密鑰錯誤', skey, err)
return ret
if __name__ == '__main__':
pub_key = '''-----BEGIN PUBLIC KEY-----
MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQC7PyjMEuniN6BPn8oqzIZ6AO1N
jSTO9R3adCCIwKfKIEoWXXM+tHDpktdPKSaAsWJPTNAGvEvtxOfzXib/EMXKqD0e
Uy5MatfpRjRdf1hJVimmfrb09Qx2j7CsKLy7nD23m4xubdYBwvkjMwt/L3JxB5D6
qryW1wei/j1c+/OCxQIDAQAB
-----END PUBLIC KEY-----'''
pri_key = '''-----BEGIN RSA PRIVATE KEY-----
MIICXQIBAAKBgQC7PyjMEuniN6BPn8oqzIZ6AO1NjSTO9R3adCCIwKfKIEoWXXM+
tHDpktdPKSaAsWJPTNAGvEvtxOfzXib/EMXKqD0eUy5MatfpRjRdf1hJVimmfrb0
9Qx2j7CsKLy7nD23m4xubdYBwvkjMwt/L3JxB5D6qryW1wei/j1c+/OCxQIDAQAB
AoGAT7vGYJgRNf4f6qgNS4pKHTu10RcwPFyOOM7IZ9M5380+HyXuBB6MEjowKwpH
1fcy+LepwaR+5KG7b5uBGY4H2ticMtdysBd9gLwnY4Eh4j7LCWE54HvELpeWXkWp
FQdb/NQhcqMAGwYsTnRPdBqkrUmJBTYqEGkIlqCQ5vUJOCECQQDhe0KGmbq1RWp6
TDvgpA2dUmlt2fdP8oNW8O7MvbDaQRduoZnVRTPYCDKfzFqpNXL1hAYgth1N0vzD
nv3VoLcpAkEA1JcY+rLv5js1g5Luv8LaI5/3uOg0CW7fmh/LfGuz8k/OxASN+cAO
UjPHrxtc5xn1zat4/bnV5GEdlOp/DhquPQJBAIV2Fsdi4M+AueiPjPWHRQO0jvDV
jfwFOFZSn5YSRUa6NmtmPY6tumUJXSWWqKb1GwlVTuc3xBqXYsNLLUWwLhkCQQDJ
UJCiD0LohhdGEqUuSKnj5H9kxddJO4pZXFSI7UEJbJQDwcBkyn+FTm2BH+tZGZdQ
fVnlA89OJr0poOpSg+eNAkAKY85SR9KASaTiDBoPpJ8N805XEhd0Kq+ghzSThxL3
fVtKUQLiCh7Yd8oMd/G5S3xWJHUXSioATT8uPRH2bOb/
-----END RSA PRIVATE KEY-----'''
#r = RsaHelper(pri_file='private_key.pem', pub_file='public_key.pem')
r = RsaHelper(pub_skey=pub_key,pri_skey=pri_key)
data = "hello word 中國"
encrydata = r.enc_bytes(data.encode(encoding='utf-8'))
encrydata =base64.b64encode(encrydata)
print(encrydata)
encrydata = 'uDeQATxRbbkjTBVHXa6yi8B0KOIu7HLZuvKpXz5KNYQ8RRUTE5P3MF9d4hOG3qq+zk5z8y/1EngzFvpbsljP5qc71YQZbJEUAXARBAWB9ex7GyVlLzIA/T5bF7OmcoCr4fkWt4OYzC0aaFsKsmGDXS6aWGjD6ObulIjizDZiv8k='
encrydata = base64.b64decode(encrydata)
encrydata = r.dec_bytes(encrydata)
print(encrydata.decode("utf-8"))