forked from home-assistant/core
add tests
This commit is contained in:
@@ -4,6 +4,8 @@ from collections.abc import AsyncGenerator, Generator
|
||||
from unittest.mock import AsyncMock, patch
|
||||
|
||||
from aioimmich import ImmichAlbums, ImmichAssests, ImmichServer, ImmichUsers
|
||||
from aioimmich.albums.models import ImmichAddAssetsToAlbumResponse
|
||||
from aioimmich.assets.models import ImmichAssetUploadResponse
|
||||
from aioimmich.server.models import (
|
||||
ImmichServerAbout,
|
||||
ImmichServerStatistics,
|
||||
@@ -61,6 +63,12 @@ def mock_immich_albums() -> AsyncMock:
|
||||
mock = AsyncMock(spec=ImmichAlbums)
|
||||
mock.async_get_all_albums.return_value = [MOCK_ALBUM_WITHOUT_ASSETS]
|
||||
mock.async_get_album_info.return_value = MOCK_ALBUM_WITH_ASSETS
|
||||
mock.async_add_assets_to_album.return_value = [
|
||||
ImmichAddAssetsToAlbumResponse.from_dict(
|
||||
{"id": "abcdef-0123456789", "success": True}
|
||||
)
|
||||
]
|
||||
|
||||
return mock
|
||||
|
||||
|
||||
@@ -70,6 +78,9 @@ def mock_immich_assets() -> AsyncMock:
|
||||
mock = AsyncMock(spec=ImmichAssests)
|
||||
mock.async_view_asset.return_value = b"xxxx"
|
||||
mock.async_play_video_stream.return_value = MockStreamReaderChunked(b"xxxx")
|
||||
mock.async_upload_asset.return_value = ImmichAssetUploadResponse.from_dict(
|
||||
{"id": "abcdef-0123456789", "status": "created"}
|
||||
)
|
||||
return mock
|
||||
|
||||
|
||||
|
267
tests/components/immich/test_services.py
Normal file
267
tests/components/immich/test_services.py
Normal file
@@ -0,0 +1,267 @@
|
||||
"""Test the Immich services."""
|
||||
|
||||
from pathlib import Path
|
||||
from unittest.mock import Mock
|
||||
|
||||
from aioimmich.exceptions import ImmichError, ImmichNotFoundError
|
||||
import pytest
|
||||
|
||||
from homeassistant.components.immich.const import DOMAIN
|
||||
from homeassistant.components.immich.services import SERVICE_UPLOAD_FILE
|
||||
from homeassistant.core import HomeAssistant
|
||||
from homeassistant.exceptions import ServiceValidationError
|
||||
from homeassistant.helpers import entity_registry as er
|
||||
|
||||
from . import setup_integration
|
||||
|
||||
from tests.common import MockConfigEntry
|
||||
|
||||
|
||||
async def test_setup_services(
|
||||
hass: HomeAssistant,
|
||||
mock_immich: Mock,
|
||||
mock_config_entry: MockConfigEntry,
|
||||
) -> None:
|
||||
"""Test setup of immich services."""
|
||||
await setup_integration(hass, mock_config_entry)
|
||||
|
||||
services = hass.services.async_services_for_domain(DOMAIN)
|
||||
assert services
|
||||
assert SERVICE_UPLOAD_FILE in services
|
||||
|
||||
|
||||
async def test_upload_file(
|
||||
hass: HomeAssistant,
|
||||
mock_immich: Mock,
|
||||
mock_config_entry: MockConfigEntry,
|
||||
tmp_path: Path,
|
||||
) -> None:
|
||||
"""Test upload_file service."""
|
||||
test_file = tmp_path / "image.png"
|
||||
test_file.write_bytes(b"abcdef")
|
||||
|
||||
await setup_integration(hass, mock_config_entry)
|
||||
|
||||
await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_UPLOAD_FILE,
|
||||
{
|
||||
"config_entry_id": mock_config_entry.entry_id,
|
||||
"file": test_file.as_posix(),
|
||||
},
|
||||
blocking=True,
|
||||
)
|
||||
|
||||
mock_immich.assets.async_upload_asset.assert_called_with(test_file.as_posix())
|
||||
mock_immich.albums.async_get_album_info.assert_not_called()
|
||||
mock_immich.albums.async_add_assets_to_album.assert_not_called()
|
||||
|
||||
|
||||
async def test_upload_file_to_album(
|
||||
hass: HomeAssistant,
|
||||
mock_immich: Mock,
|
||||
mock_config_entry: MockConfigEntry,
|
||||
tmp_path: Path,
|
||||
) -> None:
|
||||
"""Test upload_file service with target album_id."""
|
||||
test_file = tmp_path / "image.png"
|
||||
test_file.write_bytes(b"abcdef")
|
||||
|
||||
await setup_integration(hass, mock_config_entry)
|
||||
|
||||
await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_UPLOAD_FILE,
|
||||
{
|
||||
"config_entry_id": mock_config_entry.entry_id,
|
||||
"file": test_file.as_posix(),
|
||||
"album_id": "721e1a4b-aa12-441e-8d3b-5ac7ab283bb6",
|
||||
},
|
||||
blocking=True,
|
||||
)
|
||||
|
||||
mock_immich.assets.async_upload_asset.assert_called_with(test_file.as_posix())
|
||||
mock_immich.albums.async_get_album_info.assert_called_with(
|
||||
"721e1a4b-aa12-441e-8d3b-5ac7ab283bb6", True
|
||||
)
|
||||
mock_immich.albums.async_add_assets_to_album.assert_called_with(
|
||||
"721e1a4b-aa12-441e-8d3b-5ac7ab283bb6", ["abcdef-0123456789"]
|
||||
)
|
||||
|
||||
|
||||
async def test_upload_file_config_entry_not_found(
|
||||
hass: HomeAssistant,
|
||||
mock_immich: Mock,
|
||||
mock_config_entry: MockConfigEntry,
|
||||
) -> None:
|
||||
"""Test upload_file service raising config_entry_not_found."""
|
||||
await setup_integration(hass, mock_config_entry)
|
||||
|
||||
with pytest.raises(
|
||||
ServiceValidationError,
|
||||
match='Failed to perform action "upload_file". Config entry not found',
|
||||
):
|
||||
await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_UPLOAD_FILE,
|
||||
{
|
||||
"config_entry_id": "unknown_entry",
|
||||
"file": "blabla",
|
||||
},
|
||||
blocking=True,
|
||||
)
|
||||
|
||||
|
||||
async def test_upload_file_config_entry_not_loaded(
|
||||
hass: HomeAssistant,
|
||||
mock_immich: Mock,
|
||||
mock_config_entry: MockConfigEntry,
|
||||
) -> None:
|
||||
"""Test upload_file service raising config_entry_not_loaded."""
|
||||
mock_config_entry.disabled_by = er.RegistryEntryDisabler.USER
|
||||
await setup_integration(hass, mock_config_entry)
|
||||
|
||||
with pytest.raises(
|
||||
ServiceValidationError,
|
||||
match='Failed to perform action "upload_file". Config entry not loaded',
|
||||
):
|
||||
await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_UPLOAD_FILE,
|
||||
{
|
||||
"config_entry_id": mock_config_entry.entry_id,
|
||||
"file": "blabla",
|
||||
},
|
||||
blocking=True,
|
||||
)
|
||||
|
||||
|
||||
async def test_upload_file_file_not_found(
|
||||
hass: HomeAssistant,
|
||||
mock_immich: Mock,
|
||||
mock_config_entry: MockConfigEntry,
|
||||
) -> None:
|
||||
"""Test upload_file service raising file_not_found."""
|
||||
await setup_integration(hass, mock_config_entry)
|
||||
|
||||
with pytest.raises(
|
||||
ServiceValidationError,
|
||||
match='Failed to perform action "upload_file". File `not_existing.file` not found',
|
||||
):
|
||||
await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_UPLOAD_FILE,
|
||||
{
|
||||
"config_entry_id": mock_config_entry.entry_id,
|
||||
"file": "not_existing.file",
|
||||
},
|
||||
blocking=True,
|
||||
)
|
||||
|
||||
|
||||
async def test_upload_file_album_not_found(
|
||||
hass: HomeAssistant,
|
||||
mock_immich: Mock,
|
||||
mock_config_entry: MockConfigEntry,
|
||||
tmp_path: Path,
|
||||
) -> None:
|
||||
"""Test upload_file service raising album_not_found."""
|
||||
test_file = tmp_path / "image.png"
|
||||
test_file.write_bytes(b"abcdef")
|
||||
|
||||
await setup_integration(hass, mock_config_entry)
|
||||
|
||||
mock_immich.albums.async_get_album_info.side_effect = ImmichNotFoundError(
|
||||
{
|
||||
"message": "Not found or no album.read access",
|
||||
"error": "Bad Request",
|
||||
"statusCode": 400,
|
||||
"correlationId": "nyzxjkno",
|
||||
}
|
||||
)
|
||||
|
||||
with pytest.raises(
|
||||
ServiceValidationError,
|
||||
match='Failed to perform action "upload_file". Album with id `721e1a4b-aa12-441e-8d3b-5ac7ab283bb6` not found',
|
||||
):
|
||||
await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_UPLOAD_FILE,
|
||||
{
|
||||
"config_entry_id": mock_config_entry.entry_id,
|
||||
"file": test_file.as_posix(),
|
||||
"album_id": "721e1a4b-aa12-441e-8d3b-5ac7ab283bb6",
|
||||
},
|
||||
blocking=True,
|
||||
)
|
||||
|
||||
|
||||
async def test_upload_file_upload_failed(
|
||||
hass: HomeAssistant,
|
||||
mock_immich: Mock,
|
||||
mock_config_entry: MockConfigEntry,
|
||||
tmp_path: Path,
|
||||
) -> None:
|
||||
"""Test upload_file service raising upload_failed."""
|
||||
test_file = tmp_path / "image.png"
|
||||
test_file.write_bytes(b"abcdef")
|
||||
|
||||
await setup_integration(hass, mock_config_entry)
|
||||
|
||||
mock_immich.assets.async_upload_asset.side_effect = ImmichError(
|
||||
{
|
||||
"message": "Boom! Upload failed",
|
||||
"error": "Bad Request",
|
||||
"statusCode": 400,
|
||||
"correlationId": "nyzxjkno",
|
||||
}
|
||||
)
|
||||
with pytest.raises(
|
||||
ServiceValidationError,
|
||||
match=f'Failed to perform action "upload_file". Upload of file `{test_file.as_posix()}` failed',
|
||||
):
|
||||
await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_UPLOAD_FILE,
|
||||
{
|
||||
"config_entry_id": mock_config_entry.entry_id,
|
||||
"file": test_file.as_posix(),
|
||||
},
|
||||
blocking=True,
|
||||
)
|
||||
|
||||
|
||||
async def test_upload_file_to_album_upload_failed(
|
||||
hass: HomeAssistant,
|
||||
mock_immich: Mock,
|
||||
mock_config_entry: MockConfigEntry,
|
||||
tmp_path: Path,
|
||||
) -> None:
|
||||
"""Test upload_file service with target album_id raising upload_failed."""
|
||||
test_file = tmp_path / "image.png"
|
||||
test_file.write_bytes(b"abcdef")
|
||||
|
||||
await setup_integration(hass, mock_config_entry)
|
||||
|
||||
mock_immich.albums.async_add_assets_to_album.side_effect = ImmichError(
|
||||
{
|
||||
"message": "Boom! Add to album failed.",
|
||||
"error": "Bad Request",
|
||||
"statusCode": 400,
|
||||
"correlationId": "nyzxjkno",
|
||||
}
|
||||
)
|
||||
with pytest.raises(
|
||||
ServiceValidationError,
|
||||
match=f'Failed to perform action "upload_file". Upload of file `{test_file.as_posix()}` failed',
|
||||
):
|
||||
await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_UPLOAD_FILE,
|
||||
{
|
||||
"config_entry_id": mock_config_entry.entry_id,
|
||||
"file": test_file.as_posix(),
|
||||
"album_id": "721e1a4b-aa12-441e-8d3b-5ac7ab283bb6",
|
||||
},
|
||||
blocking=True,
|
||||
)
|
Reference in New Issue
Block a user