Quickstart
Five steps: create a test key, find your card id, enroll a customer, award something, and listen for what happens next.
1. Create a test key
From Settings → API & Webhooks, click Create test key. Test keys start with psk_test_, work on every plan — including your 14-day trial — and never ask for billing details. The raw key is shown once at creation; store it in your own secrets manager, not in source control.
2. Find your card id
cardId identifies which loyalty program (BusinessCard) a customer enrolls on. List your org's cards to find it — a test key sees the same cards a live key does.
curl https://api.passtastic.io/api/v1/cards \
-H "X-Api-Key: YOUR_TEST_KEY"[
{
"cardId": "64f1c2a9b8e4a2d1c0a1b2c3",
"name": "Loyalty Card",
"passType": "stamp_card",
"dataCollectionEnabled": true,
"questions": [
{ "key": "email", "label": "Email", "type": "email", "required": true, "isIdentifier": true }
]
}
]3. Enroll a customer
cardId is the loyalty program (BusinessCard) to enroll them on — the same card id you'd use with a live key; Passtastic keeps a private test-mode copy of it behind the scenes. externalCustomerId is your own identifier (CRM contact id, user id, etc.) — Passtastic uses it to resolve the customer on every later call.
Send email and phone whenever you have them. If this person already signed up on their own — through the merchant's sign-up page, an import, or the counter — Passtastic matches them and attaches your externalCustomerId to the card they already carry, instead of issuing a second one.
curl -X POST https://api.passtastic.io/api/v1/customers \
-H "X-Api-Key: YOUR_TEST_KEY" \
-H "Content-Type: application/json" \
-d '{
"externalCustomerId": "crm_10293",
"cardId": "64f1c2a9b8e4a2d1c0a1b2c3",
"name": "Alex Rivera",
"email": "alex@example.com"
}'{
"passUserId": "66a1e2f3c9d4b5a6f7081920",
"externalCustomerId": "crm_10293",
"cardId": "64f1c2a9b8e4a2d1c0a1b2c3",
"result": "created",
"matchedBy": null,
"linked": true,
"installUrl": "https://passtastic.io/get-pass/64f1c2a9b8e4a2d1c0a1b2c3?code=8K3F2Q",
"status": "pending_install"
}Open the installUrl on your phone and add the card — it shows TEST. Every pass created with a test key carries a TEST · prefix on its name, so nobody mistakes it for a real customer's card.
result is "created" for a brand-new customer and "matched" when Passtastic recognised an existing one — matchedBy tells you which identifier did it.
4. Award stamps or points
curl -X POST https://api.passtastic.io/api/v1/customers/crm_10293/earn \
-H "X-Api-Key: YOUR_TEST_KEY" \
-H "Content-Type: application/json" \
-d '{
"type": "points",
"from": "spend",
"spend": { "amount": 24.50, "currency": "EUR" },
"note": "Order #4821"
}'{ "balance": { "points": 245 }, "transactionId": "66a1e2f3c9d4b5a6f7081920" }The pass on your phone updates within seconds.
5. Subscribe to a webhook
So your system finds out about redemptions or level changes as they happen, without polling for them.
curl -X POST https://api.passtastic.io/api/v1/webhooks \
-H "X-Api-Key: YOUR_TEST_KEY" \
-H "Content-Type: application/json" \
-d '{
"url": "https://your-system.com/hooks/passtastic",
"events": ["balance.updated", "reward.redeemed"]
}'Test webhooks: switch the Webhooks panel to Test in Settings → API & Webhooks and point an endpoint at a URL that can receive test traffic — your next earn call will fire it.
Going live
Going live: create a live key and replace the test key. Card IDs stay the same — the rest of your integration doesn't change. See Keys and test mode for what else differs between the two.