0

I am trying to make a password storage system, but am currently struggling with an error from a python module ( cryptography.fernet) . I have tried googling but have come to no avail and am asking here. Does anybody know how to fix this? ( code below )

import PGL
from cryptography.fernet import Fernet as Fn
class APM():
    class database():
        def genkey():
            keyfile = open("D:\\CODING\\Python\\APMKEY.APMKEY", "wb")
            key = Fn.generate_key()
            keyfile.write(key)
        def encrypt(self):
            key = open("D:\\CODING\\Python\\APMKEY.APMKEY", "rb")
            database = open("D:\\CODING\\Python\\APMDatabase.APMDATA", "w")

            newdata = Fn(key).encrypt(database.encode())
            database.write(newdata)
        def decrypt(self):
            key = open("D:\\CODING\\Python\\APMKEY.APMKEY", "rb")
            database = open("D:\\CODING\\Python\\APMDatabase.APMDATA", "w")

            newdata = Fn(key).decrypt(database)
            database.write(newdata)
        def access(self):
            database = open("D:\\CODING\\Python\\APMDatabase.APMDATA", "r")
            content = database.readlines()
            print(content)
        def write(self):
            database = open("D:\\CODING\\Python\\APMDatabase.APMDATA", "a")
            database.write("\"NAME OF SITE\", \"WEBSITE URL\", \"USERNAME\", \"PASSWORD\", \"XTRA INFO\"\n")
        def reencrypt():
            key = Fn.generate_key()
            keyfile = open("D:\\CODING\\Python\\APMKEY.APMKEY", "r")
            oldkey = keyfile.read()
            keyfile.close()
            keyfile = open("D:\\CODING\\Python\\APMKEY.APMKEY", "w")
            keyfile.write(key)
            APM.database.decrypt(oldkey)
            APM.database.encrypt(key)



    class gen():
        def password():
            PGL.gen.password()
        def username():
            PGL.gen.username()

APM.database.encrypt("a")

for more context, PGL is a file which generates a password and a username for me, and the "a" in the function "APM.database.encrypt("a")" is just a filler for self, as i havent implemented it fully. Traceback:

Traceback (most recent call last):
  File "D:\CODING\Python\APM.py", line 51, in <module>
    APM.database.encrypt("a")
  File "D:\CODING\Python\APM.py", line 18, in encrypt
    newdata = Fn(key).encrypt(database.encode())
  File "C:\Users\Anton\AppData\Local\Programs\Python\Python310\lib\site-packages\cryptography\fernet.py", line 33, in __init__
    key = base64.urlsafe_b64decode(key)
  File "C:\Users\Anton\AppData\Local\Programs\Python\Python310\lib\base64.py", line 131, in urlsafe_b64decode
    s = _bytes_from_decode_data(s)
  File "C:\Users\Anton\AppData\Local\Programs\Python\Python310\lib\base64.py", line 45, in _bytes_from_decode_data
    raise TypeError("argument should be a bytes-like object or ASCII "
TypeError: argument should be a bytes-like object or ASCII string, not 'BufferedReader'
Press any key to continue . . .
1
  • (1) As it is, you're leaking file handles left and right. Please use with blocks. (2) Show the traceback to your error, please. You're evidently passing a file handle to something that expects data, but we can't tell what. (3) Don't use nested classes as namespaces. You're mixing and matching what should be static methods with non-static methods anyway... Commented Oct 24, 2022 at 13:08

1 Answer 1

1

By the looks of it, you might want something like this. (You should maybe brush up on how classes and instance methods work.)

from cryptography.fernet import Fernet


class APMDatabase:
    def __init__(self, keyfile_path, database_path):
        self.keyfile_path = keyfile_path
        self.database_path = database_path

    def generate_key(self):
        key = Fernet.generate_key()
        with open(self.keyfile_path, "wb") as keyfile:
            keyfile.write(key)

    def read_key(self):
        with open(self.keyfile_path, "rb") as keyfile:
            return keyfile.read()

    def encrypt(self):
        key = self.read_key()
        with open(self.database_path, "rb") as database:
            newdata = Fernet(key).encrypt(database.read())
        with open(self.database_path, "wb") as database:
            database.write(newdata)

    def decrypt(self):
        key = self.read_key()
        with open(self.database_path, "rb") as database:
            newdata = Fernet(key).decrypt(database.read())
        with open(self.database_path, "wb") as database:
            database.write(newdata)

    def write(self, line):
        # NB: database must be decrypted before calling this
        with open(self.database_path, "a") as database:
            database.write(line)

    def reencrypt(self):
        self.decrypt()  # decrypt with current key
        self.generate_key()  # generate and write new key
        self.encrypt()  # encrypt with new key


db = APMDatabase(
    keyfile_path="D:\\CODING\\Python\\APMKEY.APMKEY",
    database_path="D:\\CODING\\Python\\APMDatabase.APMDATA",
)

db.write('"NAME OF SITE", "WEBSITE URL", "USERNAME", "PASSWORD", "XTRA INFO"\n')
db.encrypt()
Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.