Skip to content

Funding receipts: 'Confirm this receipt' write path (matchingReceipt) for mutual/multi-attestor provenance #174

Description

@hb-agent

Summary

Add a write path that lets a party confirm an existing funding receipt by writing their own counterpart org.hypercerts.funding.receipt that links back to the original via the lexicon's matchingReceipt strongRef. This is the producer of the mutually-confirmed and multi-attestor provenance the read side already renders (PR #173 / magic-indexer #214).

Why

The funding-receipt provenance UI (#173) shows attestation tags computed by the indexer from matchingReceipt-linked clusters. Today nothing in the app writes that link, so every payment has a single attestation and mutually-confirmed / multi-attestor rows never appear. To light those up we need a UX that writes a counterpart receipt.

Scope

  • A "Confirm this receipt" affordance on a funding receipt the viewer is named in (or can vouch for): recipient, sender, or a third party.
  • On confirm, write a new org.hypercerts.funding.receipt on the viewer's PDS that:
    • copies the same amount, currency, from, to, for as the original (so the indexer's field-equality check passes), and
    • sets matchingReceipt to the original's strongRef ({ uri, cid }).
  • New funding-receipt.ts helper in src/lib/atproto/ (create / delete), rate-limit registered, mirroring the existing record-write helpers.
  • Allowlist org.hypercerts.funding.receipt in ALLOWED_WRITE_COLLECTIONS (src/app/api/xrpc/[...method]/route.ts) — the app currently only reads receipts.
  • Optimistic UI: the new attestation/chip should appear without a full reload (the indexer recomputes the cluster once both sides are ingested).

Dependencies

Notes / open questions

  • One-directional link: only the second writer can reference the first. The indexer back-propagates the verdict to both, so writing one counterpart is enough.
  • Default visibility: per the funding-receipts design doc, the funder/sender side should likely default-hide unacknowledged claims to avoid "X funded me" spam — decide whether a confirm also flips visibility.
  • Free-text from/to (wallet addresses) can't be matched to a DID, so confirmation is most meaningful when at least one party is an account.

Related: PR #173 (read/render), magic-indexer #214, hypercerts-lexicon #224.

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions