|
| 1 | +#!/usr/bin/env python3 |
| 2 | +"""Run PatchProof's trusted local fixture without external dependencies.""" |
| 3 | + |
| 4 | +from __future__ import annotations |
| 5 | + |
| 6 | +import tempfile |
| 7 | +from pathlib import Path |
| 8 | + |
| 9 | +from patchproof.approval import PatchApproval |
| 10 | +from patchproof.proposal import PatchProposal |
| 11 | +from patchproof.repository import ReadOnlyRepository |
| 12 | +from patchproof.runner import UnsafeLocalRunner |
| 13 | +from patchproof.validator import ValidationReceipt, store_validation, validate_patch |
| 14 | + |
| 15 | + |
| 16 | +ROOT = Path(__file__).resolve().parents[1] |
| 17 | +PHASE_LABELS = { |
| 18 | + "baseline_reproduction": "补丁前复现 / fail before patch", |
| 19 | + "patched_reproduction": "补丁后复现 / pass after patch", |
| 20 | + "full_regression": "完整回归 / full regression", |
| 21 | + "hidden_tests": "隐藏测试 / external hidden tests", |
| 22 | +} |
| 23 | + |
| 24 | + |
| 25 | +def main() -> int: |
| 26 | + repository = ReadOnlyRepository(ROOT / "fixtures" / "calculator") |
| 27 | + before = repository.snapshot() |
| 28 | + proposal = PatchProposal.create( |
| 29 | + unified_diff=(ROOT / "fixtures" / "division-by-zero.diff").read_text( |
| 30 | + encoding="utf-8" |
| 31 | + ), |
| 32 | + base_snapshot=before.digest, |
| 33 | + ) |
| 34 | + approval = PatchApproval.create( |
| 35 | + run_id="quickstart-demo", |
| 36 | + proposal=proposal, |
| 37 | + approved_by="local-demo", |
| 38 | + supplied_proposal_hash=proposal.proposal_hash, |
| 39 | + ) |
| 40 | + receipt = validate_patch( |
| 41 | + repository=repository, |
| 42 | + proposal=proposal, |
| 43 | + approval=approval, |
| 44 | + reproduction_tests=ROOT / "fixtures" / "reproduction", |
| 45 | + hidden_tests=ROOT / "fixtures" / "hidden", |
| 46 | + runner=UnsafeLocalRunner(timeout_seconds=10), |
| 47 | + ) |
| 48 | + unchanged = repository.snapshot() == before |
| 49 | + with tempfile.TemporaryDirectory(prefix="patchproof-demo-") as directory: |
| 50 | + stored = store_validation(receipt, Path(directory)) |
| 51 | + loaded = ValidationReceipt.from_json( |
| 52 | + stored.receipt_path.read_text(encoding="utf-8") |
| 53 | + ) |
| 54 | + integrity_verified = loaded == receipt |
| 55 | + |
| 56 | + print("PatchProof 可信本地演示 / trusted-local demo") |
| 57 | + print("------------------------------------------------") |
| 58 | + for phase in receipt.phases: |
| 59 | + status = "PASS" if phase.passed else "FAIL" |
| 60 | + print( |
| 61 | + f"[{status}] {PHASE_LABELS[phase.name]} " |
| 62 | + f"({phase.tests_run} test{'s' if phase.tests_run != 1 else ''})" |
| 63 | + ) |
| 64 | + print("------------------------------------------------") |
| 65 | + print(f"验证结果 / validation: {'PASSED' if receipt.success else 'FAILED'}") |
| 66 | + print(f"真实仓库未变 / repository unchanged: {'YES' if unchanged else 'NO'}") |
| 67 | + print( |
| 68 | + "回执完整性 / receipt integrity: " |
| 69 | + f"{'VERIFIED' if integrity_verified else 'INVALID'}" |
| 70 | + ) |
| 71 | + print("证据等级 / proof grade: NO (trusted-local; Docker required)") |
| 72 | + return 0 if receipt.success and unchanged and integrity_verified else 1 |
| 73 | + |
| 74 | + |
| 75 | +if __name__ == "__main__": |
| 76 | + raise SystemExit(main()) |
0 commit comments