I have the following code to transfer an S3 file to Box:
from boxsdk import JWTAuth, Client
import boto3
import json
import os
import tempfile
class BoxTransfer:
def __init__(self, bucket_name=None, file_name=None, folders=None) -> None:
self.bucket_name = bucket_name
self.file_name = file_name
self.folders = folders or {}
json_data = json.loads(os.environ['BOX_AUTHENTICATION'])
auth = JWTAuth(
client_id=json_data['boxAppSettings']['clientID'],
client_secret=json_data['boxAppSettings']['clientSecret'],
enterprise_id=json_data['enterpriseID'],
jwt_key_id=json_data['boxAppSettings']['appAuth']['publicKeyID'],
rsa_private_key_data=json_data['boxAppSettings']['appAuth']['privateKey'],
rsa_private_key_passphrase=json_data['boxAppSettings']['appAuth']['passphrase']
)
self.box_client = Client(auth)
self.folder = None
def get_user_id(self):
my_user = self.box_client.user().get()
def upload_file(self):
self.get_user_id()
with tempfile.NamedTemporaryFile() as tmp:
s3 = boto3.client('s3')
s3.download_fileobj(self.bucket_name, self.file_name, tmp)
tmp.seek(0)
s3_folder_name = self.file_name.split("/")[0]
s3_file_name = self.file_name.split("/")[-1]
s3_box_folder = self.folders[s3_folder_name]['box_folder']
self.folder = self.box_client.folder(s3_box_folder)
self.folder.upload(file_path=tmp.name, file_name=s3_file_name)
My problem is when I try to unit test the above. When I use the real box authentication data, the unit test runs fine. But, when I try to replace it with fake authentication data, it fails with the error “ValueError: (‘Could not deserialize key data. The data may be in an incorrect format, it may be encrypted with an unsupported algorithm, or it may be an unsupported key type (e.g. EC curves with explicit parameters).’, [<OpenSSLError(code=503841036, lib=60, reason=524556, reason_text=unsupported)>])”. How can I replace the box authentication with fake authentication in the unit test?
import pytest
import os
import boxsdk
import unittest
from unittest.mock import patch, MagicMock
import json
from lib.box_client import BoxTransfer
class TestBoxClient(unittest.TestCase):
@patch('os.environ')
@patch('boto3.client')
@patch('lib.box_client.BoxTransfer')
def test_get_items_returns_one(self, mock_box_transfer, mock_s3_client, mock_env):
original_os_environ = dict(os.environ)
mock_instance = mock_box_transfer.return_value
mock_instance.folder = MagicMock()
mock_instance.folder.get_items = MagicMock(return_value=[])
mock_s3 = MagicMock()
mock_s3.download_fileobj = MagicMock()
mock_s3_client.return_value = mock_s3
mock_env.__getitem__.side_effect = lambda x: json.dumps({
'boxAppSettings': {
'clientID': 'fake_client_id',
'clientSecret': 'fake_client_secret',
'appAuth': {
'publicKeyID': 'fake_key_id',
'privateKey': '-----BEGIN PRIVATE KEY-----fake_private_keyn-----END PRIVATE KEY-----',
'passphrase': 'fake_passphrase'
}
},
'enterpriseID': 'fake_enterprise_id'
}) if x == 'BOX_AUTHENTICATION' else 'fake_folder_value' if x in ['BOX_FOLDER'] else original_os_environ.get(x, 'default_value')
mock_tmp = MagicMock()
mock_tmp.name = 'fake_name'
box_transfer = BoxTransfer("box-dev", "test.txt")
box_transfer.upload_file(file_path=mock_tmp.name, file_name=s3_file_name)
items = box_transfer.folder.get_items()
self.assertIsInstance(items, boxsdk.pagination.limit_offset_based_object_collection.LimitOffsetBasedObjectCollection)
self.assertEqual(len(list(items)), 1)