claire/tests/test_cli_smoke.py

51 lines
1.8 KiB
Python
Raw Permalink Normal View History

"""CLI smoke tests.
Most CLI behavior is now indirectly covered by test_api.py (the CLI is a
thin httpx wrapper over the JSON API). These tests verify the local-only
verbs (`init`) and the "server unreachable" error path.
"""
from __future__ import annotations
from pathlib import Path
import pytest
from typer.testing import CliRunner
from claire.cli import app
def test_init_creates_config_and_db(tmp_path: Path, monkeypatch: pytest.MonkeyPatch) -> None:
monkeypatch.setenv("XDG_DATA_HOME", str(tmp_path / "data"))
monkeypatch.setenv("XDG_CONFIG_HOME", str(tmp_path / "config"))
runner = CliRunner()
result = runner.invoke(app, ["init"])
assert result.exit_code == 0, result.output
assert "machine_id" in result.output
assert (tmp_path / "config" / "claire" / "claire.toml").exists()
assert (tmp_path / "data" / "claire" / "claire.db").exists()
def test_cli_emits_helpful_error_when_server_down(
tmp_path: Path, monkeypatch: pytest.MonkeyPatch
) -> None:
"""`claire project list` should exit 3 with a clear message when the server
isn't running. We point at a definitely-dead port to force ConnectError."""
monkeypatch.setenv("XDG_DATA_HOME", str(tmp_path / "data"))
monkeypatch.setenv("XDG_CONFIG_HOME", str(tmp_path / "config"))
# Init creates the config so we can mutate it.
runner = CliRunner()
runner.invoke(app, ["init"])
# Point the CLI at a dead port.
cfg_path = tmp_path / "config" / "claire" / "claire.toml"
content = cfg_path.read_text()
content = content.replace("port = 8765", "port = 1")
cfg_path.write_text(content)
result = runner.invoke(app, ["project", "list"])
assert result.exit_code == 3
assert "could not reach claire server" in result.output
assert "claire serve" in result.output