Skip to content

Execute redemption (Unified)

Request

Process redemption execution using role-based detection. Supports user, business, and admin redemption processing.

ERC721 Dynamic Context & Template Interpolation:

For ERC721 tokens, you can provide a context object whose values become available as {{context.xxx}} placeholders in the token's name/description and AI prompts.

Context sources (merge order):

  1. TokenMetadata.defaultPromptContext{{defaults.xxx}}
  2. Redemption.context (admin-defined) → {{context.xxx}} (always applied)
  3. RedemptionRedeemRequest.context (this field) → {{context.xxx}} (only if allowExternalContextOverwrite=true)

Example - Event ticket redemption:

{
  "redemptionId": "redemption-uuid",
  "context": {
    "seatNumber": "A12",
    "attendeeName": "John Smith"
  }
}

With TokenMetadata name: "{{context.attendeeName}} - Seat {{context.seatNumber}}" Result: "John Smith - Seat A12"

Security
projectKey or authJWT
Bodyapplication/jsonrequired
redemptionIdstringrequired

The redemption id

businessIdstring or nullrequired

Business ID for this redemption transaction.

Token Recipient Priority:

  1. redemption.ownerBusinessId - Business that created/owns the redemption (default)
  2. dto.businessId - This field (override for marketplace/facilitator scenarios)
  3. TENANT - Platform fallback for platform-wide redemptions

Stamp Token Resolution (resolveByBusiness=true): When a redemption's priceTokenUnits contains stamp tokens with resolveByBusiness=true, this field is also used to identify which business's on-chain tokenId to burn.

  • If the redemption has an ownerBusinessId, that is used automatically — no need to provide this.
  • For tenant-level redemptions (no ownerBusinessId), you must provide this field so the server knows which business's stamp slot to resolve and burn.

Use Cases:

  • Omit for standard business-owned redemptions (both recipient and stamp resolution default to owner)
  • Provide for tenant-level stamp redemptions to specify which business's stamps to burn
  • Provide for marketplace scenarios where a facilitator processes redemptions for another business
contextobject

ERC721 only - User-provided external context for template interpolation and AI prompts.

SECURITY: Only applied if TokenMetadata.allowExternalContextOverwrite is true (admin opt-in required). Redemption.context (admin-controlled) is ALWAYS applied regardless.

Template Interpolation: Values become available as {{context.keyName}} placeholders in TokenMetadata name/description fields and AI prompts.

Special validity keys:

  • validityDate - Base date for trigger-based validity
  • validityEndDate - End date for date ranges (e.g., hotel checkout)
  • validityDuration - Override duration in days/hours

Custom keys: Any arbitrary key becomes {{context.keyName}} placeholder.

Example: { guestName: "John", roomNumber: "305", validityEndDate: "2026-04-20T11:00:00Z" }

Example:
{ "guestName": "John Doe", "validityDate": "2026-04-15T14:00:00Z", "validityEndDate": "2026-04-20T11:00:00Z" }
curl -i -X POST \
  https://docs.pers.ninja/_mock/swagger/redemptions/redeems \
  -H 'Content-Type: application/json' \
  -H 'x-project-key: YOUR_API_KEY_HERE' \
  -d '{
    "redemptionId": "string",
    "businessId": "string",
    "context": {
      "guestName": "John Doe",
      "validityDate": "2026-04-15T14:00:00Z",
      "validityEndDate": "2026-04-20T11:00:00Z"
    }
  }'

Responses

Redemption executed successfully

Bodyapplication/json
redeemobject(RedemptionRedeemDTO)required

The redemption redeem details that the user redeemed

senderTransactionobject or null(TransactionRequestResponseDTO)required

The sender transaction that resulted from the user redeeming the redemption, this is applicable for redemptions that involve sending tokens from the user to a specific address

Response
{ "redeem": { "id": "string", "userId": "string", "redemptionId": "string", "userCountryCode": "string", "status": "PENDING", "createdAt": "2019-08-24T14:15:22Z", "updatedAt": "2019-08-24T14:15:22Z", "message": "string", "dataSource": {}, "included": {} }, "senderTransaction": { "transaction": {}, "transactionStatus": "created", "signingData": {}, "actionable": {}, "walletSigningStatus": "string", "signatureData": {} } }