API reference
Stable
3 min read

API reference


Base URL:

text

https://api.perkamo.com

Local development default:

text

http://localhost:4001

Authenticate server calls with x-perkamo-api-key. All bodies are JSON.

Create server keys in Secret keys and copy the Space slug from Spaces.

POST /v1/identify

Creates or updates a profile.

json

{
"tenant": "commerce-test",
"user_id": "customer_123",
"traits": {
"plan": "premium",
"country": "CZ"
}
}
FieldRequiredLimitNotes
tenantyes128 charsSpace slug connected to the API key.
user_idyes256 charsStable user identifier.
traitsnoJSON objectNon-secret profile facts.

POST /v1/events

Ingests one activity event.

After sending events, inspect delivery and rule outcomes in Events and Customers.

json

{
"tenant": "commerce-test",
"user_id": "customer_123",
"event": "purchase.completed",
"transaction_id": "order_1092",
"context": {
"amount": 12900,
"currency": "CZK"
},
"occurred_at": "2026-06-01T10:00:00.000Z"
}

json

{
"applied": true,
"duplicate": false,
"delta": [{ "wallet": "points", "amount": 50 }],
"leveled_up": false,
"unlocked": [{ "type": "perk", "key": "welcome_member", "name": "Welcome member" }],
"wallet_state": { "points": 50 },
"level": {
"wallet": "points",
"level": 1,
"current": 50,
"nextLevelAt": 100,
"currentLevelAt": 0,
"progress": 0.5
}
}

POST /v1/events:batch

Ingests up to 100 events.

json

{
"events": [
{
"tenant": "commerce-test",
"user_id": "customer_123",
"event": "page.viewed",
"transaction_id": "pageview_01",
"context": { "path": "/pricing" }
}
]
}

Each event still needs its own transaction_id. Batch requests are not a replacement for all-or-nothing domain transactions in your backend.

GET /v1/profile/{user_id}

Reads current profile state.

Response excerpt:

json

{
"tenant": "commerce-test",
"user_id": "customer_123",
"traits": {},
"wallets": { "points": 50 },
"level": {
"wallet": "points",
"level": 1,
"current": 50,
"nextLevelAt": 100,
"currentLevelAt": 0,
"progress": 0.5
},
"perks": [
{
"key": "welcome_member",
"unlocked_at": "2026-06-01T10:00:00.000Z",
"metadata": {
"trigger": { "type": "points_threshold", "wallet": "points", "amount": 30 }
}
}
],
"next_perks": [
{
"key": "active_user",
"name": "Active user",
"description": "Daily habit perk for apps like progress trackers or banking."
}
],
"achievements": {
"completed": [],
"in_progress": [],
"unlocked": []
},
"flags": {
"levels": { "level_1": true },
"has_level_at_least": { "level_1": true },
"perks": { "welcome_member": true }
},
"events": [],
"streaks": [],
"active_boosts": []
}

POST /v1/rewards/redeem

Redeems a configured reward by subtracting wallet cost and returning a declarative effect.

json

{
"tenant": "commerce-test",
"user_id": "customer_123",
"reward_key": "free_shipping",
"transaction_id": "redeem_free_shipping_order_1092"
}

Perkamo returns the reward effect. Your system remains responsible for final fulfillment unless a dedicated fulfillment integration is active.

GET /v1/program

Returns the authenticated Space blueprint: earning rules, rewards, perks, achievements, levels, integration status, metrics and usage.

Edit the visible rule and wallet configuration from Program rules and Program wallets.

GET /v1/usage

Returns current billing-period usage meters for the authenticated Space.

POST /v1/admin/config/{module}

Uploads a versioned configuration module. Requires the admin:config scope.

Allowed modules in v1 are events, leveling, wallets, perks, achievements and boosts.

json

{
"version": "2026-06-01",
"active": true,
"body": {}
}

Status guide

StatusMeaningAction
400Invalid body or business ruleFix payload or show a user-safe message.
401Missing or invalid API keyCheck backend secret configuration.
403API key does not match Space or scopeCheck tenant and key scopes.
404Resource not foundCheck profile id or endpoint path.
429Rate or usage limit exceededBack off and retry later.
5xxTemporary server failureRetry with the same transaction id.