1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154
|
from unittest.mock import MagicMock
import pytest
from briefcase.exceptions import (
MissingToolError,
NonManagedToolError,
UnsupportedHostError,
)
from briefcase.integrations.base import ManagedTool
class DummyManagedTool(ManagedTool):
"""Managed Tool testing class."""
name = "ManagedDummyTool"
full_name = "Managed Dummy Tool"
supported_host_os = {"wonky"}
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.actions = []
@classmethod
def verify_install(cls, tools, **kwargs):
return f"i'm a {cls.name}"
def exists(self) -> bool:
self.actions.append("exists")
return True
def install(self):
self.actions.append("install")
def uninstall(self):
self.actions.append("uninstall")
class NonExistsManagedTool(DummyManagedTool):
def exists(self) -> bool:
return False
class NonManagedManagedTool(DummyManagedTool):
@property
def managed_install(self) -> bool:
return False
@pytest.fixture
def managed_tool(mock_tools) -> DummyManagedTool:
return DummyManagedTool(tools=mock_tools)
@pytest.fixture
def nonexistent_managed_tool(mock_tools) -> NonExistsManagedTool:
return NonExistsManagedTool(tools=mock_tools)
@pytest.fixture
def nonmanaged_managed_tool(mock_tools) -> NonManagedManagedTool:
return NonManagedManagedTool(tools=mock_tools)
@pytest.mark.parametrize(
"klass, kwargs",
[
(DummyManagedTool, {}),
(DummyManagedTool, {"one": "two", "three": "four"}),
],
)
def test_tool_verify(mock_tools, klass, kwargs, monkeypatch):
"""Tool verification checks host OS and tool install."""
# Wrap verify calls to confirm they were called
mock_verify_host = MagicMock(wraps=klass.verify_host)
monkeypatch.setattr(klass, "verify_host", mock_verify_host)
mock_verify_install = MagicMock(wraps=klass.verify_install)
monkeypatch.setattr(klass, "verify_install", mock_verify_install)
# Mock the dummy tool's supported OS
mock_tools.host_os = "wonky"
tool = klass.verify(tools=mock_tools, **kwargs)
mock_verify_host.assert_called_once_with(tools=mock_tools)
mock_verify_install.assert_called_once_with(
tools=mock_tools, app=None, install=True, **kwargs
)
assert tool == f"i'm a {klass.name}"
@pytest.mark.parametrize(
"klass, kwargs",
[
(DummyManagedTool, {}),
(DummyManagedTool, {"one": "two", "three": "four"}),
],
)
def test_tool_verify_with_app(mock_tools, first_app_config, klass, kwargs, monkeypatch):
"""App-bound Tool verification checks host OS and tool install."""
# Wrap verify calls to confirm they were called
mock_verify_host = MagicMock(wraps=klass.verify_host)
monkeypatch.setattr(klass, "verify_host", mock_verify_host)
mock_verify_install = MagicMock(wraps=klass.verify_install)
monkeypatch.setattr(klass, "verify_install", mock_verify_install)
# Mock the dummy tool's supported OS
mock_tools.host_os = "wonky"
tool = klass.verify(tools=mock_tools, app=first_app_config, **kwargs)
mock_verify_host.assert_called_once_with(tools=mock_tools)
mock_verify_install.assert_called_once_with(
tools=mock_tools,
app=first_app_config,
install=True,
**kwargs,
)
assert tool == "i'm a ManagedDummyTool"
def test_tool_unsupported_host_os(mock_tools):
"""Tool verification fails for unsupported Host OS."""
mock_tools.host_os = "not wonky"
with pytest.raises(
UnsupportedHostError,
match="ManagedDummyTool is not supported on not wonky",
):
DummyManagedTool.verify(tools=mock_tools)
def test_managed_install_is_true(managed_tool):
"""Tool.managed_install defaults False."""
assert managed_tool.managed_install is True
def test_managed_upgrade(managed_tool):
"""Order of operations is correct for upgrade."""
managed_tool.upgrade()
assert managed_tool.actions == ["exists", "uninstall", "install"]
def test_managed_raises_if_unmanaged(mock_tools, nonmanaged_managed_tool):
"""If a ManagedTool is unmanaged, upgrade raises."""
with pytest.raises(NonManagedToolError):
nonmanaged_managed_tool.upgrade()
def test_managed_raises_if_not_exists(mock_tools, nonexistent_managed_tool):
"""If a ManagedTool doesn't exist, upgrade raises."""
with pytest.raises(MissingToolError):
nonexistent_managed_tool.upgrade()
|