API version v1
PrizeNest Developer Documentation
Signed server-to-server purchase and refund events for approved partners. API keys stay separate in the partner dashboard.
API Reference
Implemented Partner API endpoints.
PrizeNest implements signed POST endpoints for purchases and refunds, plus signed GET endpoints for plan, usage, and billing visibility. Read endpoints use the existing events:read credential scope. The public base URL is https://www.prizenest.org for both TEST and LIVE credentials.
POST /api/v1/partner/purchases
Creates or replays a purchase event, calculates points from the active reward rule, records integration activity, and in LIVE mode sends the reward through the accounting engine.
| Field | Type | Required | Validation |
|---|---|---|---|
| externalOrderId | string | Yes | 1 to 160 characters; unique in partner/source/mode. |
| customer.email | string | Email or phone required | Valid email or blank string. |
| customer.phone | string | Email or phone required | Up to 32 characters; normalized server-side. |
| order.subtotalCents | integer | Yes | 0 to 100,000,000 cents. |
| order.currency | string | No | Three-letter currency; defaults to USD and is uppercased. |
| occurredAt | ISO date | No | Must include a timezone offset when provided. |
| metadata | object | No | Arbitrary JSON except partner cost fields. |
{
"externalOrderId": "ORDER-10052",
"customer": {
"email": "customer@example.com",
"phone": "+17185551234"
},
"order": {
"subtotalCents": 7500,
"currency": "USD"
},
"occurredAt": "2026-08-24T14:15:00.000Z",
"metadata": {
"channel": "online"
}
}{
"success": true,
"eventId": "cm...",
"externalOrderId": "ORDER-10052",
"reward": {
"id": "PNR_...",
"points": 150,
"status": "PENDING",
"customerStatus": "AWAITING_CUSTOMER_CLAIM",
"claimExpiresAt": "2027-08-24T14:15:00.000Z"
}
}POST /api/v1/partner/refunds
Creates or replays a refund event for an external order. Pending and awaiting-funding rewards are cancelled. Available rewards move to admin review instead of automatically creating negative balances.
| Field | Type | Required | Validation |
|---|---|---|---|
| externalOrderId | string | Yes | 1 to 160 characters; must reference the original purchase. |
| externalRefundId | string | No | 1 to 160 characters; defaults to refund:<externalOrderId>. |
| reason | string | No | Up to 500 characters. |
| occurredAt | ISO date | No | Must include a timezone offset when provided. |
| metadata | object | No | Arbitrary JSON object. |
{
"externalOrderId": "ORDER-10052",
"externalRefundId": "REFUND-9001",
"reason": "Customer cancelled before fulfillment.",
"occurredAt": "2026-08-24T15:20:00.000Z"
}{
"success": true,
"eventId": "cm...",
"externalOrderId": "ORDER-10052",
"refund": {
"externalRefundId": "REFUND-9001",
"status": "CANCELLED"
},
"reward": {
"id": "PNR_...",
"points": 150,
"status": "CANCELLED"
}
}GET /api/v1/partner/plans
Returns published merchant plan versions, monthly and annual prices, included point allowance, overage rate, API rate limit, support class, and feature entitlements.
GET /api/v1/partner/usage
Returns the current billing period, included points consumed, overage points, accrued overage amount, reward-liability estimate, usage projection, recommendation, and recent usage events.
GET /api/v1/partner/billing
Returns the active merchant subscription, selected plan version, wallet snapshot, reward-funding balance, and recent invoices.
Idempotency
Send a stable Idempotency-Key for every retry. The same credential, key, event type, and payload hash returns the stored response. Reuse with different data returns a conflict. Purchase externalOrderId is also unique inside partner, environment, source, and event type.
Events
Purchase and refund processing records PartnerOrderEvent rows and IntegrationEvent rows that appear in partner and admin logs. A public GET/read event endpoint is not implemented yet.
Code examples
curl -X POST "$PRIZENEST_BASE_URL/api/v1/partner/purchases" \
-H "Content-Type: application/json" \
-H "X-PrizeNest-Key: $PRIZENEST_KEY" \
-H "X-PrizeNest-Timestamp: $PRIZENEST_TIMESTAMP" \
-H "X-PrizeNest-Signature: $PRIZENEST_SIGNATURE" \
-H "Idempotency-Key: ORDER-10052" \
--data '{ "externalOrderId": "ORDER-10052", "customer": { "email": "customer@example.com", "phone": "+17185551234" }, "order": { "subtotalCents": 7500, "currency": "USD" }, "occurredAt": "2026-08-24T14:15:00.000Z", "metadata": { "channel": "online" }}'import hashlib
import hmac
import json
import os
import time
import urllib.request
body = json.dumps({
"externalOrderId": "ORDER-10052",
"customer": {"email": "customer@example.com"},
"order": {"subtotalCents": 7500, "currency": "USD"},
}, separators=(",", ":"))
path = "/api/v1/partner/purchases"
timestamp = str(int(time.time()))
body_hash = hashlib.sha256(body.encode()).hexdigest()
canonical = "\n".join(["v1", "POST", path, timestamp, body_hash])
signature = "sha256=" + hmac.new(
os.environ["PRIZENEST_SECRET"].encode(),
canonical.encode(),
hashlib.sha256,
).hexdigest()
request = urllib.request.Request(
os.environ["PRIZENEST_BASE_URL"] + path,
data=body.encode(),
method="POST",
headers={
"Content-Type": "application/json",
"X-PrizeNest-Key": os.environ["PRIZENEST_KEY"],
"X-PrizeNest-Timestamp": timestamp,
"X-PrizeNest-Signature": signature,
"Idempotency-Key": "ORDER-10052",
},
)<?php
$body = json_encode([
'externalOrderId' => 'ORDER-10052',
'customer' => ['email' => 'customer@example.com'],
'order' => ['subtotalCents' => 7500, 'currency' => 'USD'],
]);
$path = '/api/v1/partner/purchases';
$timestamp = (string) time();
$bodyHash = hash('sha256', $body);
$canonical = implode("\n", ['v1', 'POST', $path, $timestamp, $bodyHash]);
$signature = 'sha256=' . hash_hmac('sha256', $canonical, getenv('PRIZENEST_SECRET'));
?>