API reference

Every endpoint of the psyke Reseller API. All require the X-Reseller-API-Key header, and all can return the shared auth (401) and throttle (429) errors from the error reference.

Base URL: https://api.p-syke.com/api/reseller. Request bodies: read endpoints take none; POST /orders is multipart/form-data. Responses are JSON, except GET /orders/{order_id}/result, which is a file download.

GET/api/reseller/services

Returns the full service catalog (11 services). The code is what you pass as service_code to POST /orders; price_per_number is the USD price charged per number.

Request

cURL
curl -s "$BASE/services" -H "X-Reseller-API-Key: $KEY"

Response 200

Response schema
FieldTypeDescription
servicesarray<Service>The 11 resellable services.
services[].codestringService code, e.g. "tg-active". Pass as service_code on POST /orders.
services[].namestringHuman-readable service name.
services[].platformstringPlatform label: telegram, whatsapp, facebook, instagram, amazon, binance, or other.
services[].price_per_numbernumberUSD charged per accepted number. Small values may serialize in scientific notation (e.g. 1.544e-05).
Example response
{
  "services": [
    { "code": "tg-active", "name": "Telegram active + registered", "platform": "telegram", "price_per_number": 0.0004 },
    { "code": "ws-registered", "name": "WhatsApp registered check", "platform": "whatsapp", "price_per_number": 0.00001544 },
    { "code": "binance", "name": "Binance registered check", "platform": "binance", "price_per_number": 0.00132353 }
  ]
}

Errors

CodeHTTPWhen
INVALID_API_KEY401The X-Reseller-API-Key header is missing entirely.
authentication_failed401The key is malformed (wrong prefix / shorter than 16 chars) or unknown / inactive / revoked.
throttled429You exceeded the rate limit (120/min, per API key).

GET/api/reseller/countries

Returns the supported country catalog (the FMT country list filtered to valid 2-letter ISO codes). Use code (uppercase ISO-2) as the country value on POST /orders.

Request

cURL
curl -s "$BASE/countries" -H "X-Reseller-API-Key: $KEY"

Response 200

Response schema
FieldTypeDescription
countriesarray<Country>Supported countries, in catalog order (not alphabetical).
countries[].codestringISO-2 code, uppercase. Pass as country on POST /orders.
countries[].namestringEnglish country name (no flag). A few rows have name == code — real catalog data.
countries[].area_codestringInternational dialing prefix, e.g. "1" for US, "55" for Brazil.
Example response
{
  "countries": [
    { "code": "US", "name": "United States", "area_code": "1" },
    { "code": "BR", "name": "Brazil", "area_code": "55" },
    { "code": "BT", "name": "Bhutan", "area_code": "975" }
  ]
}

Errors

CodeHTTPWhen
INVALID_API_KEY401The X-Reseller-API-Key header is missing entirely.
authentication_failed401The key is malformed (wrong prefix / shorter than 16 chars) or unknown / inactive / revoked.
throttled429You exceeded the rate limit (120/min, per API key).

GET/api/reseller/balance

Returns your prepaid wallet balance. 1 token = 1 USD.

Request

cURL
curl -s "$BASE/balance" -H "X-Reseller-API-Key: $KEY"

Response 200

Response schema
FieldTypeDescription
token_balancestringBalance as a fixed 6-decimal string (a precise decimal — do not parse as float if you need exact accounting).
currencystringAlways "USD".
Example response
{
  "token_balance": "98.460000",
  "currency": "USD"
}

Errors

CodeHTTPWhen
INVALID_API_KEY401The X-Reseller-API-Key header is missing entirely.
authentication_failed401The key is malformed (wrong prefix / shorter than 16 chars) or unknown / inactive / revoked.
throttled429You exceeded the rate limit (120/min, per API key).

POST/api/reseller/orders

Submit a phone-number list for scanning. This is the only write endpoint and the only one that spends your wallet. The request is multipart/form-data (file upload).

Send an Idempotency-Key header (any unique string, ≤ 64 chars) so a network retry replays the original order (HTTP 200 with "replayed": true) instead of charging twice. Without it, every retry that reaches the server creates a new, separately charged order.

Request headers
FieldTypeDescription
X-Reseller-API-Keystring (required)Your API key.
Content-Typemultipart/form-dataSet automatically by curl -F / FormData.
Idempotency-Keystring (optional, ≤ 64 chars)Replay guard. Scoped to your account.
Request body (multipart form fields)
FieldTypeDescription
service_codestring (required)One of the 11 catalog codes from GET /services. Trimmed server-side.
countrystring (required)ISO-2 code; trimmed then uppercased. Must be in GET /countries.
filefile (required)Phone-number list, one number per line, UTF-8, digits only (no + prefix). Max 20 MB.

Request

cURL
curl -s -X POST "$BASE/orders" \
  -H "X-Reseller-API-Key: $KEY" \
  -H "Idempotency-Key: order-2026-07-17-001" \
  -F "service_code=tg-active" \
  -F "country=US" \
  -F "[email protected]"

Response 201

Response schema
FieldTypeDescription
order_idstringUTC microsecond timestamp, format YYYYMMDDThhmmssffffffZ (chronologically sortable). Rare same-microsecond collisions get a "-<hex>" suffix. Treat as opaque.
statusstringOrder status right after submission — normally "queued".
service_codestringEcho of the submitted service code.
countrystringEcho of the normalized (uppercased) country code.
input_countintegerCount of valid, deduplicated numbers accepted and billed.
coststringTotal charge as a fixed 6-decimal string = input_count × price_per_number.
wallet_balance_afterstringYour wallet balance after the charge (decimal string).
replayedboolean (only on replay)Present and true only when an Idempotency-Key matched an existing order; the response is then HTTP 200, not 201.
Example response
{
  "order_id": "20260702T034401344985Z",
  "status": "queued",
  "service_code": "tg-active",
  "country": "US",
  "input_count": 2000,
  "cost": "0.800000",
  "wallet_balance_after": "98.460000"
}

Errors

CodeHTTPWhen
INVALID_API_KEY401The X-Reseller-API-Key header is missing entirely.
authentication_failed401The key is malformed (wrong prefix / shorter than 16 chars) or unknown / inactive / revoked.
throttled429You exceeded the rate limit (120/min, per API key).
UNKNOWN_SERVICE400service_code is not one of the 11 catalog codes.
UNKNOWN_COUNTRY400country (after trim + uppercase) is not a supported ISO-2 code.
VALIDATION_ERROR400The file field is missing, or the Idempotency-Key header is longer than 64 characters.
FILE_TOO_LARGE400The uploaded file exceeds 20 MB.
MIN_NUMBERS400Fewer than 2000 valid numbers remain after normalization + dedup. Nothing is charged.
INSUFFICIENT_BALANCE402Your wallet balance is too low to charge the job. No order is created.
NOT_QUEUEABLE409The order could not be queued (rare internal state).
ORDER_REF_CONFLICT503The server could not allocate a unique order id after bounded retries (extremely rare). No charge is made.

GET/api/reseller/orders/{order_id}

Poll order status and metadata. This is the endpoint you loop on to detect completion.

Path parameters
FieldTypeDescription
order_idstring (path)The order_id returned by POST /orders. Use it verbatim.

Request

cURL
curl -s "$BASE/orders/$ORDER_ID" -H "X-Reseller-API-Key: $KEY"

Response 200

Response schema
FieldTypeDescription
order_idstringThe order id (same value you polled with).
statusstringOne of draft, queued, running, completed, failed.
service_codestringReseller service code for this order.
countrystringISO-2 country code.
input_countintegerValid, deduplicated numbers accepted at submit time.
result_countintegerNumber of result rows (0 until completed).
result_suspectbooleanQuality flag; false by default.
created_atstringISO-8601 timestamp.
completed_atstring | nullISO-8601 timestamp, or null until completed.
failure_messagestringEmpty "" unless the order failed, in which case a customer-safe reason (internal/provider detail is never exposed).
Example response
{
  "order_id": "20260702T034401344985Z",
  "status": "running",
  "service_code": "tg-active",
  "country": "US",
  "input_count": 2000,
  "result_count": 0,
  "result_suspect": false,
  "created_at": "2026-07-02T03:44:01.344985+00:00",
  "completed_at": null,
  "failure_message": ""
}

Errors

CodeHTTPWhen
INVALID_API_KEY401The X-Reseller-API-Key header is missing entirely.
authentication_failed401The key is malformed (wrong prefix / shorter than 16 chars) or unknown / inactive / revoked.
throttled429You exceeded the rate limit (120/min, per API key).
NOT_FOUND404No order matches that id for your account (never existed, malformed id, or belongs to another tenant).

GET/api/reseller/orders/{order_id}/result

Download the finished result. The success response is a FILE (CSV or TSV), not JSON. Only call it once GET /orders/{order_id} reports status == "completed".

Path parameters
FieldTypeDescription
order_idstring (path)The order_id returned by POST /orders.

Request

cURL
curl -s "$BASE/orders/$ORDER_ID/result" -H "X-Reseller-API-Key: $KEY" -OJ

Response 200

The success response is a file download (CSV or TSV), not JSON. Use the Content-Type / Content-Disposition header to pick the extension.

Response headers + body
# CSV branch (generated export file present)
Content-Type: text/csv; charset=utf-8
Content-Disposition: attachment; filename="order_20260702T034401344985Z_result.csv"

# TSV branch (inline text result)
Content-Type: text/tab-separated-values; charset=utf-8
Content-Disposition: attachment; filename="order_20260702T034401344985Z_result.tsv"

phone,id
14155550001,123

Errors

CodeHTTPWhen
INVALID_API_KEY401The X-Reseller-API-Key header is missing entirely.
authentication_failed401The key is malformed (wrong prefix / shorter than 16 chars) or unknown / inactive / revoked.
throttled429You exceeded the rate limit (120/min, per API key).
NOT_FOUND404No order matches that id for your account (never existed, malformed id, or belongs to another tenant).
NOT_READY409The order is not completed yet. The message includes the current status.
RESULT_UNAVAILABLE500The order is completed but the result payload could not be retrieved (missing export file and no inline text).