01 · Quickstart
Creating the first payment request
Amount fields are submitted in kuruş (minor units). For example, 12550 represents ₺125.50. The 201 response includes direct IBAN instructions or a secure payment page.
Configure API access
Generate an active API key from the merchant dashboard.
Submit the request
Use a unique idempotency key (UUID v4) for every POST request.
Verify the outcome
Finalize financial outcomes via webhook or transaction query API.
curl --request POST --url https://payinextra.com/api/v1/payments/deposits --header 'Content-Type: application/json' --header 'X-API-Key: YOUR_API_KEY' --header 'X-Merchant-Id: YOUR_MERCHANT_ID' --header 'X-Idempotency-Key: 550e8400-e29b-41d4-a716-446655440000' --data '{
"amount": 12550,
"currency": "TRY",
"paymentMethod": "bank_transfer",
"merchantReference": "order-2026-000045",
"customer": {
"name": "Ahmet Yılmaz",
"reference": "customer-1742",
"email": "ahmet@example.com"
},
"metadata": {
"cartId": "cart-8GQ39"
}
}'
{
"paymentId": "pay_01H9YE1N5CB3X7S9HESY7Y5XGK",
"type": "deposit",
"status": "pending",
"paymentMethod": "bank_transfer",
"merchantReference": "order-2026-000045",
"amount": 12550,
"currency": "TRY",
"paymentPageUrl": null,
"metadata": {
"selectedWallet": {
"id": "pay_01H9YE1N5CB3X7S9HESY7Y5XGK",
"iban": "TR120006200119000006672315",
"accountName": "PAY-IN EXTRA TAHSILAT",
"bankName": "Ornek Banka"
}
},
"expiresAt": "2026-07-25T15:30:00.000Z"
}
02 · Acceptance Boundary
HTTP response determines whether the transaction is owned by the platform
Do not interpret status codes solely as technical success. The boundary below determines whether a new request can be created and whether a callback should be expected.
Accepted
In deposits, payment instructions generated; in withdrawals, provider acceptance permanently recorded.
Owned, awaiting outcome
Used only in withdrawals. Do not open a new request; wait for reconciliation via the same paymentId.
Not accepted into normal flow
Apply error.code action in the response. Do not expect a normal outcome callback for this request.
Transport result uncertain
Do not generate a new key. Retry with the same body and the same idempotency key.
Deposit acceptance condition
Bank transfer deposit is accepted only when instructions enabling customer payment are generated.
{
"paymentId": "pay_01H9YE1N5CB3X7S9HESY7Y5XWQ",
"type": "withdrawal",
"status": "pending",
"failureCode": "PROVIDER_RESULT_UNKNOWN",
"failureReason": "Processing outcome requires reconciliation",
"merchantReference": "withdrawal-2026-0088",
"amount": 25000,
"approvedAmount": null,
"currency": "TRY",
"payoutMethod": "havale"
}
If an unaccepted deposit is later verified successful by provider, initial POST decision and replay do not change. Late success callback is only sent after dual approval.
GET /payments/{paymentId} shows succeeded status and approvedAmount only after dual approval completes. GET /payment-requests/{merchantReference} always retains initial API acceptance decision.
A new deposit.succeeded event with new eventId may arrive even if deposit.failed was previously received. Deduplicate by eventId and process monotonically by sequence.
03 · Security
Pass required credentials in every request
Store API keys only in secure backend environments. Never expose them in browser or public source code.
YOUR_API_KEY
İşyeri paneli üzerinden oluşturulan gizli API anahtarıdır.
YOUR_MERCHANT_ID
İsteğin sahibi olan işyerine atanmış benzersiz kimliktir.
UUID v4
Her yeni POST işlemi için üretilmesi gereken benzersiz anahtardır.
It is strongly recommended to define allowed server IP addresses in merchant settings.
04 · Financial Security
Prevent duplicate records during retries
On timeout, retry using the same request payload and the same X-Idempotency-Key.
1. Associate the key with the order record and store permanently.
2. Use identical request body and key upon timeout.
3. Verify uncertain outcomes via merchantReference query.
Do not use the same key with different amounts or customer details.
Do not initiate a new payment via a different channel after a timeout.
Do not deduplicate webhooks based solely on paymentId.
05 · API Reference
Core API Endpoints
Base service address: https://payinextra.com/api/v1
/payments/deposits
Para yatırma talebi oluşturma
Geçerli IBAN veya güvenli ödeme sayfası üretilebildiğinde talebi kabul eder.
/payments/withdrawals
Para çekme talebi oluşturma
Kesin sağlayıcı kabulünde 201, sonucu mutabakat bekleyen sahiplenilmiş talepte 202 döndürür.
/payments/{paymentId}
İşlem durumu sorgulama
Para yatırma, para çekme veya kripto işleminin güncel platform durumunu döndürür.
/payment-requests/{merchantReference}
İşyeri referansı ile sorgulama
İlk API kararını ve idempotent kabul sonucunu işyeri referansıyla doğrular.
/get-balance
Bakiye bilgisi sorgulama
TRY cinsinden kullanılabilir, blokeli ve ödeme işlemine uygun bakiyeleri kuruş bazında döndürür.
Kripto İşlemleri
Yetki gerektirirKripto işlem yetkileri, işyeri hesabı için ayrıca etkinleştirilmelidir.
/payments/crypto-deposits
/payments/crypto-withdrawals
/payments/crypto-payouts
06 · Asynchronous Outcome
Unique and reliable transaction outcomes
Merchant callbacks carry verified lifecycle states. amount reflects initial request; approvedAmount reflects finalized amount.
Deposit Events
deposit.pending
deposit.processing
deposit.succeeded
deposit.corrected
deposit.failed
deposit.refunded
Withdrawal Events
withdrawal.pending
withdrawal.succeeded
withdrawal.failed
withdrawal.cancelled
Payout Events
payout.pending
payout.processing
payout.succeeded
payout.failed
{
"event": "deposit.succeeded",
"eventId": "evt_9f3a7c2b5e81",
"sequence": 2,
"version": 2,
"paymentId": "pay_01H9YE1N5CB3X7S9HESY7Y5XGK",
"type": "deposit",
"status": "succeeded",
"merchantReference": "order-2026-000045",
"amount": 12550,
"approvedAmount": 12550,
"currency": "TRY",
"occurredAt": "2026-07-25T14:42:18.000Z"
}
deposit.corrected is sent only if explicitly subscribed in v2 event filters. approvedAmount is the new canonical amount, previousApprovedAmount is the previous amount.
{
"event": "deposit.corrected",
"eventId": "evt_correction_7b3f491c",
"sequence": 3,
"version": 2,
"paymentId": "pay_01H9YE1N5CB3X7S9HESY7Y5XGK",
"type": "deposit",
"status": "succeeded",
"merchantReference": "order-2026-000045",
"amount": 50000,
"approvedAmount": 50000,
"previousApprovedAmount": 500000,
"correctionId": "01a007f3-51b3-7160-9334-275bcfb359a3",
"correctionVersion": 3,
"correctionSnapshotHash": "0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef",
"currency": "TRY",
"occurredAt": "2026-07-25T15:02:10.000Z"
}
Verification Headers
Webhook Receiver Requirements
- HMAC-SHA256 imzasını değiştirilmemiş ham istek içeriği üzerinden doğrulayın.
- Timestamp alanı için en fazla 300 saniyelik tekrar oynatma penceresi uygulayın.
- eventId değerini benzersiz olarak saklayın ve yinelenen bildirimlere yeniden işlem yapmayın.
aggregate_version_sparse_v1monoton artandır; aradaki sayı boş diye işlemi bekletmeyin.- Olayı ve bakiyeyi veritabanına kaydettikten sonra 2xx dönün. Herhangi bir 2xx nihai ACK kabul edilir.
- Endpoint duplicate modundaysa 409 Conflict dönebilirsiniz; sistem bunu başarılı kabul eder.
07 · Error Handling
Evaluate HTTP status and error.code together
All error responses include X-Request-ID header and requestId field for end-to-end traceability.
| HTTP | Kod (error.code) | Aksiyon | Önerilen İşlem |
|---|---|---|---|
| 400 | MISSING_IDEMPOTENCY_KEY | Düzeltin | Eksik başlığı ekleyin. Aynı ticari talep için önceden üretilmiş anahtarı kullanın. |
| 401 | MISSING_CREDENTIALS · INVALID_MERCHANT · INVALID_API_KEY | Düzeltin | Kimlik bilgilerini doğrulayın; geçerli anahtar olmadan otomatik tekrar yapmayın. |
| 403 | IP_NOT_ALLOWED · FIREWALL_BLOCKED | Düzeltin | Çıkış IP adresini işyeri panelindeki izin listesine ekleyin ve aynı talebi yeniden gönderin. |
| 403 | DEPOSITS_DISABLED · WITHDRAWALS_DISABLED | Düzeltin | İlgili işlem türü işyeri için kapalıdır. Hesap ayarı açılmadan talebi tekrarlamayın. |
| 404 | PAYMENT_NOT_FOUND | Kontrol edin | paymentId veya merchantReference değerini ve isteğin doğru işyeri hesabıyla yapıldığını doğrulayın. |
| 409 | IDEMPOTENCY_KEY_REUSED | Göndermeyin | Anahtar farklı içerikle kullanılmıştır. İlk isteğin gövdesini geri yükleyin; yeni işlem üretmeyin. |
| 409 | DUPLICATE_REFERENCE · DUPLICATE_MERCHANT_REFERENCE | Sorgulayın | Referans mevcut talebe aittir. Yeni kayıt açmak yerine mevcut talebi sorgulayın. |
| 409 | REQUEST_IN_PROGRESS | Aynı anahtar | İlk istek tamamlanmaktadır. Kısa süre bekleyip aynı gövde ve idempotency anahtarıyla tekrar edin. |
| 422 | VALIDATION_ERROR · ERR_PROVIDER_VALIDATION | Düzeltin | Alanları hata ayrıntısına göre düzeltin. Düzeltilmemiş aynı talebi tekrar göndermeyin. |
| 422 | ERR_PROVIDER_REJECTED | Kesin red | Talep kesin olarak reddedilmiştir. Bu işlem için callback beklemeyin. |
| 429 | RATE_LIMITED | Aynı anahtar | Retry-After süresini bekleyip aynı istek gövdesi ve anahtarla yeniden deneyin. |
| 502 | ERR_PROVIDER_RESPONSE_INVALID | İnceleyin | Geçerli ödeme talimatı üretilemedi; talep kabul edilmedi ve callback beklenmemelidir. |
| 503 | ERR_PROVIDER_RESULT_UNKNOWN | Mutabakat | Gönderim sonucu belirsizdir. Yeni anahtar üretmeyin. Aynı anahtar yalnız kanonik sonucu döndürür; yeniden gönderim yapmaz. Talebin durumunu sorgulayın. |
| 503 | ERR_PROVIDER_UNAVAILABLE · ERR_POOL_WITHDRAWAL_CAPACITY_FULL · FINANCIAL_CUTOVER_IN_PROGRESS | Yeni talep | Talep kabul edilmemiştir. Aynı anahtar kanonik 503 sonucunu döndürür ve yeniden gönderim yapmaz. Geçici engel kalktıktan sonra yeni anahtar ve benzersiz merchantReference ile ayrı bir talep oluşturun. |
| 503 | ERR_POOL_NO_ACCOUNT | Yeni çekim | details.retryable=true olsa da aynı anahtar terminal 503 sonucunu tekrarlar. İlk çekimin kabul edilmediğini doğrulayın; uygun hesap oluştuğunda yeni anahtar ve benzersiz merchantReference ile ayrı bir çekim oluşturun. |
| 503 | API_JOURNAL_UNAVAILABLE · API_RESULT_UNAVAILABLE | Aynı anahtar | Güvenli kabul altyapısı geçici olarak hazır değildir. Yeni işlem oluşturmadan tekrar edin. |
| 500 | INTERNAL_ERROR · AUTHENTICATION_ERROR | Aynı anahtar | requestId değerini kaydedin ve aynı talebi kontrollü gecikmeyle yeniden gönderin. |
08 · Final Checklist
Go-live Checklist
Verify all requirements in sandbox before launching in production.
OpenAPI 1.1.1 · revizyon 2026-08-15