Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 8 additions & 4 deletions GITHUB_ISSUES.md
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@ Every issue inherits `AGENTS.md` and the definition of done in `IMPLEMENTATION_P
| 10 | ABUSE-001 | Enforce native App Check and privacy-preserving abuse limits | P0 | L | partial: Enterprise browser source/tests tracked in [#159](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/159); provider config, native enforcement, rate limits, and live proof open | CI-001 baseline |
| 11 | PAY-001 | Add strict request schemas and immutable monetary snapshots | P0 | L | partial: PAY-001A source/tests tracked in [#157](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/157); B/C/D and endpoint adoption open | ABUSE-001 interface agreed |
| 12 | PROMO-001 | Disable unmodeled Stripe promotions until discounts are authoritative | P0 | S | source/tests complete under open GitHub issue #102; provider inventory and deployment remain owner action | PAY-001 for any future discount contract |
| 13 | PAY-002 | Implement idempotent payment commands and explicit state machines | P0 | L | partial: PAY-002A1 pure state source/tests tracked in [#161](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/161); PAY-002B1 pure command identity tracked in [#163](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/163); registered-only journal pair tracked in PAY-002B2A [#165](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/165); PAY-002B2B lease/fence source/tests tracked in [#169](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/169); PAY-002B2C1 immutable initial plan tracked in [#173](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/173); PAY-002B2C2 pre-send evidence/cutoff tracked in [#182](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/182); PAY-002B2C3A pure closed reconciliation decision tracked in [#184](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/184); evidence persistence/authorization/runtime/migration/sagas open | CONFIG-001, PAY-001 |
| 13 | PAY-002 | Implement idempotent payment commands and explicit state machines | P0 | L | partial: PAY-002A1 pure state source/tests tracked in [#161](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/161); PAY-002B1 pure command identity tracked in [#163](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/163); registered-only journal pair tracked in PAY-002B2A [#165](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/165); PAY-002B2B lease/fence source/tests tracked in [#169](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/169); PAY-002B2C1 immutable initial plan tracked in [#173](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/173); PAY-002B2C2 pre-send evidence/cutoff tracked in [#182](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/182); PAY-002B2C3A pure closed reconciliation decision tracked in [#184](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/184); PAY-002B2C3B immutable candidate persistence tracked in [#206](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/206); authorization/runtime/migration/sagas open | CONFIG-001, PAY-001 |
| 14 | PAY-003 | Build idempotent, async-aware Stripe webhook ingestion | P0 | L | PAY-003A source merged in #101; PAY-003B/C remain open; not deployed | CONFIG-001, PAY-001/PAY-002 target contract |
| 15 | RACE-001 | Add transactional race-capacity reservations | P0 | L | proposed | PAY-002, PAY-003 event contract |
| 16 | MERCH-001 | Add SKU variants and transactional inventory reservations | P0 | L | proposed | PAY-002, PAY-003 event contract |
Expand Down Expand Up @@ -630,7 +630,7 @@ The local webhook/creator patch is a safety default, not a complete discount fea
## PAY-002 — Implement idempotent payment commands and explicit state machines

**Labels:** `priority:P0`, `type:reliability`, `type:security`, `area:stripe`, `area:firebase`, `size:L`, `needs-migration`
**Status:** Partial. PAY-002A1 pure state source/tests are tracked in live [#161](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/161). PAY-002B1 pure command-identity source/tests are tracked in live [#163](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/163). PAY-002B2A registered-only journal source/tests are tracked in live [#165](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/165). PAY-002B2B lease/fence source and tests are tracked in live [#169](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/169). PAY-002B2C1 immutable initial-plan source/tests are tracked in live [#173](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/173). PAY-002B2C2 pre-POST evidence and retry-cutoff source/tests are tracked in live [#182](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/182). PAY-002B2C3A pure closed reconciliation-decision source/tests are tracked in live [#184](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/184). Verified evidence persistence, safe attempt advancement, runtime adoption, real legacy inventory/migration, and checkout sagas remain open.
**Status:** Partial. PAY-002A1 pure state source/tests are tracked in live [#161](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/161). PAY-002B1 pure command-identity source/tests are tracked in live [#163](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/163). PAY-002B2A registered-only journal source/tests are tracked in live [#165](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/165). PAY-002B2B lease/fence source and tests are tracked in live [#169](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/169). PAY-002B2C1 immutable initial-plan source/tests are tracked in live [#173](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/173). PAY-002B2C2 pre-POST evidence and retry-cutoff source/tests are tracked in live [#182](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/182). PAY-002B2C3A pure closed reconciliation-decision source/tests are tracked in live [#184](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/184). PAY-002B2C3B immutable reconciliation-candidate persistence source/tests are tracked in live [#206](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/206). Safe attempt advancement, runtime adoption, real legacy inventory/migration, and checkout sagas remain open.
**Depends on:** CONFIG-001 and PAY-001

### Current atomic boundary
Expand All @@ -647,9 +647,13 @@ PAY-002B2C2 [#182](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/182) ow

PAY-002B2C3A [#184](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/184) owns only the unused pure closed attempt-1 evidence policy. Its exact flat version-1 record contains closed evidence categories and no provider-object, business, member, account, metadata, amount, timestamp, URL, free-text, or raw-status-code identifier/payload value. Only the complete matching tuple for trusted proof that endpoint execution never began, or the complete matching tuple for an exact verified expired/unpaid Session with verified expiry and an explicitly eligible new logical generation, returns `new_attempt_candidate`. The complete matching exact-open or verified-success tuple returns `existing_attempt_found`; every single-field difference, timeout, lost connection, provider error, old/pruned key, missing/not-found object, empty/partial search, unknown/processing state, mismatch, or conflict returns `reconciliation_required`. All outputs are fixed/frozen and non-identifying.

C3A is not a reconciler or authorization boundary. It stores nothing, calls nothing, has no runtime/index import, cannot send/execute/advance or create attempt `2`, and does not replay a provider result. C3B must persist immutable paired verified evidence; C3C must separately authorize/version a later attempt only after that proof, an allowed business transition, and a fresh lease. PAY-002C/D, PAY-003B, RACE-001B, MERCH-001B, PAY-004, and PAY-005 depend on the completed B2C chain.
C3A is not a reconciler or authorization boundary. It stores nothing, calls nothing, has no runtime/index import, cannot send/execute/advance or create attempt `2`, and does not replay a provider result.

B2A/B2B/C1/C2 add no TTL. Deleting both C2 partners would look like first use, so [#110](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/110) must approve retention and a server-only tombstone or equivalent durable duplicate barrier before any journal record is removed. CI-001B3 [#167](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/167) runs the exact demo-project/opt-in command-journal suite as a separate hosted release prerequisite; #169, #173, and #182 expand that same file. Hosted results remain synthetic source proof only. The current foundations, including C3A, are unused: they add no endpoint/index export, Firebase deployment, Stripe/provider configuration, production read/write, website change, or officer behavior.
PAY-002B2C3B [#206](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/206) owns only the unused immutable reconciliation-candidate record/audit pair. It snapshots one exact C3A input, then validates the exact B1 registration, B2 lease history, C1 attempt-1 plan, and complete C2 record/audit. It may persist only an exact `new_attempt_candidate`, only at or after C2's stored 23-hour deadline, and only when the current validated lease is expired. Before either time gate, it writes nothing and returns the unchanged C3A candidate. The deterministic record and audit carry command-bound complete-plan/send commitments, closed evidence enums, observed fence/expiry, trusted time, and a complete-record digest. Exact retries are read-only. Changed valid evidence conflicts; orphan, malformed, future, or foundation-mismatched records fail closed without repair. No raw account/key/parameters/IDs/money/free text/provider response or attempt `2` is stored or returned.

C3B's fixed `requires_separate_authorization` result is not provider retrieval/truth, caller authorization, send permission, response replay, or a business transition. C3C must separately authorize/version a later attempt only after the persisted proof, an allowed business transition, and a fresh lease. PAY-002C/D, PAY-003B, RACE-001B, MERCH-001B, PAY-004, and PAY-005 depend on the completed B2C chain.

B2A/B2B/C1/C2/C3B add no TTL. Deleting both C2 or C3B partners could remove a durable duplicate barrier, so [#110](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/110) must approve retention and a server-only tombstone or equivalent durable barrier before any journal record is removed. CI-001B3 [#167](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/167) runs the exact demo-project/opt-in command-journal suite as a separate hosted release prerequisite; #169, #173, #182, and #206 expand that same file. Hosted results remain synthetic source proof only. The current foundations, including C3A/C3B, are unused: they add no endpoint/index export, Firebase deployment, Stripe/provider configuration, production read/write, website change, or officer behavior.

### Problem

Expand Down
2 changes: 1 addition & 1 deletion GITHUB_ISSUE_SLICES.md
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,7 @@ An agent-ready child has one observable outcome, one trust boundary, explicit de
| PAY-002B2C1 | source/tests tracked in live [#173](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/173); PAY-002B2B/#169; unused/no runtime or deploy | While the exact current lease/fence is active, atomically bind one immutable attempt-1 Stripe account/mode/API-version/static `checkout_session_create` POST mapping/parameters/key plan and deterministic audit. Reject arbitrary or object-ID-bearing paths. Store only command-bound commitments; this is not account proof or send permission. | Mock plus #167-hosted emulator races for exact bind/recovery/conflict/expiry/takeover/malformed partners and byte-preserved B2A/B2B records; explicit browser-denial tests. |
| PAY-002B2C2 | source/tests tracked in live [#182](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/182); PAY-002B2C1/#173 and CI-001B3/#167; unused/no runtime or deploy | Recompute the exact B1/C1 attempt-1 plan under the current lease/fence, then atomically create a separate pre-POST marker and deterministic audit. Bind both to a command-bound digest of every immutable C1 plan field. The persisted version-1 deadline is 23 hours after the marker. The first atomic creation, and an exact retry, return fixed `send_permitted` only after a post-transaction trusted-time check remains before the transaction-validated lease's captured expiry and deadline; this does not re-read lifecycle state. Equality, later time, rollback, missing/unreadable paired time, or plan replacement reconciles or fails closed. Never create attempt 2 or make a provider request. | Mock and #167-hosted emulator concurrency, post-transaction lease expiry, self-consistent plan replacement, commit-failure, lost-response, takeover, nanosecond cutoff, unknown-time, timeout/connection-loss/5xx ambiguity, conflict, malformed-partner, byte-preservation, redaction, static no-call/random, and explicit browser-denial tests. |
| PAY-002B2C3A | source/tests tracked in live [#184](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/184); PAY-002B2C2/#182 and merged PAY-003A/#101 vocabulary; unused/no runtime or deploy | Define only the pure exact flat version-1 Stripe attempt-1 evidence classifier. Closed enums produce fixed frozen `existing_attempt_found`, `new_attempt_candidate`, or `reconciliation_required`; a candidate is never send/advance permission. Only verified never-began or exact verified expired/unpaid evidence can be a candidate. | Exhaust the closed matrix and every single-field mutation; timeout/connection/provider-error/old-key/missing-reference/not-found/empty-or-partial-search/unknown/conflict advancement denied; hostile shape/proxy/accessor/Unicode/redaction/no-side-effect/static no-adoption tests. |
| PAY-002B2C3B | proposed; PAY-002B2C3A/#184 | Append one immutable paired reconciliation evidence record/audit only after a trusted verifier produces an exact C3A input. Keep all prior command, lifecycle, plan, send, and provider-attempt evidence immutable. Do not authorize or create attempt `2`. | Mock plus emulator atomic-pair/exact-retry/orphan/conflict/concurrency/immutability/browser-denial tests; verifier inputs are synthetic and contain no production/provider data. |
| PAY-002B2C3B | source/tests tracked in live [#206](https://github.com/Run-MPRC/Run-MPRC.github.io/issues/206); PAY-002B2C3A/#184 and PAY-002B2C2/#182; unused/no runtime or deploy | Append one immutable paired reconciliation candidate record/audit only after exact C1/C2 validation, the stored 23-hour cutoff, current lease expiry, and an exact C3A candidate. Bind complete plan/send evidence plus observed lease proof; keep all prior records immutable. Do not authorize or create attempt `2`. | Mock plus emulator atomic-pair/exact-retry/orphan/conflict/concurrency/immutability/lost-ack/browser-denial tests; verifier inputs are synthetic and contain no production/provider data. |
| PAY-002B2C3C | proposed; PAY-002B2C3B | Under a fresh lease and allowed business transition, consume the persisted C3B result to authorize and version a later provider attempt. Never advance on candidate classification alone; keep every earlier attempt immutable. PAY-003B may later consume this result. | Safe never-began and expired/unpaid advancement tests plus timeout/5xx/old-key/missing-reference/partial-search/stale-lease/conflict denial and retry/concurrency invariants. |
| PAY-002C | proposed; PAY-001B, PAY-002B2C3C, RACE-001B | Convert race checkout to persistence-first record/hold plus deterministic Stripe Session saga. | One record/Session on retry at every failure boundary. |
| PAY-002D | proposed; PAY-001C, PAY-002B2C3C, MERCH-001B | Convert merchandise/catalog creation to persistence-first order/hold plus deterministic Stripe keys. | One order/Session/catalog object on retry; failure recovery tests. |
Expand Down
Loading