@rpp402/sdk
v0.1.4
Published
TypeScript SDK for the Robinhood Payments Protocol. Mirrors the protocol's six primitives one-to-one, with no additional abstractions.
Maintainers
Readme
@rpp402/sdk
Published under MIT to the @rpp402 scope on npm.
npm install @rpp402/sdkTypeScript SDK for RPP402. It mirrors the protocol exactly - one method per primitive, no incidental abstractions - and validates every response against @rpp402/protocol's JSON Schemas at runtime, not just at compile time. Ships ESM and CommonJS builds with full type declarations. Requires Node.js 20 or newer (it uses the global fetch).
Quickstart
import { createClient } from "@rpp402/sdk";
const rpp = createClient({ agentWallet: "0xYourAgentWalletAddress" });
const service = await rpp.discover("market-data.example"); // RPP402-001
const session = await rpp.session.create(service); // RPP402-003
const quote = await session.quote(service, { // RPP402-002 (+ attaches leg)
capability: "market-data.quote",
params: { ticker: "NVDA" },
settlementAsset: service.supported_assets[0],
});
await session.intent({ // RPP402-004
asset: quote.price.asset,
authorization: { type: "agentic_account_delegation", account_id: "aa_...", delegation_ref: "del_..." },
});
await session.settle(); // RPP402-005 (polls to a terminal state)
const receipt = await session.receipt(); // RPP402-006For an eip712_signature authorization instead of Agentic Account delegation, pass a signTypedData function to createClient() and omit authorization from session.intent() - the SDK builds and signs the payload itself.
What you get
- One method per primitive.
discover,session.create,session.quote,session.intent,session.settle,session.receipt- each maps to exactly one RFC. - Validated responses. A non-conformant server produces an
Rpp402ValidationErrorinstead of a malformed object being passed through silently. - Typed errors. Every non-2xx response becomes an
Rpp402Errorcarrying the RFC 9457problem+jsontype,status, anddetail. Network failures, timeouts, and malformed bodies are normalized to the same error type, so you never have to catch a rawfetchrejection. - Exact money. Leg totals are summed with
BigIntdecimal-string math, neverparseFloat- amounts don't drift. - Built-in timeout. Requests time out after 30s by default; pass
timeoutMs(or your ownAbortSignal) to change it. - No bundled wallet library.
signTypedDatais caller-injected, so you choose viem, ethers, or an Agentic Account SDK.
MPP interop
Client-side helpers for MPP (the Machine Payments Protocol) live under the mpp namespace, so an agent can also pay MPP-protected resources:
import { mpp } from "@rpp402/sdk";
const res = await fetch(url); // 402 with `WWW-Authenticate: Payment ...`
const challenges = mpp.parseChallenges(res.headers.get("www-authenticate") ?? "");
const authorization = mpp.buildAuthorization(signedCredential); // "Payment <base64url>"
await fetch(url, { headers: { authorization } });MPP is an HTTP auth scheme with no third-party facilitator - settlement runs on its own rails (Stripe on Tempo). These helpers cover reading challenges and building the credential header; the method-specific credential is caller-supplied, the same way signTypedData is.
Learn more
- Protocol RFCs: https://rpp402.com/docs
- Schemas and types:
@rpp402/protocol - CLI and scaffolding:
@rpp402/cli
