I am very new at python, I was working on a program that encrypts a text string, then saves it to a file. My program works perfectly when I encrypt then decrypt it in the same session. What I would like to do is: encrypt a file, then close the program, come back to it later and decrypt it. I don't know how the cryptography module works, but judging how it is called the "key" I assume it would be important for security, but I do not know. When I try to save the fernet key to a text file it displays an error message. When I try to decrypt a message that was encrypted in a previous session it displays 4 errors referencing the cryptography module. To conclude, I was wondering if it is possible to use the cryptography module to decrypt data between sessions. If not, is there an alternate way I could complete this task? Thanks for any help. here is my code:
from cryptography.fernet import Fernet
key = Fernet.generate_key()
f = Fernet(key)
sel = input("Would you like to encrypt or decrypt? (1 = encrypt, 2 = decrypt) ")
if sel == 1:
inp = raw_input("Enter Text: ") # Type here
encoded = f.encrypt(inp)
a, b = encoded[:len(encoded)/2], encoded[len(encoded)/2:]
print ("YOUR PASSWORD: ")
print b
file = open('password.txt', 'w')
file.write(a)
elif sel == 2:
inp = raw_input("Enter Password: ")
file = open('password.txt', 'r')
a = file.readline()
combine = (a + inp)
out = f.decrypt(combine)
print out
here is the error that occurs when you enter a "password" from a previous session:
Traceback (most recent call last):
File "/Users/Zak/PycharmProjects/Password/test.py", line 18, in <module>
out = f.decrypt(combine)
File "/Users/Zak/PycharmProjects/Password/venv/lib/python2.7/site-packages/cryptography/fernet.py", line 75, in decrypt
return self._decrypt_data(data, timestamp, ttl)
File "/Users/Zak/PycharmProjects/Password/venv/lib/python2.7/site-packages/cryptography/fernet.py", line 119, in _decrypt_data
self._verify_signature(data)
File "/Users/Zak/PycharmProjects/Password/venv/lib/python2.7/site-packages/cryptography/fernet.py", line 108, in _verify_signature
raise InvalidToken
cryptography.fernet.InvalidToken
Also this is what happens when you edit the code to save the key to a blank .txt file. Keep in mind this error does not reflect the code above.
Traceback (most recent call last):
File "/Users/Zak/PycharmProjects/Password/test.py", line 5, in <module>
file.write(f)
TypeError: expected a character buffer object
fernet import Fernet def write_key(): """ Generates a key and save it into a file """ key = Fernet. generate_key() with open("key. key", "wb") as key_file: key_file. write(key) def load_key(): """ Loads the key from the current directory named `key.
derive(password)) f = Fernet(key) token = f. encrypt(b"Secret message!") token # b'...' f. decrypt(token) # b'Secret message!
The result of this encryption is known as a “Fernet token” and has strong privacy and authenticity guarantees. data (bytes) – The message you would like to encrypt. A secure message that cannot be read or altered without the key. It is URL-safe base64-encoded.
A fernet key is used to encrypt and decrypt fernet tokens. Each key is actually composed of two smaller keys: a 128-bit AES encryption key and a 128-bit SHA256 HMAC signing key. The keys are held in a key repository that keystone passes to a library that handles the encryption and decryption of tokens.
With a few modifications, your script can be made to work the way you intended (but read the answer until the end to learn why this might no be an entirely good idea):
from cryptography.fernet import Fernet
sel = input("Would you like to encrypt or decrypt? (1 = encrypt, 2 = decrypt) ")
if sel == 1:
key = Fernet.generate_key()
print ("YOUR KEY: ")
print key
f = Fernet(key)
inp = raw_input("Enter Text: ") # Type here
encoded = f.encrypt(inp)
with open('encoded.txt', 'w') as file:
file.write(encoded)
elif sel == 2:
inp = raw_input("Enter Key: ")
f = Fernet(inp)
with open('encoded.txt', 'r') as file:
encoded = file.readline()
out = f.decrypt(encoded)
print out
Testing it:
$ python2 test.py
Would you like to encrypt or decrypt? (1 = encrypt, 2 = decrypt) 1
YOUR KEY:
gRNCcDPDnSzqT2RT4nFJA6MYtsJkBG85sMEy9TogRYg=
Enter Text: This is a secret
$ python2 test.py
Would you like to encrypt or decrypt? (1 = encrypt, 2 = decrypt) 2
Enter Key: gRNCcDPDnSzqT2RT4nFJA6MYtsJkBG85sMEy9TogRYg=
This is a secret
You may have noticed that I changed the word PASSWORD
into KEY
-- because that long string of characters is actually the key (in a URL-safe, base64-encoded form) used for the encrypt()
and decrypt()
transformations.
In practice, this is normally not what you would be doing. The key can not be memorized and people would typically store it somewhere in a file and use copy-paste to enter it. This increases the risk that the key will leak.
As an alternative, a so-called key-derivation mechanism can be used. In that case, the key
bytes are not generated randomly with the Fernet.generate_key()
function, but they are calculated using a key-derivation function that is applied to a, easier to memorize but well-chosen, passphrase. For an example of that, see the section Using passwords with Fernet.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With