-
Notifications
You must be signed in to change notification settings - Fork 0
/
script.py
63 lines (61 loc) · 2.11 KB
/
script.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
import os
from cryptography.hazmat.primitives.kdf.scrypt import Scrypt
from cryptography.hazmat.primitives import hashes, hmac
from cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes
from cryptography.hazmat.backends import default_backend
def encrypt_file(file_name, password):
# Generate a salt
salt = os.urandom(16)
# Generate key from password using the salt and KDF
kdf = Scrypt(
salt=salt,
length=32,
n=2**14,
r=8,
p=1,
backend=default_backend()
)
key = kdf.derive(password)
# Encrypt the file
with open(file_name, "rb") as file:
plaintext = file.read()
cipher = Cipher(algorithms.XChaCha20Poly1305(key), modes.GCM(os.urandom(12)), backend=default_backend())
encryptor = cipher.encryptor()
ciphertext = encryptor.update(plaintext) + encryptor.finalize()
# write the metadata to a json file
metadata = {
'original_name': file_name,
'salt': salt,
'nonce': encryptor.nonce,
'ciphertext': ciphertext,
'tag': encryptor.tag
}
encrypted_file_metadata = file_name + ".metadata"
with open(encrypted_file_metadata, "wb") as f:
f.write(json.dumps(metadata))
os.remove(file_name)
return encrypted_file_metadata
def decrypt_file(file_metadata, password):
# read the metadata from json file
with open(file_metadata, "rb") as f:
metadata = json.loads(f.read())
# Generate key from password using the salt and KDF
salt = metadata['salt']
kdf = Scrypt(
salt=salt,
length=32,
n=2**14,
r=8,
p=1,
backend=default_backend()
)
key = kdf.derive(password)
# Decrypt the file
cipher = Cipher(algorithms.XChaCha20Poly1305(key), modes.GCM(metadata['nonce'], metadata['tag']), backend=default_backend())
decryptor = cipher.decryptor()
plaintext = decryptor.update(metadata['ciphertext']) + decryptor.finalize()
decrypted_file = metadata['original_name']
with open(decrypted_file, "wb") as file:
file.write(plaintext)
os.remove(file_metadata)
return decrypted