kaann.gunerr
kaann.gunerr

Reputation: 170

Implementing Laravel crypt and decrypt functions in python

I was able to find the decrypt function with a few researches, and now I am trying to write laravel encrypt function using python.

I can decrypt using it:

class decrypter:
    def __init__(cls, key):
        cls.key = key

    def decrypt(cls, text):
        decoded_text = json.loads(base64.b64decode(text))
        iv = base64.b64decode(decoded_text['iv'])

        crypt_object = AES.new(key=cls.key, mode=AES.MODE_CBC, IV=iv)

        decoded = base64.b64decode(decoded_text['value'])
        decrypted = crypt_object.decrypt(decoded)

        return unpad(decrypted, 16).decode('utf-8')


def decrypt_string(str):
    try:
        key = b"xxxx+xxxxxx+x+xxxx+xxxxx"
        key = base64.b64decode(key)
        msg = str
        obj = decrypter(key)
        decrypted = obj.decrypt(msg)
        return decrypted
    except Exception as e:
        logla.logla(e, "decrypt_string")
        print(e)

But I couldn't find a source for the encrypt method. There is a source I could find, but I couldn't run it.

enter link description here

Upvotes: 0

Views: 711

Answers (1)

user21105343
user21105343

Reputation:

For encryption, proceed in the opposite direction:

  • Create an IV
  • Pad plaintext
  • Save IV and ciphertext to JSON
  • Encode JSON with Base64

For encryption as in the linked code, additionally the MAC has to be generated and the PHP serialization has to be used:

import json
import base64
from Crypto.Cipher import AES
from Crypto.Util.Padding import pad, unpad
from Crypto.Random import get_random_bytes
from Crypto.Hash import HMAC, SHA256
from phpserialize import loads, dumps

class encrypter:

    def __init__(cls, key):
        cls.key = key

    def encrypt(cls, text):
        text = dumps(text)
        msg = pad(text, 16)
        iv = get_random_bytes(16) # b'0123456789012345'       
        crypt_object = AES.new(key=cls.key, mode=AES.MODE_CBC, IV=iv)
        encrypted = crypt_object.encrypt(msg)
        ivB64 = base64.b64encode(iv)
        encryptedB64 = base64.b64encode(encrypted)
        mac = HMAC.new(cls.key, digestmod=SHA256).update(ivB64+encryptedB64).hexdigest()       
        json_string = json.dumps({'iv': ivB64.decode(), 'value': encryptedB64.decode(), 'mac': mac})
        return base64.b64encode(json_string.encode())

def encrypt_string(str, key):
    try:
        msg = str.encode()
        obj = encrypter(key)
        encrypted = obj.encrypt(msg)
        return encrypted
    except Exception as e:
        print(e)

# Test
keyB64 = b'MDEyMzQ1Njc4OTAxMjM0NTY3ODkwMTIzNDU2Nzg5MDE='
key = base64.b64decode(keyB64)
plaintext= 'This is a test plaintext'
encrypted = encrypt_string(plaintext, key)
decrypted = decrypt_string(encrypted, key)
print(encrypted)
print(base64.b64decode(encrypted))

For the test-IV b'0123456789012345' the output is:

b'eyJpdiI6ICJNREV5TXpRMU5qYzRPVEF4TWpNME5RPT0iLCAidmFsdWUiOiAiTlE1djFpaWU1QnFoTWNwRlhNdUFSZ2N3YVlrNG5CZlJyYmRKUGRna3FDcUN6NEZ6ZDhSOHhIUy95N1N3TWlQTyIsICJtYWMiOiAiYmYwNGJjMWEyN2NhNWUzMGFlYTdjZTI4Y2FkYTBlZGVjOGEwMzc3NWZhODVhMDc2MGRhODUzNDc1OTBmYmNmZCJ9'
b'{"iv": "MDEyMzQ1Njc4OTAxMjM0NQ==", "value": "NQ5v1iie5BqhMcpFXMuARgcwaYk4nBfRrbdJPdgkqCqCz4Fzd8R8xHS/y7SwMiPO", "mac": "bf04bc1a27ca5e30aea7ce28cada0edec8a03775fa85a0760da85347590fbcfd"}'

The linked code produces the same output using the same plaintext, key, and test-IV.

Upvotes: 1

Related Questions