hermes-agent/tests/skills/test_google_workspace_setup.py

93 lines
3.1 KiB
Python

"""The Google Workspace setup script must not install packages itself.
The Google SDKs ship in the [google] extra, which [all] contains, so each
supported install path already has them. A stripped environment is a broken
install, and the repair is `hermes update`, not a pip run from inside a
skill script that writes to whatever interpreter it happens to be under.
These tests hold that line: the script reports the repair, and it exits
rather than continuing into an API call that would fail with an import
error further down.
"""
from __future__ import annotations
import builtins
import importlib.util
from pathlib import Path
import pytest
SETUP_PATH = (
Path(__file__).resolve().parents[2]
/ "skills/productivity/google-workspace/scripts/setup.py"
)
@pytest.fixture()
def setup_module():
spec = importlib.util.spec_from_file_location(
"test_google_workspace_setup_module",
SETUP_PATH,
)
assert spec is not None and spec.loader is not None
module = importlib.util.module_from_spec(spec)
spec.loader.exec_module(module)
return module
def _break_google_imports(monkeypatch, setup_module) -> None:
"""Make the three Google SDK imports fail, and leave the rest alone."""
real_import = builtins.__import__
broken = {"googleapiclient", "google.auth", "google_auth_oauthlib"}
def fake_import(name, *args, **kwargs):
if name in broken:
raise ImportError(f"No module named {name!r}")
return real_import(name, *args, **kwargs)
monkeypatch.setattr(builtins, "__import__", fake_import)
def test_missing_sdks_stop_the_script(setup_module, monkeypatch, capsys):
"""Exit rather than run on into an API call that cannot work."""
_break_google_imports(monkeypatch, setup_module)
with pytest.raises(SystemExit) as exc:
setup_module._require_google_libs()
assert exc.value.code == 1
def test_the_message_names_the_repair(setup_module, monkeypatch, capsys):
"""A user needs the command that fixes this, not the import error.
The packages come from an extra, so the fix is to repair the install.
A pip command here would write to whichever interpreter the script runs
under, which is not always the one Hermes uses.
"""
_break_google_imports(monkeypatch, setup_module)
with pytest.raises(SystemExit):
setup_module._require_google_libs()
err = capsys.readouterr().err
assert "hermes update" in err
assert "uv sync --extra all" in err
assert "[google]" in err
def test_present_sdks_are_not_an_error(setup_module):
"""The venv running the tests has the [google] extra, so this passes."""
pytest.importorskip("googleapiclient")
pytest.importorskip("google.auth")
pytest.importorskip("google_auth_oauthlib")
setup_module._require_google_libs()
def test_the_script_installs_nothing(setup_module):
"""No install path may reappear here.
An earlier version pip-installed a hardcoded list of pins, which is a
second copy of what the [google] extra already declares.
"""
assert not hasattr(setup_module, "install_deps")
assert not hasattr(setup_module, "_missing_required_packages")