from utils import AlphabetUtils as au def encrypt_text(cleartext: str, keyword: str) -> str: """ Encrypts the given text with the given keyword :param cleartext: The text to encrypt :param keyword: The keyword to use :return: The encrypted text """ # If the ciphertext is longer than the keyword, we need to multiply the keyword while len(cleartext) > len(keyword): keyword += keyword resulting = '' for char_index in range(len(cleartext)): char = cleartext[char_index] key = keyword[char_index] cipherchar = _get_corresponding_cipher(char, key) resulting += cipherchar return resulting def decrypt_text(ciphertext: str, keyword: str) -> str: """ Decrypts the given ciphertext with the given keyword :param ciphertext: The text to decrypt :param keyword: The keyword to use :return: The decrypted text """ # If the ciphertext is longer than the keyword, we need to multiply the keyword while len(ciphertext) > len(keyword): keyword += keyword resulting = '' for char_index in range(len(ciphertext)): char = ciphertext[char_index] key = keyword[char_index] clearchar = _get_corresponding_char(char, key) resulting += clearchar return resulting def _get_corresponding_cipher(char: str, key: str) -> str: """ Calculates the corresponding cipher char for the given clearchar/keychar combination using the vigenere square :param char: The cleartext char :param key: The keyword char :return: The cipher char """ char_index = au.get_index_of_letter(char) key_index = au.get_index_of_letter(key) # Based on the layout of the vigenere square, this should in theory work cipher_index = (char_index + key_index) % 26 return au.get_letter_at_index(cipher_index) def _get_corresponding_char(cipher: str, key: str) -> str: """ Calculates the corresponding cleartext char for the given cipherchar/keychar combination using the vigenere square :param cipher: The cipher char :param key: The keyword char :return: The cleartext char """ cipher_index = au.get_index_of_letter(cipher) key_index = au.get_index_of_letter(key) # Based on the layout of the vigenere square, this should in theory work char_index = (cipher_index - key_index) % 26 return au.get_letter_at_index(char_index) if __name__ == '__main__': print(encrypt_text('BonkRocks', 'SuperSecretKeyword')) print(decrypt_text('ticoiggmj', 'SuperSecretKeyword'))