Skip to content

feat: claim rewards on a CommitKudos page instead of peanut.to - #185

Draft
zaibon wants to merge 1 commit into
mainfrom
feat/claim-page
Draft

zaibon wants to merge 1 commit into
mainfrom
feat/claim-page

Conversation

@zaibon

@zaibon zaibon commented Oct 4, 2026 •

Copy link
Copy Markdown
Owner

What

  • New /claim page. It reads a reward link from the chain (amount, network, sender, date, already-claimed state) without a wallet, switches the wallet to the link's network, and claims the reward to the connected address. With no link in the URL, it offers a box to paste a link, and old peanut.to links work there too.
  • Reward links generated by the reward flow and the dashboard now point to {site}/claim instead of peanut.to/claim.
  • peanut.ts: new parseLink, toClaimUrl, getLinkDetails and claimLink helpers.
  • wallet.svelte.ts: a keyless public RPC (publicnode.com) for each supported network, so a link can be read without a connected wallet.
  • /api/mail only emails links to this site's own /claim page, and no longer accepts peanut links.
  • The link password is redacted from Sentry (events, transactions and breadcrumbs) and from Vercel Analytics pageviews. Session Replay isn't started when a page load starts on /claim.

Why

Peanut moved to peanut.me and SDK-created links can no longer be claimed through its site:

  • peanut.to/claim?... returns a 301 to the bare https://peanut.me/, so the link is lost.
  • peanut.me/claim looks links up in Peanut's backend (GET api.peanut.me/send-links/{pubKey}). That backend only knows links created through Peanut's app, so it returns 404 Send link not found for our links.
  • The gasless relayer (api.peanut.to/claim-v2) replies "This service has been suspended by its owner".
  • The SDK's default RPCs rely on Peanut's Infura key, which no longer works.

The Peanut contracts still work: simulating the claim of an existing Sepolia link (deposit #1778) against the v4.3 contract succeeds. So we can keep the SDK for deposits and host the claim step ourselves.

Design decisions

  • The recipient pays gas. Peanut's gasless relayer is gone, so whoever claims needs a little of the chain's native token. The page says so. Running our own relayer is possible later but out of scope here.
  • Links point to the site that created them (window.location.origin + /claim), so production links go to https://commitkudos.com/claim, local dev to localhost, and Vercel previews to the preview URL. Claims can be tested end to end anywhere, and /api/mail only emails links to its own origin. The trade-off: links created on a preview deployment stop working once that preview is gone. Verified by running getLinksFromTx with this baseUrl on the real Sepolia deposit, which produced https://commitkudos.com/claim?c=11155111&v=v4.3&i=1778#p=….
  • Same link format as Peanut (?c=&v=&i=#p=). This lets toClaimUrl rewrite old peanut.to links (including the older #?c=…&p= form) with no migration.
  • Claims are built with prepareClaimTx and our own RPC. We don't use the SDK's claimLink, which may fall back to the dead default providers. This is the same transaction that was simulated successfully.
  • Secret handling. Anyone who has the #p= password can take the funds. A global Sentry event processor redacts it from every event type. Replay frame hooks never see the page URL, so Replay is skipped when the app loads on /claim instead. Claim links are always opened with a full page load (from an email or a pasted URL).
  • CLAIM_PATH and the redaction helpers live in #lib/claim.ts. That keeps the server mail route from importing the SDK and AppKit, which only run in the browser.

Testing

  • pnpm check, eslint src, prettier --check src and pnpm build pass.
  • Simulated the claim of an existing Sepolia link from two different addresses: it returns true at about 66k gas.
  • Not done yet: a real claim through the page with a wallet. Also check that a freshly created reward emails a /claim link.

Follow-ups

  • Contributors who already received peanut.to links need to paste them into /claim.
  • The footer still says "Built on Peanut Protocol" and links to peanut.to (which now redirects to peanut.me).

🤖 Generated with Claude Code

Peanut moved to peanut.me and its claim page no longer opens links made
with the SDK: peanut.to redirects to the homepage, dropping the link, and
peanut.me only knows links registered through its own backend. The
gasless relayer (api.peanut.to) is suspended and the SDK's default RPCs
rely on a dead Infura key.

The deposits themselves are still claimable on-chain, so reward links now
point to a /claim page that reads the link through public RPCs and claims
it with the recipient's wallet. Old peanut.to links can be pasted there.

The link password lives in the URL fragment, so it is redacted from
Sentry events, breadcrumbs and Vercel Analytics, and Session Replay is
not started on the claim page.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@vercel

vercel Bot commented Oct 4, 2026 •

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated
commitkudos Ready Ready Preview Oct 4, 2026 3:53pm UTC

This branch was successfully deployed

1 active deployment
Preview — 5121bf07 Deployed Oct 4, 2026 by vercel[bot]
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant