We built a Splitwise alternative where the link is the account
说明与用途
PeanutSplit 让朋友们在不创建账户的情况下分摊费用,使用单一 URL 作为凭证,采用确定性金额处理、离线排队和安全实时更新。
问题
Friends will not create accounts, so the room URL must serve as invite, login, and data key.
结果
PeanutSplit allows friends to split expenses without account creation, using a single URL as a bearer credential, with deterministic money handling, offline queuing, and secure real‑time updates.
工作流
- Generate a 16‑byte random key, base64url‑encode it, and append it to a readable stem to form the room URL.
- Use the URL as a bearer credential; no recovery or owner override.
- Store money amounts as strings and BigInt; display numbers only.
- Lock FX rates at entry; never re‑price history.
- Queue new expenses offline and replay when online; edits require connection.
- Use SSE to notify clients of changes; clients refetch data; stream carries no room data.
- Route FX and receipt requests through an allow‑listed proxy; containers cannot reach the internet directly.
- Write usage limits into STEWARDSHIP.md to avoid feature gates and paid tiers.
- Deploy as AGPL to keep hosted forks open.
证据
If your friends have to make an account, they won’t. So the room URL had to be the whole product: the invite, the login and the data key in one string.
The link is a bearer credential. 16 random bytes, base64url, appended to a readable stem. No recovery, no owner override. Treat it like a key.
Money as strings + BigInt. A Number never touches an amount except for display. Equal splits hand out remainders deterministically.
FX locked at entry. Editing an expense never re‑prices history. Rates are fetched through a same‑origin route so the browser never talks to a second host.
Realtime that leaks nothing. SSE sends "something changed", the client refetches. The stream itself carries no room data.
No egress in prod. Containers can't reach the internet; push, FX and the receipt model go through an allowlisted proxy.
- 记录日期: 2026-10-09T00:56:01.632Z