import json import os import subprocess import sys from pathlib import Path SCRIPT = Path(__file__).parents[1] / "rulesets-write-boundary.py" def run_hook(payload: dict, rulesets: Path) -> dict | None: proc = subprocess.run( [sys.executable, str(SCRIPT)], input=json.dumps(payload), text=True, capture_output=True, env={**os.environ, "RULESETS_ROOT": str(rulesets)}, check=True, ) return json.loads(proc.stdout) if proc.stdout else None def test_allows_write_from_rulesets_session(tmp_path): rulesets = tmp_path / "rulesets" rulesets.mkdir() target = rulesets / "file" result = run_hook( { "cwd": str(rulesets), "tool_name": "Write", "tool_input": {"file_path": str(target)}, }, rulesets, ) assert result is None def test_blocks_absolute_cross_project_write(tmp_path): rulesets = tmp_path / "rulesets" other = tmp_path / "other" rulesets.mkdir() other.mkdir() result = run_hook( { "cwd": str(other), "tool_name": "Edit", "tool_input": {"file_path": str(rulesets / "rule.md")}, }, rulesets, ) assert result["hookSpecificOutput"]["permissionDecision"] == "deny" assert "inbox-send rulesets" in result["hookSpecificOutput"][ "permissionDecisionReason" ] def test_blocks_write_reached_through_symlink(tmp_path): rulesets = tmp_path / "rulesets" other = tmp_path / "other" installed = tmp_path / "installed" rulesets.mkdir() other.mkdir() (rulesets / "rules").mkdir() installed.symlink_to(rulesets / "rules", target_is_directory=True) result = run_hook( { "cwd": str(other), "tool_name": "Write", "tool_input": {"file_path": str(installed / "todo-format.md")}, }, rulesets, ) assert result["hookSpecificOutput"]["permissionDecision"] == "deny" assert str(rulesets) in result["systemMessage"] def test_blocks_apply_patch_target(tmp_path): rulesets = tmp_path / "rulesets" other = tmp_path / "other" rulesets.mkdir() other.mkdir() patch = ( f"*** Begin Patch\n*** Update File: {rulesets / 'file'}\n" "@@\n-old\n+new\n*** End Patch\n" ) result = run_hook( { "cwd": str(other), "tool_name": "apply_patch", "tool_input": {"input": patch}, }, rulesets, ) assert result["hookSpecificOutput"]["permissionDecision"] == "deny" def test_allows_unrelated_write(tmp_path): rulesets = tmp_path / "rulesets" other = tmp_path / "other" rulesets.mkdir() other.mkdir() result = run_hook( { "cwd": str(other), "tool_name": "Edit", "tool_input": {"file_path": str(other / "file")}, }, rulesets, ) assert result is None