What you're trying to do
When multiple agents propose writes over weeks, .vouch/proposed/ accumulates pending proposals that never get reviewed. Those files are gitignored, so they do not show up in PRs and are easy to forget. Reviewers see a growing vouch pending list with no clear lifecycle for “we’re never going to look at this.”
I want a first-class way to expire old pending proposals: move them to decided/ with an explicit reason, emit audit events, and honor the config knob that already exists in the init template — without silently deleting history or bypassing the review gate.
Concrete example: An agent proposed three claims in March; it is now June and nobody approved or rejected them. Running vouch expire should list those three; vouch expire --apply should close them as rejected with decision_reason: expired, so vouch audit and decided/ still explain what happened.
What you've tried
vouch reject — Works per proposal but requires a human reason for each id; does not scale for bulk stale cleanup.
- Manual deletion of
proposed/*.yaml — Loses audit trail and violates the “decided/ is never GCed” model.
review.expire_pending_after_days in templates/config.template.yaml — Documented (default 90, 0 = never) but not read anywhere in code today.
Suggested shape
CLI
vouch expire # dry-run: list proposals that would expire
vouch expire --apply # perform GC
vouch expire --json # machine-readable output
What you're trying to do
When multiple agents propose writes over weeks,
.vouch/proposed/accumulates pending proposals that never get reviewed. Those files are gitignored, so they do not show up in PRs and are easy to forget. Reviewers see a growingvouch pendinglist with no clear lifecycle for “we’re never going to look at this.”I want a first-class way to expire old pending proposals: move them to
decided/with an explicit reason, emit audit events, and honor the config knob that already exists in the init template — without silently deleting history or bypassing the review gate.Concrete example: An agent proposed three claims in March; it is now June and nobody approved or rejected them. Running
vouch expireshould list those three;vouch expire --applyshould close them asrejectedwithdecision_reason: expired, sovouch auditanddecided/still explain what happened.What you've tried
vouch reject— Works per proposal but requires a human reason for each id; does not scale for bulk stale cleanup.proposed/*.yaml— Loses audit trail and violates the “decided/ is never GCed” model.review.expire_pending_after_daysintemplates/config.template.yaml— Documented (default90,0= never) but not read anywhere in code today.Suggested shape
CLI