diff --git a/gateway/platforms/homeassistant.py b/gateway/platforms/homeassistant.py index 746465594..0abebe42a 100644 --- a/gateway/platforms/homeassistant.py +++ b/gateway/platforms/homeassistant.py @@ -39,10 +39,12 @@ from gateway.platforms.base import ( logger = logging.getLogger(__name__) -def check_ha_requirements() -> bool: +def check_ha_requirements(config: Optional[PlatformConfig] = None) -> bool: """Check if Home Assistant dependencies are available and configured.""" if not AIOHTTP_AVAILABLE: return False + if config is not None and config.token: + return True if not os.getenv("HASS_TOKEN"): return False return True diff --git a/gateway/platforms/mattermost.py b/gateway/platforms/mattermost.py index 0e6c9631d..086305115 100644 --- a/gateway/platforms/mattermost.py +++ b/gateway/platforms/mattermost.py @@ -50,10 +50,11 @@ _RECONNECT_MAX_DELAY = 60.0 _RECONNECT_JITTER = 0.2 -def check_mattermost_requirements() -> bool: +def check_mattermost_requirements(config: Optional[PlatformConfig] = None) -> bool: """Return True if the Mattermost adapter can be used.""" - token = os.getenv("MATTERMOST_TOKEN", "") - url = os.getenv("MATTERMOST_URL", "") + extra = getattr(config, "extra", {}) or {} + token = getattr(config, "token", None) or os.getenv("MATTERMOST_TOKEN", "") + url = extra.get("url", "") or os.getenv("MATTERMOST_URL", "") if not token: logger.debug("Mattermost: MATTERMOST_TOKEN not set") return False @@ -736,4 +737,3 @@ class MattermostAdapter(BasePlatformAdapter): await self.handle_message(msg_event) - diff --git a/gateway/platforms/signal.py b/gateway/platforms/signal.py index 9a0a6256a..4c141f994 100644 --- a/gateway/platforms/signal.py +++ b/gateway/platforms/signal.py @@ -149,9 +149,12 @@ def _looks_like_e164_number(value: str) -> bool: return digits.isdigit() and 7 <= len(digits) <= 15 -def check_signal_requirements() -> bool: +def check_signal_requirements(config: Optional[PlatformConfig] = None) -> bool: """Check if Signal is configured (has URL and account).""" - return bool(os.getenv("SIGNAL_HTTP_URL") and os.getenv("SIGNAL_ACCOUNT")) + extra = getattr(config, "extra", {}) or {} + http_url = extra.get("http_url") or os.getenv("SIGNAL_HTTP_URL") + account = extra.get("account") or os.getenv("SIGNAL_ACCOUNT") + return bool(http_url and account) # --------------------------------------------------------------------------- diff --git a/gateway/run.py b/gateway/run.py index 14bd3ff0d..d07c2a294 100644 --- a/gateway/run.py +++ b/gateway/run.py @@ -2851,14 +2851,14 @@ class GatewayRunner: elif platform == Platform.SIGNAL: from gateway.platforms.signal import SignalAdapter, check_signal_requirements - if not check_signal_requirements(): + if not check_signal_requirements(config): logger.warning("Signal: SIGNAL_HTTP_URL or SIGNAL_ACCOUNT not configured") return None return SignalAdapter(config) elif platform == Platform.HOMEASSISTANT: from gateway.platforms.homeassistant import HomeAssistantAdapter, check_ha_requirements - if not check_ha_requirements(): + if not check_ha_requirements(config): logger.warning("HomeAssistant: aiohttp not installed or HASS_TOKEN not set") return None return HomeAssistantAdapter(config) @@ -2917,7 +2917,7 @@ class GatewayRunner: elif platform == Platform.MATTERMOST: from gateway.platforms.mattermost import MattermostAdapter, check_mattermost_requirements - if not check_mattermost_requirements(): + if not check_mattermost_requirements(config): logger.warning("Mattermost: MATTERMOST_TOKEN or MATTERMOST_URL not set, or aiohttp missing") return None return MattermostAdapter(config) diff --git a/tests/gateway/test_runner_config_backed_adapters.py b/tests/gateway/test_runner_config_backed_adapters.py new file mode 100644 index 000000000..5a15e717b --- /dev/null +++ b/tests/gateway/test_runner_config_backed_adapters.py @@ -0,0 +1,86 @@ +from gateway.config import GatewayConfig, Platform, PlatformConfig +from gateway.platforms.homeassistant import HomeAssistantAdapter, check_ha_requirements +from gateway.platforms.mattermost import MattermostAdapter, check_mattermost_requirements +from gateway.platforms.signal import SignalAdapter, check_signal_requirements +from gateway.run import GatewayRunner + + +def _clear_gateway_env(monkeypatch) -> None: + for key in ( + "HASS_TOKEN", + "HASS_URL", + "MATTERMOST_TOKEN", + "MATTERMOST_URL", + "SIGNAL_HTTP_URL", + "SIGNAL_ACCOUNT", + ): + monkeypatch.delenv(key, raising=False) + + +def test_homeassistant_requirements_accept_platform_config(monkeypatch): + _clear_gateway_env(monkeypatch) + + config = PlatformConfig(enabled=True, token="tok", extra={"url": "http://ha.local"}) + + assert check_ha_requirements(config) is True + + +def test_mattermost_requirements_accept_platform_config(monkeypatch): + _clear_gateway_env(monkeypatch) + + config = PlatformConfig(enabled=True, token="tok", extra={"url": "https://mm.example.com"}) + + assert check_mattermost_requirements(config) is True + + +def test_signal_requirements_accept_platform_config(monkeypatch): + _clear_gateway_env(monkeypatch) + + config = PlatformConfig( + enabled=True, + extra={"http_url": "http://127.0.0.1:8080", "account": "+15551234567"}, + ) + + assert check_signal_requirements(config) is True + + +def test_runner_creates_config_backed_homeassistant_adapter_without_env(monkeypatch): + _clear_gateway_env(monkeypatch) + + runner = GatewayRunner(GatewayConfig()) + config = PlatformConfig(enabled=True, token="tok", extra={"url": "http://ha.local"}) + + adapter = runner._create_adapter(Platform.HOMEASSISTANT, config) + + assert isinstance(adapter, HomeAssistantAdapter) + assert adapter._hass_token == "tok" + assert adapter._hass_url == "http://ha.local" + + +def test_runner_creates_config_backed_mattermost_adapter_without_env(monkeypatch): + _clear_gateway_env(monkeypatch) + + runner = GatewayRunner(GatewayConfig()) + config = PlatformConfig(enabled=True, token="tok", extra={"url": "https://mm.example.com"}) + + adapter = runner._create_adapter(Platform.MATTERMOST, config) + + assert isinstance(adapter, MattermostAdapter) + assert adapter._token == "tok" + assert adapter._base_url == "https://mm.example.com" + + +def test_runner_creates_config_backed_signal_adapter_without_env(monkeypatch): + _clear_gateway_env(monkeypatch) + + runner = GatewayRunner(GatewayConfig()) + config = PlatformConfig( + enabled=True, + extra={"http_url": "http://127.0.0.1:8080", "account": "+15551234567"}, + ) + + adapter = runner._create_adapter(Platform.SIGNAL, config) + + assert isinstance(adapter, SignalAdapter) + assert adapter.http_url == "http://127.0.0.1:8080" + assert adapter.account == "+15551234567"