diff --git a/src/hqt/cli.py b/src/hqt/cli.py index 7069f7f..e43cef5 100644 --- a/src/hqt/cli.py +++ b/src/hqt/cli.py @@ -1,5 +1,6 @@ import logging import os +import shutil import subprocess import sys import traceback @@ -105,7 +106,6 @@ def launch(inside_tmux: bool = False): @main.command() def doctor(): """Check system requirements.""" - import shutil from hqt.harnesses.registry import discover_harnesses tmux = shutil.which("tmux") @@ -119,6 +119,11 @@ def doctor(): click.echo(f"{name}: ✓") if not harnesses: click.echo("No harnesses found on PATH") + bwrap = shutil.which("bwrap") + if bwrap: + click.echo(f"bubblewrap: ✓ {bwrap}") + else: + click.echo("bubblewrap: ✗ not found — sandboxed sessions unavailable") @main.command(name="list") diff --git a/tests/test_cli.py b/tests/test_cli.py new file mode 100644 index 0000000..3be3570 --- /dev/null +++ b/tests/test_cli.py @@ -0,0 +1,30 @@ +from unittest.mock import patch + +from click.testing import CliRunner + +from hqt import cli as cli_module +from hqt.cli import main + + +def _which(found: set[str]): + return lambda name: f"/usr/bin/{name}" if name in found else None + + +def test_doctor_reports_bwrap_present(): + """Test that doctor reports bubblewrap when present.""" + # Patch the single shutil.which used by both cli and registry + with patch.object( + cli_module.shutil, "which", side_effect=_which({"tmux", "bwrap"}) + ): + result = CliRunner().invoke(main, ["doctor"]) + assert result.exit_code == 0 + assert "bubblewrap: ✓" in result.output + + +def test_doctor_reports_bwrap_missing(): + """Test that doctor reports bubblewrap as missing when not present.""" + # Patch the single shutil.which used by both cli and registry + with patch.object(cli_module.shutil, "which", side_effect=_which({"tmux"})): + result = CliRunner().invoke(main, ["doctor"]) + assert result.exit_code == 0 + assert "bubblewrap: ✗" in result.output