import tempfile import unittest from pathlib import Path from unittest.mock import MagicMock, patch from music_server.services.cache_uploaders import S3CacheTargetUploader, SFTPCacheTargetUploader class CacheUploaderTests(unittest.TestCase): @patch("music_server.services.cache_uploaders.paramiko.SSHClient") def test_sftp_uploader_upload_and_delete(self, ssh_client_class): ssh_client = MagicMock() sftp_client = MagicMock() ssh_client.open_sftp.return_value = sftp_client ssh_client_class.return_value = ssh_client with tempfile.TemporaryDirectory() as tmpdir: file_path = Path(tmpdir) / "song.flac" file_path.write_bytes(b"flac-data") uploader = SFTPCacheTargetUploader( host="127.0.0.1", port=22, username="tester", password="secret", remote_root="/srv/music_server_cache", ) uploader.upload_file(local_path=file_path, remote_key="music/song.flac") uploader.delete_file(remote_key="music/song.flac") uploader.test_connection() self.assertEqual(3, ssh_client.connect.call_count) sftp_client.put.assert_called_once_with(str(file_path), "/srv/music_server_cache/music/song.flac") sftp_client.remove.assert_called_once_with("/srv/music_server_cache/music/song.flac") sftp_client.listdir.assert_called_once_with("/srv/music_server_cache") @patch("music_server.services.cache_uploaders._build_boto3_client") def test_s3_uploader_upload_and_delete(self, build_client): s3_client = MagicMock() build_client.return_value = s3_client with tempfile.TemporaryDirectory() as tmpdir: file_path = Path(tmpdir) / "song.flac" file_path.write_bytes(b"flac-data") uploader = S3CacheTargetUploader( bucket="music-cache", region="ap-shanghai", endpoint_url="https://s3.example", access_key_id="AKIA", secret_access_key="SECRET", ) uploader.upload_file(local_path=file_path, remote_key="music/song.flac") uploader.delete_file(remote_key="music/song.flac") uploader.test_connection() s3_client.upload_file.assert_called_once() s3_client.delete_object.assert_called_once_with(Bucket="music-cache", Key="music/song.flac") s3_client.head_bucket.assert_called_once_with(Bucket="music-cache") if __name__ == "__main__": unittest.main()