如何使用pycryptodom

时间:2018-05-26 02:13:39

标签: python encryption pycrypto

我正在使用混合加密(RSA + AES),但是长度很大,现在我想使用ECC而不是RSA,但是在pycryptodom中没有实现它。 这是我的RSA代码

def generate_keys():
    key = RSA.generate(1024)
    private_key = key.exportKey(format='PEM', pkcs=8, 
                  protection="scryptAndAES128-CBC")
    f = open("private_key.pem", "wb")
    f.write(private_key)
    public_key = key.publickey().exportKey('PEM')
    f = open("public_key.pem", "wb")
    f.write(public_key)
    f.close()

def encrypt(username, msg):
    #get the reciever's public key
    f = open("{}.pem".format(username)) # a.salama.pem
    recipient_key = RSA.import_key(f.read())
    f.close()

    # Encrypt the session key with the reciever's public RSA key
    cipher_rsa = PKCS1_OAEP.new(recipient_key)

    # Encrypt the data with the AES session key
    session_key = get_random_bytes(16)

    cipher_aes = AES.new(session_key, AES.MODE_EAX)
    ciphertext, tag = cipher_aes.encrypt_and_digest(msg.encode('utf-
                    8'))
    encrypted_data = cipher_rsa.encrypt(session_key) + 
    cipher_aes.nonce + tag +  ciphertext    
    encrypted_data = base64.b64encode(encrypted_data)
    return encrypted_data

尝试使用ECC + AES后,代码将

from Crypto.PublicKey import ECC
from Crypto.Random import get_random_bytes
from Crypto.Cipher import AES, PKCS1_OAEP
import base64

def generate_keys():
    key = ECC.generate(curve='P-256') #3072 RSA 
    private_key = key.export_key(format='PEM')
    f = open('private_key.pem','wt')
    f.write(private_key)
    f.close()

    public_key = key.public_key().export_key(format='PEM')
    f = open('public_key.pem','wt')
    f.write(public_key)
    f.close()

def encrypt(username, msg):
    #get the reciever's public key
    f = open("{}.pem".format(username), 'rt') # a.salama.pem
    recipient_key = ECC.import_key(f.read())
    f.close()

    # Encrypt the session key with the reciever's public RSA key
    cipher_rsa = PKCS1_OAEP.new(recipient_key)

    # Encrypt the data with the AES session key
    session_key = get_random_bytes(16)
    #we use the EAX mode to allow detection of unauthorized 
    modifications.  
    cipher_aes = AES.new(session_key, AES.MODE_EAX)
    ciphertext, tag = cipher_aes.encrypt_and_digest(msg.encode('utf-
                      8'))
    encrypted_data = cipher_rsa.encrypt(session_key) + 
    cipher_aes.nonce + tag +  ciphertext    
    encrypted_data = base64.b64encode(encrypted_data)

    return encrypted_data.decode()

这给了我这一行的错误

cipher_rsa = PKCS1_OAEP.new(recipient_key)

但我想使用公钥加密会话密钥,如何使用pycryptodome或任何其他方式

2 个答案:

答案 0 :(得分:2)

Pycryptodome 不支持基于椭圆曲线的加密(ECC加密)。

改为使用 ECIES 算法,例如此Python库:https://github.com/kigawas/eciespy

ECIES (椭圆曲线集成加密方案)是混合加密方案,它结合了 ECC公钥加密来对会话进行非对称加密密钥,稍后用于使用对称密码(例如,使用AES-GCM)对输入数据进行加密。

答案 1 :(得分:0)

我知道这是一个古老的问题,但对于其他来到这里的人来说:

您现在可以使用Pycryptodome或Cryptography。以Pycrptodome为例:

files:
  "/opt/elasticbeanstalk/config/private/eb-docker-log-start" :
    mode: "000755"
    owner: root
    group: root
    content: |
      EB_CONFIG_DOCKER_CURRENT_APP=`cat /opt/elasticbeanstalk/deployment/.aws_beanstalk.current-container-id | cut -c 1-12`
      mkdir -p /var/log/eb-docker/containers/eb-current-app/
      ln -sf /var/log/eb-docker/containers/eb-current-app/eb-$EB_CONFIG_DOCKER_CURRENT_APP-stdouterr.log /var/log/eb-docker/containers/eb-current-app/stdouterr.log
      docker logs -f $EB_CONFIG_DOCKER_CURRENT_APP >> /var/log/eb-docker/containers/eb-current-app/eb-$EB_CONFIG_DOCKER_CURRENT_APP-stdouterr.log 2>&1
commands:
  fix_logging:
    command: systemctl restart eb-docker-log.service
    cwd: /home/ec2-user
    test: "[ ! -L /var/log/eb-docker/containers/eb-current-app/stdouterr.log ] && systemctl is-active --quiet eb-docker-log"