Authentication
Authorization: Bearer sp_agent_xxxxxxxx_…
# or
X-SuperPay-Key: sp_agent_xxxxxxxx_…
Request body
| Field | Type | Required | Description |
| amount | number | required | USD amount (0 < amount ≤ 1,000,000) |
| cards | object[] | required | User's card portfolio — see card schema below |
| mcc | string | optional | ISO 18245 4-digit MCC; takes precedence over category |
| category | string | optional | Spend category fallback (groceries, dining, gas, travel, …) |
| merchant_name | string | optional | Merchant display name for name-based category resolution |
Card object schema (each element of cards[])
| Field | Type | Required | Description |
| id | string | required | Your internal card ID — returned unchanged in response |
| issuer | string | required | Card issuer name, e.g. "Chase", "Citi" |
| reward_type | string | required | One of: cashback | points | miles |
| base_rate | number | required | Base earn rate as a percentage (e.g. 2 for 2% cashback, 1.5 for 1.5x points) |
| category_bonuses | object[] | optional | Array of {category, rate} bonus overrides |
Response shape
{
"recommendation_id": "9f8b2c…",
"category": "groceries",
"amount_cents": 8745,
"top_cards": [
{
"rank": 1,
"id": "amex_bcp",
"issuer": "American Express",
"reward_type": "cashback",
"reward_rate": 6,
"reason": "6% on groceries",
"estimated_reward_cents": 524,
"estimated_reward_display": "$5.24"
},
{ "rank": 2, … },
{ "rank": 3, … }
],
"top_card": { … }
}
Error codes
| Status | Code | Meaning |
| 400 | INVALID_AMOUNT | amount missing, ≤ 0, or > $1,000,000 |
| 400 | INVALID_CARD_DATA | One or more cards failed validation; see card_errors[] |
| 401 | MISSING_API_KEY | No key in Authorization or X-SuperPay-Key header |
| 401 | INVALID_API_KEY | Key not recognized or hash mismatch |
| 401 | API_KEY_REVOKED | Key revoked — rotate or contact hello@superpayrewards.com |
| 403 | ORIGIN_NOT_ALLOWED | Browser request from unregistered origin (production keys) |
| 429 | RATE_LIMITED | Over 300 req/min; see Retry-After header |
| 500 | INTERNAL_ERROR | SuperPay-side failure — safe to retry with backoff |
Code examples
curl -X POST https://superpayrewards.com/v1/agent/recommend \
-H "Authorization: Bearer sp_agent_xxxxxxxx_..." \
-H "Content-Type: application/json" \
-d '{
"amount": 87.45,
"mcc": "5411",
"merchant_name": "Whole Foods",
"cards": [
{
"id": "amex_bcp",
"issuer": "American Express",
"reward_type": "cashback",
"base_rate": 1,
"category_bonuses": [{ "category": "groceries", "rate": 6 }]
},
{ "id": "citi_dc", "issuer": "Citi", "reward_type": "cashback", "base_rate": 2 }
]
}'
const res = await fetch('https://superpayrewards.com/v1/agent/recommend', {
method: 'POST',
headers: {
'Authorization': `Bearer ${process.env.SUPERPAY_AGENT_KEY}`,
'Content-Type': 'application/json',
},
body: JSON.stringify({
amount: 87.45,
mcc: '5411',
merchant_name: 'Whole Foods',
cards: [
{ id: 'amex_bcp', issuer: 'American Express', reward_type: 'cashback',
base_rate: 1, category_bonuses: [{ category: 'groceries', rate: 6 }] },
{ id: 'citi_dc', issuer: 'Citi', reward_type: 'cashback', base_rate: 2 },
],
}),
});
const { top_cards, category } = await res.json();
// top_cards[0].reason → "6% on groceries"
// Pass directly to your agent's response.
import os, requests
resp = requests.post(
'https://superpayrewards.com/v1/agent/recommend',
headers={
'Authorization': f"Bearer {os.environ['SUPERPAY_AGENT_KEY']}",
'Content-Type': 'application/json',
},
json={
'amount': 87.45,
'mcc': '5411',
'merchant_name': 'Whole Foods',
'cards': [
{'id': 'amex_bcp', 'issuer': 'American Express',
'reward_type': 'cashback', 'base_rate': 1,
'category_bonuses': [{'category': 'groceries', 'rate': 6}]},
{'id': 'citi_dc', 'issuer': 'Citi',
'reward_type': 'cashback', 'base_rate': 2},
],
},
timeout=10,
)
best = resp.json()['top_cards'][0]
print(best['reason']) # → "6% on groceries"
// OpenAI tool definition
{
"type": "function",
"function": {
"name": "get_best_payment_card",
"description": "Returns the optimal credit card for a purchase based on reward rates. Always call before the user pays.",
"parameters": {
"type": "object",
"properties": {
"amount": { "type": "number", "description": "Purchase amount in USD" },
"merchant_name": { "type": "string", "description": "Merchant or store name" },
"mcc": { "type": "string", "description": "ISO 18245 MCC if available" }
},
"required": ["amount"]
}
}
}
// In your tool handler, fetch user cards from memory, then:
const result = await getBestCard({ amount, merchantName, mcc, cards: userCards });
// Inject result.bestCard.reason into the assistant message.
Try it
Sandbox key
Response
// Response will appear here