-
Notifications
You must be signed in to change notification settings - Fork 786
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #1506 from guardicore/mongo_key_encryption
Mongo key encryption
- Loading branch information
Showing
37 changed files
with
280 additions
and
175 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
32 changes: 32 additions & 0 deletions
32
monkey/monkey_island/cc/resources/auth/credential_utils.py
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,32 @@ | ||
import json | ||
from typing import Tuple | ||
|
||
import bcrypt | ||
from flask import Request, request | ||
|
||
from monkey_island.cc.environment.user_creds import UserCreds | ||
|
||
|
||
def hash_password(plaintext_password): | ||
salt = bcrypt.gensalt() | ||
password_hash = bcrypt.hashpw(plaintext_password.encode("utf-8"), salt) | ||
|
||
return password_hash.decode() | ||
|
||
|
||
def password_matches_hash(plaintext_password, password_hash): | ||
return bcrypt.checkpw(plaintext_password.encode("utf-8"), password_hash.encode("utf-8")) | ||
|
||
|
||
def get_user_credentials_from_request(_request) -> UserCreds: | ||
username, password = get_username_password_from_request(_request) | ||
password_hash = hash_password(password) | ||
|
||
return UserCreds(username, password_hash) | ||
|
||
|
||
def get_username_password_from_request(_request: Request) -> Tuple[str, str]: | ||
cred_dict = json.loads(request.data) | ||
username = cred_dict.get("username", "") | ||
password = cred_dict.get("password", "") | ||
return username, password |
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
23 changes: 14 additions & 9 deletions
23
monkey/monkey_island/cc/server_utils/encryption/__init__.py
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
65 changes: 37 additions & 28 deletions
65
monkey/monkey_island/cc/server_utils/encryption/data_store_encryptor.py
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,50 +1,59 @@ | ||
import os | ||
from typing import Union | ||
|
||
# PyCrypto is deprecated, but we use pycryptodome, which uses the exact same imports but | ||
# is maintained. | ||
from Crypto import Random # noqa: DUO133 # nosec: B413 | ||
|
||
from monkey_island.cc.server_utils.encryption import KeyBasedEncryptor | ||
from monkey_island.cc.server_utils.encryption import ( | ||
IEncryptor, | ||
KeyBasedEncryptor, | ||
PasswordBasedBytesEncryptor, | ||
) | ||
from monkey_island.cc.server_utils.file_utils import open_new_securely_permissioned_file | ||
|
||
_encryptor = None | ||
_KEY_FILENAME = "mongo_key.bin" | ||
_BLOCK_SIZE = 32 | ||
|
||
_encryptor: Union[None, IEncryptor] = None | ||
|
||
class DataStoreEncryptor: | ||
_BLOCK_SIZE = 32 | ||
_KEY_FILENAME = "mongo_key.bin" | ||
|
||
def __init__(self, key_file_dir): | ||
key_file = os.path.join(key_file_dir, self._KEY_FILENAME) | ||
def _load_existing_key(key_file_path: str, secret: str) -> KeyBasedEncryptor: | ||
with open(key_file_path, "rb") as f: | ||
encrypted_key = f.read() | ||
cipher_key = PasswordBasedBytesEncryptor(secret).decrypt(encrypted_key) | ||
return KeyBasedEncryptor(cipher_key) | ||
|
||
if os.path.exists(key_file): | ||
self._load_existing_key(key_file) | ||
else: | ||
self._init_key(key_file) | ||
|
||
self._key_base_encryptor = KeyBasedEncryptor(self._cipher_key) | ||
def _create_new_key(key_file_path: str, secret: str) -> KeyBasedEncryptor: | ||
cipher_key = _get_random_bytes() | ||
encrypted_key = PasswordBasedBytesEncryptor(secret).encrypt(cipher_key) | ||
with open_new_securely_permissioned_file(key_file_path, "wb") as f: | ||
f.write(encrypted_key) | ||
return KeyBasedEncryptor(cipher_key) | ||
|
||
def _init_key(self, password_file_path: str): | ||
self._cipher_key = Random.new().read(self._BLOCK_SIZE) | ||
with open_new_securely_permissioned_file(password_file_path, "wb") as f: | ||
f.write(self._cipher_key) | ||
|
||
def _load_existing_key(self, key_file): | ||
with open(key_file, "rb") as f: | ||
self._cipher_key = f.read() | ||
def _get_random_bytes() -> bytes: | ||
return Random.new().read(_BLOCK_SIZE) | ||
|
||
def enc(self, message: str): | ||
return self._key_base_encryptor.encrypt(message) | ||
|
||
def dec(self, enc_message: str): | ||
return self._key_base_encryptor.decrypt(enc_message) | ||
def remove_old_datastore_key(key_file_dir: str): | ||
key_file_path = _get_key_file_path(key_file_dir) | ||
if os.path.isfile(key_file_path): | ||
os.remove(key_file_path) | ||
|
||
|
||
def initialize_datastore_encryptor(key_file_dir): | ||
def initialize_datastore_encryptor(key_file_dir: str, secret: str): | ||
global _encryptor | ||
|
||
_encryptor = DataStoreEncryptor(key_file_dir) | ||
key_file_path = _get_key_file_path(key_file_dir) | ||
if os.path.exists(key_file_path): | ||
_encryptor = _load_existing_key(key_file_path, secret) | ||
else: | ||
_encryptor = _create_new_key(key_file_path, secret) | ||
|
||
|
||
def get_datastore_encryptor(): | ||
def _get_key_file_path(key_file_dir: str) -> str: | ||
return os.path.join(key_file_dir, _KEY_FILENAME) | ||
|
||
|
||
def get_datastore_encryptor() -> IEncryptor: | ||
return _encryptor |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Empty file.
File renamed without changes.
File renamed without changes.
Oops, something went wrong.