mirror of
				https://github.com/arcan1s/ahriman.git
				synced 2025-11-03 23:33:41 +00:00 
			
		
		
		
	complete status tests
This commit is contained in:
		@ -14,14 +14,14 @@ def test_process_build(executor: Executor, package_ahriman: Package, mocker: Moc
 | 
			
		||||
    mocker.patch("ahriman.core.build_tools.task.Task.build", return_value=[Path(package_ahriman.base)])
 | 
			
		||||
    mocker.patch("ahriman.core.build_tools.task.Task.init")
 | 
			
		||||
    move_mock = mocker.patch("shutil.move")
 | 
			
		||||
    watcher_client_mock = mocker.patch("ahriman.core.watcher.client.Client.set_building")
 | 
			
		||||
    status_client_mock = mocker.patch("ahriman.core.status.client.Client.set_building")
 | 
			
		||||
 | 
			
		||||
    # must return list of built packages
 | 
			
		||||
    assert executor.process_build([package_ahriman]) == [package_ahriman]
 | 
			
		||||
    # must move files (once)
 | 
			
		||||
    move_mock.assert_called_once()
 | 
			
		||||
    # must update status
 | 
			
		||||
    watcher_client_mock.assert_called_once()
 | 
			
		||||
    status_client_mock.assert_called_once()
 | 
			
		||||
    # must clear directory
 | 
			
		||||
    from ahriman.core.repository.cleaner import Cleaner
 | 
			
		||||
    Cleaner.clear_build.assert_called_once()
 | 
			
		||||
@ -35,10 +35,10 @@ def test_process_build_failure(executor: Executor, package_ahriman: Package, moc
 | 
			
		||||
    mocker.patch("ahriman.core.build_tools.task.Task.build", return_value=[Path(package_ahriman.base)])
 | 
			
		||||
    mocker.patch("ahriman.core.build_tools.task.Task.init")
 | 
			
		||||
    mocker.patch("shutil.move", side_effect=Exception())
 | 
			
		||||
    watcher_client_mock = mocker.patch("ahriman.core.watcher.client.Client.set_failed")
 | 
			
		||||
    status_client_mock = mocker.patch("ahriman.core.status.client.Client.set_failed")
 | 
			
		||||
 | 
			
		||||
    executor.process_build([package_ahriman])
 | 
			
		||||
    watcher_client_mock.assert_called_once()
 | 
			
		||||
    status_client_mock.assert_called_once()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_process_remove_base(executor: Executor, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
@ -47,13 +47,13 @@ def test_process_remove_base(executor: Executor, package_ahriman: Package, mocke
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("ahriman.core.repository.executor.Executor.packages", return_value=[package_ahriman])
 | 
			
		||||
    repo_remove_mock = mocker.patch("ahriman.core.alpm.repo.Repo.remove")
 | 
			
		||||
    watcher_client_mock = mocker.patch("ahriman.core.watcher.client.Client.remove")
 | 
			
		||||
    status_client_mock = mocker.patch("ahriman.core.status.client.Client.remove")
 | 
			
		||||
 | 
			
		||||
    executor.process_remove([package_ahriman.base])
 | 
			
		||||
    # must remove via alpm wrapper
 | 
			
		||||
    repo_remove_mock.assert_called_once()
 | 
			
		||||
    # must update status
 | 
			
		||||
    watcher_client_mock.assert_called_once()
 | 
			
		||||
    status_client_mock.assert_called_once()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_process_remove_base_multiple(executor: Executor, package_python_schedule: Package,
 | 
			
		||||
@ -63,7 +63,7 @@ def test_process_remove_base_multiple(executor: Executor, package_python_schedul
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("ahriman.core.repository.executor.Executor.packages", return_value=[package_python_schedule])
 | 
			
		||||
    repo_remove_mock = mocker.patch("ahriman.core.alpm.repo.Repo.remove")
 | 
			
		||||
    watcher_client_mock = mocker.patch("ahriman.core.watcher.client.Client.remove")
 | 
			
		||||
    status_client_mock = mocker.patch("ahriman.core.status.client.Client.remove")
 | 
			
		||||
 | 
			
		||||
    executor.process_remove([package_python_schedule.base])
 | 
			
		||||
    # must remove via alpm wrapper
 | 
			
		||||
@ -72,7 +72,7 @@ def test_process_remove_base_multiple(executor: Executor, package_python_schedul
 | 
			
		||||
        for package, props in package_python_schedule.packages.items()
 | 
			
		||||
    ], any_order=True)
 | 
			
		||||
    # must update status
 | 
			
		||||
    watcher_client_mock.assert_called_once()
 | 
			
		||||
    status_client_mock.assert_called_once()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_process_remove_base_single(executor: Executor, package_python_schedule: Package,
 | 
			
		||||
@ -82,13 +82,13 @@ def test_process_remove_base_single(executor: Executor, package_python_schedule:
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("ahriman.core.repository.executor.Executor.packages", return_value=[package_python_schedule])
 | 
			
		||||
    repo_remove_mock = mocker.patch("ahriman.core.alpm.repo.Repo.remove")
 | 
			
		||||
    watcher_client_mock = mocker.patch("ahriman.core.watcher.client.Client.remove")
 | 
			
		||||
    status_client_mock = mocker.patch("ahriman.core.status.client.Client.remove")
 | 
			
		||||
 | 
			
		||||
    executor.process_remove(["python2-schedule"])
 | 
			
		||||
    # must remove via alpm wrapper
 | 
			
		||||
    repo_remove_mock.assert_called_once()
 | 
			
		||||
    # must not update status
 | 
			
		||||
    watcher_client_mock.assert_not_called()
 | 
			
		||||
    status_client_mock.assert_not_called()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_process_remove_nothing(executor: Executor, package_ahriman: Package, package_python_schedule: Package,
 | 
			
		||||
@ -131,7 +131,7 @@ def test_process_update(executor: Executor, package_ahriman: Package, mocker: Mo
 | 
			
		||||
    move_mock = mocker.patch("shutil.move")
 | 
			
		||||
    repo_add_mock = mocker.patch("ahriman.core.alpm.repo.Repo.add")
 | 
			
		||||
    sign_package_mock = mocker.patch("ahriman.core.sign.gpg.GPG.sign_package", side_effect=lambda fn, _: [fn])
 | 
			
		||||
    watcher_client_mock = mocker.patch("ahriman.core.watcher.client.Client.set_success")
 | 
			
		||||
    status_client_mock = mocker.patch("ahriman.core.status.client.Client.set_success")
 | 
			
		||||
 | 
			
		||||
    # must return complete
 | 
			
		||||
    assert executor.process_update([Path(package.filename) for package in package_ahriman.packages.values()])
 | 
			
		||||
@ -142,7 +142,7 @@ def test_process_update(executor: Executor, package_ahriman: Package, mocker: Mo
 | 
			
		||||
    # must add package
 | 
			
		||||
    repo_add_mock.assert_called_once()
 | 
			
		||||
    # must update status
 | 
			
		||||
    watcher_client_mock.assert_called_once()
 | 
			
		||||
    status_client_mock.assert_called_once()
 | 
			
		||||
    # must clear directory
 | 
			
		||||
    from ahriman.core.repository.cleaner import Cleaner
 | 
			
		||||
    Cleaner.clear_packages.assert_called_once()
 | 
			
		||||
@ -156,14 +156,14 @@ def test_process_update_group(executor: Executor, package_python_schedule: Packa
 | 
			
		||||
    mocker.patch("shutil.move")
 | 
			
		||||
    mocker.patch("ahriman.models.package.Package.load", return_value=package_python_schedule)
 | 
			
		||||
    repo_add_mock = mocker.patch("ahriman.core.alpm.repo.Repo.add")
 | 
			
		||||
    watcher_client_mock = mocker.patch("ahriman.core.watcher.client.Client.set_success")
 | 
			
		||||
    status_client_mock = mocker.patch("ahriman.core.status.client.Client.set_success")
 | 
			
		||||
 | 
			
		||||
    executor.process_update([Path(package.filename) for package in package_python_schedule.packages.values()])
 | 
			
		||||
    repo_add_mock.assert_has_calls([
 | 
			
		||||
        mock.call(executor.paths.repository / package.filename)
 | 
			
		||||
        for package in package_python_schedule.packages.values()
 | 
			
		||||
    ], any_order=True)
 | 
			
		||||
    watcher_client_mock.assert_called_with(package_python_schedule)
 | 
			
		||||
    status_client_mock.assert_called_with(package_python_schedule)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_process_update_failed(executor: Executor, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
@ -172,10 +172,10 @@ def test_process_update_failed(executor: Executor, package_ahriman: Package, moc
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("shutil.move", side_effect=Exception())
 | 
			
		||||
    mocker.patch("ahriman.models.package.Package.load", return_value=package_ahriman)
 | 
			
		||||
    watcher_client_mock = mocker.patch("ahriman.core.watcher.client.Client.set_failed")
 | 
			
		||||
    status_client_mock = mocker.patch("ahriman.core.status.client.Client.set_failed")
 | 
			
		||||
 | 
			
		||||
    executor.process_update([Path(package.filename) for package in package_ahriman.packages.values()])
 | 
			
		||||
    watcher_client_mock.assert_called_once()
 | 
			
		||||
    status_client_mock.assert_called_once()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_process_update_failed_on_load(executor: Executor, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
 | 
			
		||||
@ -7,28 +7,28 @@ from ahriman.models.package import Package
 | 
			
		||||
def test_updates_aur(update_handler: UpdateHandler, package_ahriman: Package,
 | 
			
		||||
                     mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must provide updates with status watcher updates
 | 
			
		||||
    must provide updates with status updates
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("ahriman.core.repository.update_handler.UpdateHandler.packages", return_value=[package_ahriman])
 | 
			
		||||
    mocker.patch("ahriman.models.package.Package.is_outdated", return_value=True)
 | 
			
		||||
    mocker.patch("ahriman.models.package.Package.load", return_value=package_ahriman)
 | 
			
		||||
    watcher_client_mock = mocker.patch("ahriman.core.watcher.client.Client.set_pending")
 | 
			
		||||
    status_client_mock = mocker.patch("ahriman.core.status.client.Client.set_pending")
 | 
			
		||||
 | 
			
		||||
    assert update_handler.updates_aur([], False) == [package_ahriman]
 | 
			
		||||
    watcher_client_mock.assert_called_once()
 | 
			
		||||
    status_client_mock.assert_called_once()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_updates_aur_failed(update_handler: UpdateHandler, package_ahriman: Package,
 | 
			
		||||
                            mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must update status watcher via client for failed load
 | 
			
		||||
    must update status via client for failed load
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("ahriman.core.repository.update_handler.UpdateHandler.packages", return_value=[package_ahriman])
 | 
			
		||||
    mocker.patch("ahriman.models.package.Package.load", side_effect=Exception())
 | 
			
		||||
    watcher_client_mock = mocker.patch("ahriman.core.watcher.client.Client.set_failed")
 | 
			
		||||
    status_client_mock = mocker.patch("ahriman.core.status.client.Client.set_failed")
 | 
			
		||||
 | 
			
		||||
    update_handler.updates_aur([], False)
 | 
			
		||||
    watcher_client_mock.assert_called_once()
 | 
			
		||||
    status_client_mock.assert_called_once()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_updates_aur_filter(update_handler: UpdateHandler, package_ahriman: Package, package_python_schedule: Package,
 | 
			
		||||
@ -92,10 +92,10 @@ def test_updates_manual_status_known(update_handler: UpdateHandler, package_ahri
 | 
			
		||||
    mocker.patch("pathlib.Path.iterdir", return_value=[package_ahriman.base])
 | 
			
		||||
    mocker.patch("ahriman.core.repository.update_handler.UpdateHandler.packages", return_value=[package_ahriman])
 | 
			
		||||
    mocker.patch("ahriman.models.package.Package.load", return_value=package_ahriman)
 | 
			
		||||
    watcher_client_mock = mocker.patch("ahriman.core.watcher.client.Client.set_pending")
 | 
			
		||||
    status_client_mock = mocker.patch("ahriman.core.status.client.Client.set_pending")
 | 
			
		||||
 | 
			
		||||
    update_handler.updates_manual()
 | 
			
		||||
    watcher_client_mock.assert_called_once()
 | 
			
		||||
    status_client_mock.assert_called_once()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_updates_manual_status_unknown(update_handler: UpdateHandler, package_ahriman: Package,
 | 
			
		||||
@ -106,10 +106,10 @@ def test_updates_manual_status_unknown(update_handler: UpdateHandler, package_ah
 | 
			
		||||
    mocker.patch("pathlib.Path.iterdir", return_value=[package_ahriman.base])
 | 
			
		||||
    mocker.patch("ahriman.core.repository.update_handler.UpdateHandler.packages", return_value=[])
 | 
			
		||||
    mocker.patch("ahriman.models.package.Package.load", return_value=package_ahriman)
 | 
			
		||||
    watcher_client_mock = mocker.patch("ahriman.core.watcher.client.Client.set_unknown")
 | 
			
		||||
    status_client_mock = mocker.patch("ahriman.core.status.client.Client.set_unknown")
 | 
			
		||||
 | 
			
		||||
    update_handler.updates_manual()
 | 
			
		||||
    watcher_client_mock.assert_called_once()
 | 
			
		||||
    status_client_mock.assert_called_once()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_updates_manual_with_failures(update_handler: UpdateHandler, package_ahriman: Package,
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										39
									
								
								tests/ahriman/core/status/conftest.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										39
									
								
								tests/ahriman/core/status/conftest.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,39 @@
 | 
			
		||||
import pytest
 | 
			
		||||
 | 
			
		||||
from pytest_mock import MockerFixture
 | 
			
		||||
from typing import Any, Dict
 | 
			
		||||
 | 
			
		||||
from ahriman.core.configuration import Configuration
 | 
			
		||||
from ahriman.core.status.client import Client
 | 
			
		||||
from ahriman.core.status.watcher import Watcher
 | 
			
		||||
from ahriman.core.status.web_client import WebClient
 | 
			
		||||
from ahriman.models.build_status import BuildStatus, BuildStatusEnum
 | 
			
		||||
from ahriman.models.package import Package
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
# helpers
 | 
			
		||||
@pytest.helpers.register
 | 
			
		||||
def get_package_status(package: Package) -> Dict[str, Any]:
 | 
			
		||||
    return {"status": BuildStatusEnum.Unknown.value, "package": package.view()}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
@pytest.helpers.register
 | 
			
		||||
def get_package_status_extended(package: Package) -> Dict[str, Any]:
 | 
			
		||||
    return {"status": BuildStatus().view(), "package": package.view()}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
# fixtures
 | 
			
		||||
@pytest.fixture
 | 
			
		||||
def client() -> Client:
 | 
			
		||||
    return Client()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
@pytest.fixture
 | 
			
		||||
def watcher(configuration: Configuration, mocker: MockerFixture) -> Watcher:
 | 
			
		||||
    mocker.patch("pathlib.Path.mkdir")
 | 
			
		||||
    return Watcher("x86_64", configuration)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
@pytest.fixture
 | 
			
		||||
def web_client() -> WebClient:
 | 
			
		||||
    return WebClient("localhost", 8080)
 | 
			
		||||
							
								
								
									
										116
									
								
								tests/ahriman/core/status/test_client.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										116
									
								
								tests/ahriman/core/status/test_client.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,116 @@
 | 
			
		||||
from pytest_mock import MockerFixture
 | 
			
		||||
 | 
			
		||||
from ahriman.core.configuration import Configuration
 | 
			
		||||
from ahriman.core.status.client import Client
 | 
			
		||||
from ahriman.core.status.web_client import WebClient
 | 
			
		||||
from ahriman.models.build_status import BuildStatusEnum
 | 
			
		||||
from ahriman.models.package import Package
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_add(client: Client, package_ahriman: Package) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must process package addition without errors
 | 
			
		||||
    """
 | 
			
		||||
    client.add(package_ahriman, BuildStatusEnum.Unknown)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_get(client: Client, package_ahriman: Package) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must return empty package list
 | 
			
		||||
    """
 | 
			
		||||
    assert client.get(package_ahriman.base) == []
 | 
			
		||||
    assert client.get(None) == []
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_get_self(client: Client) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must return unknown status for service
 | 
			
		||||
    """
 | 
			
		||||
    assert client.get_self().status == BuildStatusEnum.Unknown
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_remove(client: Client, package_ahriman: Package) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must process remove without errors
 | 
			
		||||
    """
 | 
			
		||||
    client.remove(package_ahriman.base)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_update(client: Client, package_ahriman: Package) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must update package status without errors
 | 
			
		||||
    """
 | 
			
		||||
    client.update(package_ahriman.base, BuildStatusEnum.Unknown)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_update_self(client: Client) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must update self status without errors
 | 
			
		||||
    """
 | 
			
		||||
    client.update_self(BuildStatusEnum.Unknown)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_set_building(client: Client, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must set building status to the package
 | 
			
		||||
    """
 | 
			
		||||
    update_mock = mocker.patch("ahriman.core.status.client.Client.update")
 | 
			
		||||
    client.set_building(package_ahriman.base)
 | 
			
		||||
 | 
			
		||||
    update_mock.assert_called_with(package_ahriman.base, BuildStatusEnum.Building)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_set_failed(client: Client, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must set failed status to the package
 | 
			
		||||
    """
 | 
			
		||||
    update_mock = mocker.patch("ahriman.core.status.client.Client.update")
 | 
			
		||||
    client.set_failed(package_ahriman.base)
 | 
			
		||||
 | 
			
		||||
    update_mock.assert_called_with(package_ahriman.base, BuildStatusEnum.Failed)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_set_pending(client: Client, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must set building status to the package
 | 
			
		||||
    """
 | 
			
		||||
    update_mock = mocker.patch("ahriman.core.status.client.Client.update")
 | 
			
		||||
    client.set_pending(package_ahriman.base)
 | 
			
		||||
 | 
			
		||||
    update_mock.assert_called_with(package_ahriman.base, BuildStatusEnum.Pending)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_set_success(client: Client, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must set success status to the package
 | 
			
		||||
    """
 | 
			
		||||
    add_mock = mocker.patch("ahriman.core.status.client.Client.add")
 | 
			
		||||
    client.set_success(package_ahriman)
 | 
			
		||||
 | 
			
		||||
    add_mock.assert_called_with(package_ahriman, BuildStatusEnum.Success)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_set_unknown(client: Client, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must add new package with unknown status
 | 
			
		||||
    """
 | 
			
		||||
    add_mock = mocker.patch("ahriman.core.status.client.Client.add")
 | 
			
		||||
    client.set_unknown(package_ahriman)
 | 
			
		||||
 | 
			
		||||
    add_mock.assert_called_with(package_ahriman, BuildStatusEnum.Unknown)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_load_dummy_client(configuration: Configuration) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must load dummy client if no settings set
 | 
			
		||||
    """
 | 
			
		||||
    assert isinstance(Client.load("x86_64", configuration), Client)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_load_full_client(configuration: Configuration) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must load full client if no settings set
 | 
			
		||||
    """
 | 
			
		||||
    configuration.set("web", "host", "localhost")
 | 
			
		||||
    configuration.set("web", "port", "8080")
 | 
			
		||||
    assert isinstance(Client.load("x86_64", configuration), WebClient)
 | 
			
		||||
							
								
								
									
										219
									
								
								tests/ahriman/core/status/test_watcher.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										219
									
								
								tests/ahriman/core/status/test_watcher.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,219 @@
 | 
			
		||||
import pytest
 | 
			
		||||
import tempfile
 | 
			
		||||
 | 
			
		||||
from pathlib import Path
 | 
			
		||||
from pytest_mock import MockerFixture
 | 
			
		||||
from unittest.mock import PropertyMock
 | 
			
		||||
 | 
			
		||||
from ahriman.core.exceptions import UnknownPackage
 | 
			
		||||
from ahriman.core.status.watcher import Watcher
 | 
			
		||||
from ahriman.models.build_status import BuildStatus, BuildStatusEnum
 | 
			
		||||
from ahriman.models.package import Package
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_cache_load(watcher: Watcher, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must load state from cache
 | 
			
		||||
    """
 | 
			
		||||
    response = {"packages": [pytest.helpers.get_package_status_extended(package_ahriman)]}
 | 
			
		||||
 | 
			
		||||
    mocker.patch("pathlib.Path.is_file", return_value=True)
 | 
			
		||||
    mocker.patch("pathlib.Path.open")
 | 
			
		||||
    mocker.patch("json.load", return_value=response)
 | 
			
		||||
 | 
			
		||||
    watcher.known = {package_ahriman.base: (None, None)}
 | 
			
		||||
    watcher._cache_load()
 | 
			
		||||
 | 
			
		||||
    package, status = watcher.known[package_ahriman.base]
 | 
			
		||||
    assert package == package_ahriman
 | 
			
		||||
    assert status.status == BuildStatusEnum.Unknown
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_cache_load_json_error(watcher: Watcher, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must not fail on json errors
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("pathlib.Path.is_file", return_value=True)
 | 
			
		||||
    mocker.patch("pathlib.Path.open")
 | 
			
		||||
    mocker.patch("json.load", side_effect=Exception())
 | 
			
		||||
 | 
			
		||||
    watcher._cache_load()
 | 
			
		||||
    assert not watcher.known
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_cache_load_no_file(watcher: Watcher, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must not fail on missing file
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("pathlib.Path.is_file", return_value=False)
 | 
			
		||||
 | 
			
		||||
    watcher._cache_load()
 | 
			
		||||
    assert not watcher.known
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_cache_load_unknown(watcher: Watcher, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must not load unknown package
 | 
			
		||||
    """
 | 
			
		||||
    response = {"packages": [pytest.helpers.get_package_status_extended(package_ahriman)]}
 | 
			
		||||
 | 
			
		||||
    mocker.patch("pathlib.Path.is_file", return_value=True)
 | 
			
		||||
    mocker.patch("pathlib.Path.open")
 | 
			
		||||
    mocker.patch("json.load", return_value=response)
 | 
			
		||||
 | 
			
		||||
    watcher._cache_load()
 | 
			
		||||
    assert not watcher.known
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_cache_save(watcher: Watcher, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must save state to cache
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("pathlib.Path.open")
 | 
			
		||||
    json_mock = mocker.patch("json.dump")
 | 
			
		||||
 | 
			
		||||
    watcher.known = {package_ahriman.base: (package_ahriman, BuildStatus())}
 | 
			
		||||
    watcher._cache_save()
 | 
			
		||||
    json_mock.assert_called_once()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_cache_save_failed(watcher: Watcher, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must not fail on dumping packages
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("pathlib.Path.open")
 | 
			
		||||
    mocker.patch("json.dump", side_effect=Exception())
 | 
			
		||||
 | 
			
		||||
    watcher._cache_save()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_cache_save_load(watcher: Watcher, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must save state to cache which can be loaded later
 | 
			
		||||
    """
 | 
			
		||||
    dump_file = Path(tempfile.mktemp())
 | 
			
		||||
    mocker.patch("ahriman.core.status.watcher.Watcher.cache_path",
 | 
			
		||||
                 new_callable=PropertyMock, return_value=dump_file)
 | 
			
		||||
    known_current = {package_ahriman.base: (package_ahriman, BuildStatus())}
 | 
			
		||||
 | 
			
		||||
    watcher.known = known_current
 | 
			
		||||
    watcher._cache_save()
 | 
			
		||||
 | 
			
		||||
    watcher.known = {package_ahriman.base: (None, None)}
 | 
			
		||||
    watcher._cache_load()
 | 
			
		||||
    assert watcher.known == known_current
 | 
			
		||||
 | 
			
		||||
    dump_file.unlink()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_get(watcher: Watcher, package_ahriman: Package) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must return package status
 | 
			
		||||
    """
 | 
			
		||||
    watcher.known = {package_ahriman.base: (package_ahriman, BuildStatus())}
 | 
			
		||||
    package, status = watcher.get(package_ahriman.base)
 | 
			
		||||
    assert package == package_ahriman
 | 
			
		||||
    assert status.status == BuildStatusEnum.Unknown
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_get_failed(watcher: Watcher, package_ahriman: Package) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must fail on unknown package
 | 
			
		||||
    """
 | 
			
		||||
    with pytest.raises(UnknownPackage):
 | 
			
		||||
        watcher.get(package_ahriman.base)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_load(watcher: Watcher, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must correctly load packages
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("ahriman.core.repository.repository.Repository.packages", return_value=[package_ahriman])
 | 
			
		||||
    cache_mock = mocker.patch("ahriman.core.status.watcher.Watcher._cache_load")
 | 
			
		||||
 | 
			
		||||
    watcher.load()
 | 
			
		||||
    cache_mock.assert_called_once()
 | 
			
		||||
    package, status = watcher.known[package_ahriman.base]
 | 
			
		||||
    assert package == package_ahriman
 | 
			
		||||
    assert status.status == BuildStatusEnum.Unknown
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_load_known(watcher: Watcher, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must correctly load packages with known statuses
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("ahriman.core.repository.repository.Repository.packages", return_value=[package_ahriman])
 | 
			
		||||
    mocker.patch("ahriman.core.status.watcher.Watcher._cache_load")
 | 
			
		||||
    watcher.known = {package_ahriman.base: (package_ahriman, BuildStatus(BuildStatusEnum.Success))}
 | 
			
		||||
 | 
			
		||||
    watcher.load()
 | 
			
		||||
    _, status = watcher.known[package_ahriman.base]
 | 
			
		||||
    assert status.status == BuildStatusEnum.Success
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_remove(watcher: Watcher, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must remove package base
 | 
			
		||||
    """
 | 
			
		||||
    cache_mock = mocker.patch("ahriman.core.status.watcher.Watcher._cache_save")
 | 
			
		||||
    watcher.known = {package_ahriman.base: (package_ahriman, BuildStatus())}
 | 
			
		||||
 | 
			
		||||
    watcher.remove(package_ahriman.base)
 | 
			
		||||
    assert not watcher.known
 | 
			
		||||
    cache_mock.assert_called_once()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_remove_unknown(watcher: Watcher, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must not fail on unknown base removal
 | 
			
		||||
    """
 | 
			
		||||
    cache_mock = mocker.patch("ahriman.core.status.watcher.Watcher._cache_save")
 | 
			
		||||
 | 
			
		||||
    watcher.remove(package_ahriman.base)
 | 
			
		||||
    cache_mock.assert_called_once()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_update(watcher: Watcher, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must update package status
 | 
			
		||||
    """
 | 
			
		||||
    cache_mock = mocker.patch("ahriman.core.status.watcher.Watcher._cache_save")
 | 
			
		||||
 | 
			
		||||
    watcher.update(package_ahriman.base, BuildStatusEnum.Unknown, package_ahriman)
 | 
			
		||||
    cache_mock.assert_called_once()
 | 
			
		||||
    package, status = watcher.known[package_ahriman.base]
 | 
			
		||||
    assert package == package_ahriman
 | 
			
		||||
    assert status.status == BuildStatusEnum.Unknown
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_update_ping(watcher: Watcher, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must update package status only for known package
 | 
			
		||||
    """
 | 
			
		||||
    cache_mock = mocker.patch("ahriman.core.status.watcher.Watcher._cache_save")
 | 
			
		||||
    watcher.known = {package_ahriman.base: (package_ahriman, BuildStatus())}
 | 
			
		||||
 | 
			
		||||
    watcher.update(package_ahriman.base, BuildStatusEnum.Success, None)
 | 
			
		||||
    cache_mock.assert_called_once()
 | 
			
		||||
    package, status = watcher.known[package_ahriman.base]
 | 
			
		||||
    assert package == package_ahriman
 | 
			
		||||
    assert status.status == BuildStatusEnum.Success
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_update_unknown(watcher: Watcher, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must fail on unknown package status update only
 | 
			
		||||
    """
 | 
			
		||||
    cache_mock = mocker.patch("ahriman.core.status.watcher.Watcher._cache_save")
 | 
			
		||||
 | 
			
		||||
    with pytest.raises(UnknownPackage):
 | 
			
		||||
        watcher.update(package_ahriman.base, BuildStatusEnum.Unknown, None)
 | 
			
		||||
        cache_mock.assert_called_once()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_update_self(watcher: Watcher) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must update service status
 | 
			
		||||
    """
 | 
			
		||||
    watcher.update_self(BuildStatusEnum.Success)
 | 
			
		||||
    assert watcher.status.status == BuildStatusEnum.Success
 | 
			
		||||
							
								
								
									
										163
									
								
								tests/ahriman/core/status/test_web_client.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										163
									
								
								tests/ahriman/core/status/test_web_client.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,163 @@
 | 
			
		||||
import json
 | 
			
		||||
import pytest
 | 
			
		||||
 | 
			
		||||
from pytest_mock import MockerFixture
 | 
			
		||||
from requests import Response
 | 
			
		||||
 | 
			
		||||
from ahriman.core.status.web_client import WebClient
 | 
			
		||||
from ahriman.models.build_status import BuildStatus, BuildStatusEnum
 | 
			
		||||
from ahriman.models.package import Package
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_ahriman_url(web_client: WebClient) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must generate service status url correctly
 | 
			
		||||
    """
 | 
			
		||||
    assert web_client._ahriman_url().startswith(f"http://{web_client.host}:{web_client.port}")
 | 
			
		||||
    assert web_client._ahriman_url().endswith("/api/v1/ahriman")
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_package_url(web_client: WebClient, package_ahriman: Package) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must generate package status correctly
 | 
			
		||||
    """
 | 
			
		||||
    assert web_client._package_url(package_ahriman.base).startswith(f"http://{web_client.host}:{web_client.port}")
 | 
			
		||||
    assert web_client._package_url(package_ahriman.base).endswith(f"/api/v1/packages/{package_ahriman.base}")
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_add(web_client: WebClient, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must process package addition
 | 
			
		||||
    """
 | 
			
		||||
    requests_mock = mocker.patch("requests.post")
 | 
			
		||||
    payload = pytest.helpers.get_package_status(package_ahriman)
 | 
			
		||||
 | 
			
		||||
    web_client.add(package_ahriman, BuildStatusEnum.Unknown)
 | 
			
		||||
    requests_mock.assert_called_with(pytest.helpers.anyvar(str, True), json=payload)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_add_failed(web_client: WebClient, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must suppress any exception happened during addition
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("requests.post", side_effect=Exception())
 | 
			
		||||
    web_client.add(package_ahriman, BuildStatusEnum.Unknown)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_get_all(web_client: WebClient, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must return all packages status
 | 
			
		||||
    """
 | 
			
		||||
    response = [pytest.helpers.get_package_status_extended(package_ahriman)]
 | 
			
		||||
    response_obj = Response()
 | 
			
		||||
    response_obj._content = json.dumps(response).encode("utf8")
 | 
			
		||||
    response_obj.status_code = 200
 | 
			
		||||
 | 
			
		||||
    requests_mock = mocker.patch("requests.get", return_value=response_obj)
 | 
			
		||||
 | 
			
		||||
    result = web_client.get(None)
 | 
			
		||||
    requests_mock.assert_called_once()
 | 
			
		||||
    assert len(result) == len(response)
 | 
			
		||||
    assert (package_ahriman, BuildStatusEnum.Unknown) in [(package, status.status) for package, status in result]
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_get_failed(web_client: WebClient, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must suppress any exception happened during status getting
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("requests.get", side_effect=Exception())
 | 
			
		||||
    assert web_client.get(None) == []
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_get_single(web_client: WebClient, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must return single package status
 | 
			
		||||
    """
 | 
			
		||||
    response = [pytest.helpers.get_package_status_extended(package_ahriman)]
 | 
			
		||||
    response_obj = Response()
 | 
			
		||||
    response_obj._content = json.dumps(response).encode("utf8")
 | 
			
		||||
    response_obj.status_code = 200
 | 
			
		||||
 | 
			
		||||
    requests_mock = mocker.patch("requests.get", return_value=response_obj)
 | 
			
		||||
 | 
			
		||||
    result = web_client.get(package_ahriman.base)
 | 
			
		||||
    requests_mock.assert_called_once()
 | 
			
		||||
    assert len(result) == len(response)
 | 
			
		||||
    assert (package_ahriman, BuildStatusEnum.Unknown) in [(package, status.status) for package, status in result]
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_get_self(web_client: WebClient, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must return service status
 | 
			
		||||
    """
 | 
			
		||||
    response_obj = Response()
 | 
			
		||||
    response_obj._content = json.dumps(BuildStatus().view()).encode("utf8")
 | 
			
		||||
    response_obj.status_code = 200
 | 
			
		||||
 | 
			
		||||
    requests_mock = mocker.patch("requests.get", return_value=response_obj)
 | 
			
		||||
 | 
			
		||||
    result = web_client.get_self()
 | 
			
		||||
    requests_mock.assert_called_once()
 | 
			
		||||
    assert result.status == BuildStatusEnum.Unknown
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_get_self_failed(web_client: WebClient, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must suppress any exception happened during service status getting
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("requests.get", side_effect=Exception())
 | 
			
		||||
    assert web_client.get_self().status == BuildStatusEnum.Unknown
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_remove(web_client: WebClient, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must process package removal
 | 
			
		||||
    """
 | 
			
		||||
    requests_mock = mocker.patch("requests.delete")
 | 
			
		||||
 | 
			
		||||
    web_client.remove(package_ahriman.base)
 | 
			
		||||
    requests_mock.assert_called_with(pytest.helpers.anyvar(str, True))
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_remove_failed(web_client: WebClient, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must suppress any exception happened during removal
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("requests.delete", side_effect=Exception())
 | 
			
		||||
    web_client.remove(package_ahriman.base)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_update(web_client: WebClient, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must process package update
 | 
			
		||||
    """
 | 
			
		||||
    requests_mock = mocker.patch("requests.post")
 | 
			
		||||
 | 
			
		||||
    web_client.update(package_ahriman.base, BuildStatusEnum.Unknown)
 | 
			
		||||
    requests_mock.assert_called_with(pytest.helpers.anyvar(str, True), json={"status": BuildStatusEnum.Unknown.value})
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_update_failed(web_client: WebClient, package_ahriman: Package, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must suppress any exception happened during update
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("requests.post", side_effect=Exception())
 | 
			
		||||
    web_client.update(package_ahriman.base, BuildStatusEnum.Unknown)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_update_self(web_client: WebClient, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must process service update
 | 
			
		||||
    """
 | 
			
		||||
    requests_mock = mocker.patch("requests.post")
 | 
			
		||||
 | 
			
		||||
    web_client.update_self(BuildStatusEnum.Unknown)
 | 
			
		||||
    requests_mock.assert_called_with(pytest.helpers.anyvar(str, True), json={"status": BuildStatusEnum.Unknown.value})
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def test_update_self_failed(web_client: WebClient, mocker: MockerFixture) -> None:
 | 
			
		||||
    """
 | 
			
		||||
    must suppress any exception happened during service update
 | 
			
		||||
    """
 | 
			
		||||
    mocker.patch("requests.post", side_effect=Exception())
 | 
			
		||||
    web_client.update_self(BuildStatusEnum.Unknown)
 | 
			
		||||
		Reference in New Issue
	
	Block a user