Require session-owned review worktrees or documented safe-reuse proof before destructive reset/validation. Block contradictory workspace-none claims when git reset --hard occurred. Co-Authored-By: Claude Opus 4.8 (1M context) <[email protected]>
137 lines
5.1 KiB
Python
137 lines
5.1 KiB
Python
"""Tests for reviewer worktree ownership verifier (#312)."""
|
|
import sys
|
|
import unittest
|
|
from pathlib import Path
|
|
|
|
sys.path.insert(0, str(Path(__file__).resolve().parent.parent))
|
|
|
|
from reviewer_worktree_ownership import assess_worktree_ownership_report # noqa: E402
|
|
|
|
|
|
def _fresh_review_report() -> str:
|
|
return "\n".join([
|
|
"Review worktree path: branches/review-pr280-feat-issue-275-claim",
|
|
"Worktree is inside branches/ and not the main checkout.",
|
|
"Tracked state: clean; untracked state: clean.",
|
|
"Official PR-head validation on session-owned worktree.",
|
|
"Worktree mutations: none",
|
|
])
|
|
|
|
|
|
def _safe_reuse_report() -> str:
|
|
return "\n".join([
|
|
"Safe-reuse proof for existing review worktree.",
|
|
"Review worktree path: branches/docs-issue-260-forbid-commit-fallbacks",
|
|
"Worktree inside branches/; not the main checkout.",
|
|
"Not owned by another active task/session.",
|
|
"Clean tracked state; clean untracked state.",
|
|
"Branch/head before reset: feat/issue-260-example",
|
|
"Reset target SHA: abc123def4567890abcdef1234567890abcdef12",
|
|
"Project policy allows reuse/reset for this clean review worktree.",
|
|
"Worktree mutations: git reset --hard FETCH_HEAD",
|
|
"Destructive reset operations: git reset --hard FETCH_HEAD",
|
|
])
|
|
|
|
|
|
class TestWorktreeOwnership(unittest.TestCase):
|
|
def test_fresh_session_owned_passes(self):
|
|
result = assess_worktree_ownership_report(
|
|
_fresh_review_report(),
|
|
ownership_session={
|
|
"validation_ran": True,
|
|
"worktree_path": "branches/review-pr280-feat-issue-275-claim",
|
|
},
|
|
)
|
|
self.assertTrue(result["proven"], result["reasons"])
|
|
self.assertTrue(result["session_owned"])
|
|
|
|
def test_safe_reuse_with_reset_passes(self):
|
|
result = assess_worktree_ownership_report(
|
|
_safe_reuse_report(),
|
|
ownership_session={
|
|
"safe_reuse": True,
|
|
"worktree_path": "branches/docs-issue-260-forbid-commit-fallbacks",
|
|
},
|
|
command_log=["git reset --hard FETCH_HEAD"],
|
|
)
|
|
self.assertTrue(result["proven"], result["reasons"])
|
|
|
|
def test_destructive_reset_without_proof_blocks(self):
|
|
report = "\n".join([
|
|
"Review worktree path: branches/docs-issue-260-forbid-commit-fallbacks",
|
|
"Worktree mutations: git reset --hard FETCH_HEAD",
|
|
])
|
|
result = assess_worktree_ownership_report(
|
|
report,
|
|
ownership_session={
|
|
"validation_ran": True,
|
|
"worktree_path": "branches/docs-issue-260-forbid-commit-fallbacks",
|
|
},
|
|
command_log=["git reset --hard FETCH_HEAD"],
|
|
)
|
|
self.assertFalse(result["proven"])
|
|
self.assertTrue(result["block"])
|
|
|
|
def test_reused_dirty_tracked_blocks(self):
|
|
result = assess_worktree_ownership_report(
|
|
_fresh_review_report(),
|
|
ownership_session={
|
|
"validation_ran": True,
|
|
"worktree_path": "branches/review-pr280-feat-issue-275-claim",
|
|
"dirty_tracked": True,
|
|
},
|
|
)
|
|
self.assertFalse(result["proven"])
|
|
self.assertTrue(any("tracked" in r.lower() for r in result["reasons"]))
|
|
|
|
def test_safe_reuse_dirty_untracked_blocks(self):
|
|
result = assess_worktree_ownership_report(
|
|
_safe_reuse_report(),
|
|
ownership_session={
|
|
"safe_reuse": True,
|
|
"dirty_untracked": True,
|
|
"worktree_path": "branches/docs-issue-260-forbid-commit-fallbacks",
|
|
},
|
|
command_log=["git reset --hard FETCH_HEAD"],
|
|
)
|
|
self.assertFalse(result["proven"])
|
|
self.assertTrue(any("untracked" in r.lower() for r in result["reasons"]))
|
|
|
|
def test_workspace_none_with_reset_blocks(self):
|
|
report = "\n".join([
|
|
"Review worktree path: branches/review-pr280-feat-issue-275-claim",
|
|
"Workspace mutations: none",
|
|
"Worktree mutations: git reset --hard FETCH_HEAD",
|
|
])
|
|
result = assess_worktree_ownership_report(
|
|
report,
|
|
ownership_session={
|
|
"session_owned": True,
|
|
"worktree_path": "branches/review-pr280-feat-issue-275-claim",
|
|
},
|
|
command_log=["git reset --hard FETCH_HEAD"],
|
|
)
|
|
self.assertFalse(result["proven"])
|
|
self.assertTrue(any("workspace mutations" in r.lower() for r in result["reasons"]))
|
|
|
|
def test_main_checkout_blocks(self):
|
|
result = assess_worktree_ownership_report(
|
|
"Review worktree path: /Users/dev/Gitea-Tools",
|
|
ownership_session={
|
|
"validation_ran": True,
|
|
"main_checkout": True,
|
|
"worktree_path": "/Users/dev/Gitea-Tools",
|
|
},
|
|
)
|
|
self.assertFalse(result["proven"])
|
|
|
|
|
|
class TestExport(unittest.TestCase):
|
|
def test_review_proofs_reexport(self):
|
|
from review_proofs import assess_worktree_ownership_report as exported
|
|
|
|
self.assertTrue(callable(exported))
|
|
|
|
|
|
if __name__ == "__main__":
|
|
unittest.main() |