Monetization
Selling keys
Issue keys automatically when your store reports a sale — SellAuth, SellSn or any store that sends signed webhooks.
On this page
How it works
A store webhook is a URL you paste into your store. When someone buys, the store calls it, SantiAuth checks the signature, generates the keys and answers with them — one key per line — so the store can hand them to the buyer as the delivered product.
1Pays for the product
2Calls your webhook URL with a signed payload
3Verifies the signature
4Generates N keys
5Responds with the keys, one per line
6Delivers the keys as the product
- 1
Buyer → Store
Pays for the product
- 2
Store → SantiAuth
Calls your webhook URL with a signed payload
- 3
SantiAuth
Verifies the signature
- 4
SantiAuth
Generates N keys
- 5
SantiAuth → Store
Responds with the keys, one per line
- 6
Store → Buyer
Delivers the keys as the product
Supported stores:
| Store | Signature header | Algorithm |
|---|---|---|
| SellAuth | X-Signature | HMAC-SHA256 |
| SellSn | X-Webhook-Signature | HMAC-SHA256 |
| Custom | X-Custom-Signature (configurable) | HMAC-SHA256 (or SHA1 / SHA512) |
Setting up
- Open Webhooks → Store webhooks and press New webhook.
- Give it a name (e.g. SellAuth main store) and pick the Store.
- Copy the Signing secret — it is generated for you — and paste it into your store's webhook / dynamic-delivery settings.
- Copy the webhook URL and paste it into the same place in your store. It looks like:
https://api.santiauth.com/api/v1/webhooks/execute/<webhook-id>- Optionally turn on Refund handling.
- Press Test webhook — it sends a signed test event through the same pipeline as real deliveries. You should see the generated keys in the response.
Quantity
The number of keys is read from the payload field item.quantity (1 when missing, at most 100 per delivery). A buyer who orders 3 gets 3 keys.
Which keys are issued
Keys are created from your service's provider (or the provider set in provider_id). A webhook made in the dashboard issues Standard, lifetime keys. To change that, update the webhook's action_config through the API — see Update a webhook and the action_config fields:
| Option | Values |
|---|---|
| Duration | 1–8760 hours, or unlimited |
| Premium | Issue Premium keys (SA_IsUserPremium = true) |
| One-time | The key loads the script only once |
| Timer on first use | Duration starts at the first execution, not at purchase |
| HWID limit | 1–100 devices per key |
| Quantity field | Another payload path instead of item.quantity |
| Provider | provider_id — which provider issues the keys |
Custom stores
Pick Custom for any store that can send a signed JSON webhook:
- The signature is
HMAC(secret, raw request body)as hex, sent inX-Custom-Signature— asha256=style prefix is accepted. The header name and algorithm (SHA1, SHA256, SHA512) can be changed through the API. - Conditions (API) let you skip deliveries that aren't sales of this product. Each condition checks a payload field with
equals,contains,regex,exists,greater_thanorless_than, combined with AND / OR groups. A skipped delivery returns204and generates nothing.
Refunds and chargebacks
Turn on Refund handling on a webhook to revoke an order's keys when the store reports a refund or chargeback:
- Order ID field — JSON path to the order id in the payload (e.g.
idordata.uniqid). Every issued key is linked to it. - Refund rule — a field, an operator and a value (e.g.
eventequalsrefund). Deliveries matching it revoke that order's keys instead of issuing new ones. - Ban holders — optionally also ban the Discord account and bound HWID of those keys.
A refund delivery answers 200 with JSON instead of keys:
{ "event": "refund", "order_id": "A1B2C3", "reason": "...", "order_found": true, "revoked": 3, "not_found": 0 }Responses
| Status | Meaning |
|---|---|
200 | Keys generated. Body: the keys, one per line. For a refund: the JSON above. |
204 | Webhook disabled or conditions not met — nothing generated. |
400 | Missing or invalid signature, the body isn't JSON, or a refund without an order id. |
403 | The caller's IP is blocked. |
404 | Unknown webhook URL. |
409 | The same delivery is still being processed — the store's retry later gets the first run's keys, never a second set. |
413 | Payload larger than 1 MB. |
429 | Too many requests from one IP (600 per minute). Retry-After says when to retry. |
500 | Key generation failed (for example the service has no provider). |
Logs and retries
Delivery logs on each webhook show every request: the sent body, the response and the generated keys. Failed deliveries are retried automatically up to 10 times with exponential backoff (from 30 seconds up to 1 hour between tries).