class KeyGenerator: def __init__(self, key_directory=None): self.scr = SystemConfigReader() ssc = SystemConfigReader() database_options = ssc.get_all_values_from_section('Database') self.__dbm = DatabaseManagerMongo(**database_options) self.ssw = SystemSettingsWriter(self.__dbm) self.key_directory = key_directory or SystemConfigReader.DEFAULT_CONFIG_LOCATION + "/keys" def generate_rsa_keypair(self): from Crypto.PublicKey import RSA key = RSA.generate(2048) private_key = key.export_key() public_key = key.publickey().export_key() asymmetric_key = {'private': private_key, 'public': public_key} self.ssw.write('security', {'asymmetric_key': asymmetric_key}) def generate_symmetric_aes_key(self): from Crypto import Random self.ssw.write('security', {'symmetric_aes_key': Random.get_random_bytes(32)})
class SecurityManager: DEFAULT_BLOCK_SIZE = 32 DEFAULT_ALG = 'HS512' DEFAULT_EXPIRES = int(10) def __init__(self, database_manager): self.ssr = SystemSettingsReader(database_manager) self.ssw = SystemSettingsWriter(database_manager) self.salt = "cmdb" def generate_hmac(self, data): import hashlib import hmac generated_hash = hmac.new(self.get_symmetric_aes_key(), bytes(data + self.salt, 'utf-8'), hashlib.sha256) generated_hash.hexdigest() return base64.b64encode(generated_hash.digest()).decode("utf-8") def encrypt_aes(self, raw): """ see https://stackoverflow.com/questions/12524994/encrypt-decrypt-using-pycrypto-aes-256 :param raw: unencrypted data :return: """ if type(raw) == list: import json from bson import json_util raw = json.dumps(raw, default=json_util.default) raw = SecurityManager._pad(raw).encode('UTF-8') iv = Random.new().read(AES.block_size) cipher = AES.new(self.get_symmetric_aes_key(), AES.MODE_CBC, iv) return base64.b64encode(iv + cipher.encrypt(raw)) def decrypt_aes(self, enc): enc = base64.b64decode(enc) iv = enc[:AES.block_size] cipher = AES.new(self.get_symmetric_aes_key(), AES.MODE_CBC, iv) return SecurityManager._unpad(cipher.decrypt( enc[AES.block_size:])).decode('utf-8') @staticmethod def _pad(s): return s + (SecurityManager.DEFAULT_BLOCK_SIZE - len(s) % SecurityManager.DEFAULT_BLOCK_SIZE) * \ chr(SecurityManager.DEFAULT_BLOCK_SIZE - len(s) % SecurityManager.DEFAULT_BLOCK_SIZE) @staticmethod def _unpad(s): return s[:-ord(s[len(s) - 1:])] def generate_symmetric_aes_key(self): return self.ssw.write( 'security', {'symmetric_aes_key': Random.get_random_bytes(32)}) def get_symmetric_aes_key(self): try: symmetric_key = self.ssr.get_value('symmetric_aes_key', 'security') except NoDocumentFound: self.generate_symmetric_aes_key() symmetric_key = self.ssr.get_value('symmetric_aes_key', 'security') return symmetric_key @staticmethod def encode_object_base_64(data: object): from bson.json_util import dumps return base64.b64encode(dumps(data).encode('utf-8')).decode("utf-8")