Get started with Cosmo
This guide walks you through integrating your application with the Cosmo API — how to authenticate, work with partner programs, and issue points using the core endpoints.
Cosmo follows a simple flow: sign up, authenticate, retrieve your partnerships, and start issuing points. Sandbox mode lets you build and test safely before you connect to real partner programs in production.
- ✓Set up your organization and get credentials
- ✓Authenticate and make authorized requests
- ✓Load the programs available to your business
- ✓Validate destination users
- ✓Preview and issue point transactions
- ✓Retrieve transactions and handle errors correctly
Account setup
There are two paths to getting set up with Cosmo, depending on your organization's needs.
Managed setup
White-glove onboardingFor enterprises that require guided onboarding, Cosmo manages account creation and configuration on your behalf:
- Provisioning your organization in Cosmo
- Assigning API credentials
- Enabling program partnerships
- Completing KYB and compliance checks
Credentials are shared once configuration is complete.
Self-service setup
Start in minutesPrefer to set up directly? Follow the onboarding flow in the Cosmo Portal:
- Sign up using your business email
- Enter your organization's legal name
- Complete the automated KYB process
- Organization and credentials are created automatically on approval
Sandbox mode is available immediately after completion.
Sign up
To begin using Cosmo, your team creates an organization and completes identity verification.
client_id / client_secret — become visible once your KYB is approved.Sandbox integration
Sandbox mode lets you build and test without affecting live partner programs. All Sandbox transactions are isolated from production systems.
- ✓Simulated transactions — no real balances are affected.
- ✓Error triggers — error responses can be triggered deterministically with specific
destinationUserIdvalues. - ✓Mirrors production — program configurations match production structure.
- ✓No real points — no partner systems are contacted.
https://api.cosmopoints.comhttps://api.sandbox.cosmopoints.comEvery endpoint path in this guide is appended to the base URL of the environment you're targeting.
client_id. What changes per environment is the client_secret: use your sandbox secret to get a sandbox access token, and your production secret for production.Sandbox matches production logic as closely as possible, so your integration behaves identically when you switch environments.
User flow
The complete flow your system follows to issue points through Cosmo. Each step maps to a specific API endpoint.
Authenticate
POST /oauth2/tokenYour backend sends client_id and client_secret; Cosmo returns a short-lived JWT. Include Authorization: Bearer <token> in all requests. If the token expires, re-authenticate and retry. One auth endpoint for both environments — always on api.cosmopoints.com — same client_id; the client_secret you send determines whether the token is for sandbox or production.
Retrieve partnerships
GET /programsFetch the partner programs available to your organization — for populating your UI, obtaining the programId needed for issuing, and reading each program's required fields. Cache the list, refresh periodically.
Issue points
POST /programs/{programId}/validate-memberCheck the destination user is valid before issuing — reduces failed transactions.
POST /transactions/previewReturns the points for a given value without creating a transaction — for "You will receive X points" UI.
POST /transactionsCreates the transaction and issues points. Response includes transaction ID, total points, reference number, and timestamp — store them for reconciliation.
Key API endpoints
All paths below are relative to the base URL: https://api.cosmopoints.com for production, https://api.sandbox.cosmopoints.com for sandbox.
/programs/{programId}/validate-memberConfirm the destination user is valid before issuing or previewing. Request: destinationUserId, destinationUserEmail → Response: isValid.
/transactions/previewCheck how many points a fiat value yields before committing. Request: programId, value → Response: totalPoints. Performs no transaction.
/transactionsThe core transaction endpoint. Send a fiat value + currency, or an exact number of points with currency: POINTS (for promotions, bonuses, deterministic issuance). Response: id, totalPoints, referenceNumber, date — store for reconciliation.
/transactions/{transactionId}Retrieve full details of a previously issued transaction — for reconciliation, support, audit trails, webhook-retry verification, and confirming final state.
Error handling
Sandbox supports deterministic error simulation via predefined destinationUserId values — no dedicated endpoint, triggered through the normal issue-points flow. Use it to test backend error handling, frontend messaging, and retry / reconciliation flows.
- Expired or invalid token
- Missing required fields
- Exceeding allowed transaction value limit
- Exceeding allowed transaction points limit
- Invalid program ID
- No partnership with the specified program
All errors follow a structured response format for consistent handling.
Production integration
Once you've completed your sandbox testing, switching to production takes two changes: point your base URL from api.sandbox.cosmopoints.com to api.cosmopoints.com, and swap in your production client_secret (your client_id stays the same). No code changes — the API structure and endpoints are identical.
Production credentials are issued after your KYB is approved and at least one partner program is enabled. Store them securely; never expose them client-side.
- Transactions interact with live partner systems
- User validation checks real member accounts
- All issued points are financially binding
- Error simulation is not available
- Confirm active partnerships
- Validate required destination fields per program
- Handle all error cases gracefully
- Verify reconciliation logic
- Test webhook handling (if used)
Going live
Going live means issuing real points to real accounts. Final checks before launch:
- ✓Production authentication flow is functioning
- ✓At least one real user validated via Validate Member
- ✓A small live transaction issued for internal testing
- ✓Transaction retrievable via
GET /transactions/{transactionId} - ✓All transaction details stored in your internal system
After launch, monitor failed attempts, token-expiry errors, missing destination fields, traffic spikes, and reconciliation mismatches. All production transactions are permanent and billable — keep logs of validation, preview, and issue calls for downstream audits.
Point Exchange widget
A ready-made UX for point purchases and exchanges — embed it in your web or mobile app while your backend keeps all sensitive logic (auth, debits, reconciliation). Your backend obtains a short-lived access token (valid 10 minutes, server-side only — never expose clientId or clientSecret in the frontend):
{
"clientId": "string", // from the Cosmo Portal
"clientSecret": "string", // from the Cosmo Portal
"userId": "string", // any unique user identifier
"amount": number, // in your chosen currency
"referenceNumber": "string", // your internal reference
"currency": "string", // USD / SAR / AED
"description": "string | null"
}
→ response: { "accessToken": "string" }Then launch the widget with the token — in a web app (iFrame / WebView) or a mobile in-app browser:
<iframe src="https://purchase.cosmopoints.com?token=ACCESS_TOKEN" style="width: 100%; height: 600px; border: 0;" ></iframe>
The widget displays available options, collects required inputs, and sends the transaction to Cosmo. On completion, Cosmo sends a Transaction Webhook — verify it, confirm the transactionId, value, and destination, and only then apply post-completion logic like debiting the user's balance.
Multibrand widget
Lets users manage reward preferences for a Multibrand card — select and edit programs, decide how rewards are allocated, and update preferences over time. Same pattern as Point Exchange: your backend obtains a short-lived token (valid 1 minute) and your frontend launches the widget with it.
{
"clientId": "string",
"clientSecret": "string",
"userId": "string" // your unique user ID (can be opaque)
}
→ response: { "accessToken": "string" }<iframe src="https://multibrand.cosmopoints.com/?token=ACCESS_TOKEN" style="width: 100%; height: 600px; border: 0;" ></iframe>
https://multibrand.sandbox.cosmopoints.com/?token=ACCESS_TOKENWebhooks
Cosmo notifies your backend of important events, like completed transactions. Configure endpoints in the Cosmo Portal → Developers → Webhooks. Three authentication modes are supported:
Your configured username and password are included in the request — verify before processing.
Cosmo obtains a token from your token endpoint and includes it in webhook requests.
Every request is signed with your secret, delivered via x-cosmo-signature and x-cosmo-timestamp headers — verify cryptographically that requests are authentic and untampered.
Transaction webhook
Sent when a transaction (API or widget) completes. Process the transaction only after receiving it — typical uses: debit the user's balance, update your ledger, display results, trigger notifications.
{
"transactionId": "string",
"sourceProgramId": "string",
"destinationProgramId": "string",
"value": number,
"referenceNumber": "string",
"destinationAccount": {
"destinationUserEmail": "user@example.com",
"destinationUserId": "123456"
},
"timestamp": number,
"type": "string"
}Program connection webhook
Sent when a user links, edits, or removes program connections — update your internal preference model accordingly. type is LINKED | DELINKED | UPDATED.
Verifying signatures
Read the headers, take the raw JSON body exactly as sent, build ${timestamp}:${rawBody}, compute HMAC-SHA-256 with your secret, and compare with the signature — only process on match.
// verify-signature.js
const expected = crypto
.createHmac('sha256', WEBHOOK_SECRET)
.update(`${timestamp}:${rawBody}`)
.digest('hex');
const valid = crypto.timingSafeEqual(
Buffer.from(signature),
Buffer.from(expected)
);- ✓Always verify signatures before processing any event
- ✓Use
timingSafeEqualto prevent timing attacks - ✓Log invalid signatures for security monitoring
- ✓Store multiple secret versions if you rotate keys
- ✓Don't parse or trust the body until after validation
- ✓Keep your endpoint publicly reachable over HTTPS