from typing import Optional
from cryptography.fernet import Fernet
from sqlalchemy.engine import make_url


class CryptoHelper:
    """
    A helper class for encryption and decryption using Fernet (symmetric encryption).
    Requires a secret key (URL-safe base64-encoded 32-byte key).
    """

    def __init__(self, secret_key: str):
        self.fernet = Fernet(secret_key)

    @staticmethod
    def generate_key() -> str:
        """
        Generates a new Fernet key.
        Returns the key as a string. Keep this key safe and do not expose it!
        """
        return Fernet.generate_key().decode()

    def encrypt(self, data: str) -> str:
        """
        Encrypts a string and returns the encrypted token.
        """
        return self.fernet.encrypt(data.encode()).decode()

    def decrypt(self, token: str) -> str:
        """
        Decrypts an encrypted token and returns the original string.
        """
        return self.fernet.decrypt(token.encode()).decode()

    def decrypt_connection_string(self, encrypted: Optional[str]) -> Optional[str]:
        """
        Decrypts an encrypted connection string and returns it with the password masked.
        Returns None if the input is None.
        """
        if not encrypted:
            return None
        decrypted = self.decrypt(encrypted)
        return make_url(decrypted).render_as_string(hide_password=True)
