نهان سپهراز زیرساخت تا تجربه
API + Webhook Reference

مستندات اتصال به نهان رمز

نهان رمز، محصول پرداخت رمزارزی نهان سپهر است. با یک درخواست server-side لینک پرداخت بسازید، کاربر را به checkout اختصاصی بفرستید و نتیجه نهایی را با webhook امضاشده دریافت کنید.

Landing nahansepehr.irPanel panel.nahansepehr.irCheckout checkout.nahansepehr.ir
Quickstart

مسیر استاندارد اتصال

API Key را از پنل بگیرید، در backend فروشگاه payment session بسازید، سپس مشتری را به `checkout_url` منتقل کنید. پرداخت نهایی فقط با webhook تایید می‌شود.

۱ساخت پذیرنده در پنل
۲صدور API Key
۳ساخت payment session
۴هدایت مشتری به checkout
۵تایید سفارش با webhook
Authentication

احراز هویت API

کلیدهای API فقط برای سیستم‌های بیرونی مثل سایت، اپلیکیشن یا بات هستند. عملیات داخلی پنل با API Key انجام نمی‌شود.

Header پیشنهادی: Authorization: Bearer ck_live_xxx. Header جایگزین: X-API-Key: ck_live_xxx.

محیط از خود کلید تعیین می‌شود: ck_live_... همیشه واقعی و ck_test_... همیشه Sandbox است. body، header یا query نمی‌تواند محیط کلید را تغییر دهد.
Endpoint

ساخت لینک پرداخت

`merchant_order_id` کلید idempotency سفارش شماست. ارسال مجدد همان سفارش با مبلغ و ارز یکسان، invoice تکراری نمی‌سازد.

POSThttps://checkout.nahansepehr.ir/api/v1/payment-sessions
cURL
curl -X POST "https://checkout.nahansepehr.ir/api/v1/payment-sessions" \
  -H "Authorization: Bearer ck_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{
    "merchant_order_id": "ORDER-1001",
    "amount": "25.125",
    "currency": "USD",
    "processing_model": "MANAGED_CUSTODIAL"
  }'

پاسخ موفق

Response · JSON
{
  "id": "cginv_03d37a86680c66f93e300467f7db648f",
  "invoice_id": "cginv_03d37a86680c66f93e300467f7db648f",
  "merchant_order_id": "ORDER-1001",
  "processing_model": "MANAGED_CUSTODIAL",
  "environment": "LIVE",
  "livemode": true,
  "status": "WAITING_PAYMENT",
  "checkout_url": "https://checkout.nahansepehr.ir/checkout/cginv_03d37a86680c66f93e300467f7db648f",
  "invoice": {
    "asset": "USDT",
    "network": "BEP20",
    "fiat_amount": "25.125",
    "fiat_currency": "USD",
    "token_amount": "25.125000",
    "token_units": "25125000000000000000",
    "conversion": {
      "snapshot_id": "rate_01J...",
      "provider": "BRS",
      "from_currency": "USD",
      "to_currency": "USDT",
      "input_amount": "25.125",
      "output_amount": "25.125",
      "conversion_rate": "1",
      "quoted_at": "2026-08-01T10:00:00.000Z",
      "rate_fetched_at": "2026-08-01T09:58:00.000Z"
    },
    "receive_address": "0xa6a17f98e6663309fed38bdb44f17da731e4ddda",
    "qr_payload": "ethereum:0x55d398326f99059ff775485246999027b3197955@56/transfer?...",
    "expires_at": "2026-07-09T10:30:00.000Z"
  }
}

فیلدهای ضروری

merchant_order_id و amount الزامی هستند. نوع دریافت با processing_model و یکی از مقادیر MANAGED_CUSTODIAL یا NON_CUSTODIAL مشخص می‌شود؛ حذف این فیلد برای سازگاری، دریافت مدیریت‌شده را انتخاب می‌کند.

قوانین مالی

CONFIRMED وضعیت نهایی پرداخت است و پس از آن به وضعیت قبلی برنمی‌گردد.

فیلد اختیاری return_url فعال است. فقط URLهای https:// با hostname یکسان با وب‌سایت ثبت‌شده پذیرنده پذیرفته می‌شوند؛ دکمه بازگشت دستی است و تایید سفارش همچنان فقط با webhook امضاشده انجام می‌شود.
Exchange Rates

دریافت ریال، تومان و سایر ارزها

مبلغ سفارش می‌تواند با ارز مبدأ پشتیبانی‌شده ثبت شود؛ نهان رمز نرخ معتبر همان فاکتور را ثبت می‌کند و مبلغ پرداختی را فعلاً فقط به USDT روی BEP20 تبدیل می‌کند.

واحدهای ایران

IRR یعنی ریال و IRT یعنی تومان. نمونه: یک میلیون تومان باید با مقدار 1000000 در amount و مقدار IRT در currency ارسال شود.

نرخ قفل‌شده فاکتور

هر فاکتور نرخ تبدیل و مبلغ USDT خودش را نگه می‌دارد. تغییر بعدی بازار مبلغ همان فاکتور را تغییر نمی‌دهد و اگر نرخ قابل‌اعتماد در دسترس نباشد، فاکتور ساخته نمی‌شود.

GET/api/v1/rates
Rates · cURL
curl "https://checkout.nahansepehr.ir/api/v1/rates" \
  -H "Authorization: Bearer ck_live_xxx"

فهرست پاسخ علاوه بر نرخ‌ها، فیلد supported_for_usdt دارد. فقط مواردی که این مقدارشان true است برای ساخت فاکتور قابل استفاده‌اند.

POST/api/v1/rates/convert
Conversion preview · cURL
curl -X POST "https://checkout.nahansepehr.ir/api/v1/rates/convert" \
  -H "Authorization: Bearer ck_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{
    "amount": "10000000",
    "from_currency": "IRR",
    "to_currency": "USDT"
  }'

ساخت فاکتور با مبلغ ریالی

IRR payment session · cURL
curl -X POST "https://checkout.nahansepehr.ir/api/v1/payment-sessions" \
  -H "Authorization: Bearer ck_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{
    "merchant_order_id": "ORDER-IRR-1002",
    "amount": "10000000",
    "currency": "IRR"
  }'
خروجی تبدیل در این نسخه فقط USDT است. USD و USDT برای سازگاری با قرارداد قبلی همیشه یک‌به‌یک هستند. تبدیل سایر ارزها رو به بالا تا دقت micro-USDT گرد می‌شود و سپس suffix اختصاصی فاکتور اضافه می‌گردد؛ مبلغ لازم برای پرداخت را از invoice.token_amount بخوانید، نه از محاسبه سمت فروشگاه.
Sandbox

تست کامل بدون پرداخت واقعی

با Test API Key همان قرارداد ساخت، خواندن، فهرست و webhook را بدون آدرس پرداخت واقعی، تراکنش شبکه یا اثر مالی آزمایش کنید.

بدون اثر مالی

پرداخت‌های Sandbox هیچ دارایی واقعی جابه‌جا نمی‌کنند، موجودی پذیرنده را تغییر نمی‌دهند و در گزارش‌های محیط Live نمایش داده نمی‌شوند.

کلید و webhook مستقل

کلید ck_test_...، URL وبهوک و HMAC Secret آن از Live جداست. داده‌های آزمایشی بعد از ۳۰ روز، طی batchهای محدود نگهداری پاک می‌شوند.

ساخت فاکتور آزمایشی

Sandbox create · cURL
curl -X POST "https://checkout.nahansepehr.ir/api/v1/payment-sessions" \
  -H "Authorization: Bearer ck_test_xxx" \
  -H "Content-Type: application/json" \
  -d '{
    "merchant_order_id": "SANDBOX-ORDER-1001",
    "amount": "25.125",
    "currency": "USD"
  }'

شبیه‌سازی وضعیت واقعی

Sandbox simulate · cURL
curl -X POST "https://checkout.nahansepehr.ir/api/v1/sandbox/payment-sessions/PAYMENT_SESSION_ID/simulate" \
  -H "Authorization: Bearer ck_test_xxx" \
  -H "Content-Type: application/json" \
  -d '{ "status": "CONFIRMED" }'

وضعیت‌های قابل آزمایش: WAITING_PAYMENT، REVIEW_REQUIRED، CONFIRMED، EXPIRED و FAILED. پس از CONFIRMED نتیجه نهایی است؛ اگر وضعیت درخواستی با نتیجه فعلی سازگار نباشد، پاسخ HTTP 409 دریافت می‌کنید و باید یک فاکتور آزمایشی تازه بسازید.

همه responseها و webhookهای تست environment=SANDBOX و livemode=false دارند. سیستم فروشگاه باید پیش از fulfillment واقعی، علاوه بر امضا حتماً livemode === true را کنترل کند. صفحه Checkout آزمایشی QR و آدرس قابل پرداخت نمایش نمی‌دهد و دکمه‌های موفق، نیازمند بررسی، منقضی و ناموفق را برای اجرای سناریو و ارسال وب‌هوک دارد؛ Test API Key هرگز وارد مرورگر نمی‌شود.

آزمایش پرداخت مستقیم

برای آزمایش پرداخت مستقیم همان Test API Key را استفاده کنید و processing_model=NON_CUSTODIAL بفرستید. به کیف پول واقعی، فعال‌سازی مقصد یا شارژ اعتبار خدمات نیاز نیست.

ساخت پرداخت مستقیم آزمایشی · cURL
curl -X POST "https://checkout.nahansepehr.ir/api/v1/payment-sessions" \
  -H "Authorization: Bearer ck_test_xxx" \
  -H "Content-Type: application/json" \
  -d '{
    "merchant_order_id": "DIRECT-SANDBOX-1001",
    "amount": "25.125",
    "currency": "USDT",
    "processing_model": "NON_CUSTODIAL",
    "network": "BSC",
    "asset": "USDT"
  }'
شبیه‌سازی پرداخت مستقیم · cURL
curl -X POST "https://checkout.nahansepehr.ir/api/v1/sandbox/payment-sessions/PAYMENT_SESSION_ID/simulate" \
  -H "Authorization: Bearer ck_test_xxx" \
  -H "Content-Type: application/json" \
  -d '{ "state": "CONFIRMED" }'
CONFIRMEDاتصال کیف پول، آماده‌سازی انتقال، رزرو نمایشی کارمزد، ارسال، مشاهده، تأییدها و موفقیت را به‌ترتیب شبیه‌سازی می‌کند.
REVIEW_REQUIREDپرداخت مشاهده‌شده را در وضعیت نیازمند بررسی قرار می‌دهد.
TX_REVERTEDناموفق‌شدن تراکنش پس از ارسال آزمایشی را نشان می‌دهد.
REORG_INCIDENTابتدا تأیید و سپس رخداد بازآرایی شبکه را شبیه‌سازی می‌کند.
LOW_CREDITکسری اعتبار خدمات را بدون تغییر موجودی واقعی نشان می‌دهد؛ در Checkout می‌توانید شارژ ۱۰ USDT را نیز شبیه‌سازی کنید.
EXPIRED / FAILEDپایان مهلت یا خطای کنترل‌شده را بدون ساخت تراکنش نمایش می‌دهد.
مقصد، payer، tx و سند شبکه در محیط آزمایشی پرداخت مستقیم، شناسه‌های واضح آزمایشی هستند و روی BscScan یا کیف پول قابل استفاده نیستند. برای هر نتیجه نهایی، Payment Session تازه‌ای با merchant_order_id جدید بسازید.
Query API

خواندن وضعیت و فهرست پرداخت‌ها

هر دو مسیر با همان API Key پذیرنده کار می‌کنند و فقط داده همان پذیرنده را برمی‌گردانند.

GET/api/v1/payment-sessions/:id
GET/api/v1/payment-sessions?limit=20&status=CONFIRMED&cursor=...

فهرست با cursor پایدار صفحه‌بندی می‌شود؛ limit بین ۱ تا ۱۰۰ است و cursor بعدی در pagination.next_cursor می‌آید. همه خطاهای v1 شکل ثابت error.code / error.message / error.request_id و header برابر X-Request-ID دارند.

Statuses

وضعیت‌های پرداخت

وضعیت‌ها را مستقیم در سیستم خود نگاشت کنید و سفارش را فقط با `CONFIRMED` پرداخت‌شده بدانید.

CREATINGرزرو شده و در حال ساخت invoice
CREATE_FAILEDساخت invoice ناموفق بوده و با همان order قابل retry است
WAITING_PAYMENTکاربر می‌تواند در صفحه checkout پرداخت کند
REVIEW_REQUIREDنیازمند بررسی عملیاتی، مثل اختلاف مبلغ یا پرداخت بعد از انقضا
CONFIRMEDپرداخت تایید شده است؛ دریافت تکراری رویداد نباید سفارش را دوباره اعمال کند
EXPIREDمهلت پرداخت تمام شده است
FAILEDپرداخت ناموفق یا بسته شده است
پرداخت مستقیم نهان

دریافت مستقیم پرداخت در کیف پول پذیرنده

پرداخت مستقیم نهان برای پذیرندگانی است که می‌خواهند مبلغ فروش مستقیماً در کیف پول خودشان دریافت شود. این روش برای درگاه‌ها در دسترس است و پس از ثبت کیف پول دریافت و تأمین اعتبار خدمات، هنگام ساخت Payment Session انتخاب می‌شود.

تسویه مستقیم

در مدل NON_CUSTODIAL مشتری USDT را روی شبکه BSC مستقیماً به کیف پول تأییدشده پذیرنده می‌فرستد؛ بنابراین برای اصل مبلغ فروش، موجودی قابل‌برداشت در نهان ایجاد نمی‌شود.

پرداخت مانند یک انتقال عادی

مشتری مبلغ دقیق فاکتور را با هر کیف پول سازگار با USDT/BEP20 به مقصد نمایش‌داده‌شده می‌فرستد. نهان انتقال را خودکار تشخیص می‌دهد و نتیجه را در همان فاکتور و Webhook اعلام می‌کند.

کارمزد پایه پرداخت مستقیم برابر ۱٫۲۰٪ با حداقل ۰٫۲۰ USDT است و از «اعتبار خدمات پرداخت مستقیم» پذیرنده پرداخت می‌شود. کارمزد Gas را مشتری مستقیماً به شبکه می‌پردازد و نهان برای اصل پرداخت، کارمزد برداشت یا تسویه دریافت نمی‌کند.

مدیریت پرداخت مستقیم در پنل

1در صفحه «پرداخت جدید»، بین دریافت مدیریت‌شده و پرداخت مستقیم نهان انتخاب کنید. اگر پرداخت مستقیم هنوز آماده نباشد، همان‌جا مرحله ناقص حساب یا کیف پول نمایش داده می‌شود.
2در «پرداخت‌ها ← اعتبار خدمات»، موجودی خریداری‌شده و هدیه، مبلغ رزروشده، مصرف ماه و پوشش تقریبی پرداخت‌ها را ببینید.
3در فهرست پرداخت‌ها فیلتر «پرداخت مستقیم نهان» را انتخاب کنید و در جزئیات هر پرداخت، فرستنده، هش تراکنش، تعداد تأیید و سند شبکه را بررسی کنید.
4برای تطبیق حسابداری، صورتحساب‌ها و خروجی CSV را از «تسویه‌ها ← گردش اعتبار خدمات» دریافت کنید.

اعتبار خدمات پرداخت مستقیم چگونه کار می‌کند؟

شارژ آزاد و بدون انقضا

اعتبار خریداری‌شده از ۱۰ USDT قابل شارژ است و تاریخ انقضا ندارد. این اعتبار فقط برای کارمزد پرداخت مستقیم و امکانات حرفه‌ای اختیاری استفاده می‌شود و با موجودی فروش شما تفاوت دارد.

بازپرداخت اعتبار خریداری‌شده

بخش استفاده‌نشده اعتبار خریداری‌شده قابل بازپرداخت است. پیش از تأیید، مبلغ ناخالص، برآورد هزینه شبکه و مبلغ دریافتی نمایش داده می‌شود؛ پس از انجام تراکنش نیز هزینه واقعی شبکه در رسید ثبت خواهد شد.

روش شارژ اعتبار خدمات

1در «پرداخت‌ها ← اعتبار خدمات»، «افزایش اعتبار» را بزنید.
2یکی از مبالغ پیشنهادی یا مبلغ دلخواه حداقل ۱۰ USDT را وارد و خلاصه صورتحساب را بررسی کنید. این مبالغ بسته یا اشتراک نیستند.
3صورتحساب را در Checkout استاندارد نهان پرداخت کنید. پس از تأیید شبکه، اعتبار به‌صورت خودکار ثبت می‌شود و نیازی به واردکردن هش تراکنش نیست.
فقط شبکه و مبلغ نمایش‌داده‌شده در Checkout را استفاده کنید. وضعیت صورتحساب‌های باز، امکان ادامه پرداخت و اسناد کسر کارمزد در «تسویه‌ها ← گردش اعتبار خدمات» در دسترس است.

هنگام ساخت فاکتور، کارمزد همان پرداخت از اعتبار خدمات رزرو می‌شود. اگر اعتبار کافی نباشد فاکتور صادر نمی‌شود؛ در نتیجه مشتری پس از بازکردن Checkout با خطای اعتبار پذیرنده روبه‌رو نخواهد شد.

اعتبار هدیه جداگانه نمایش داده می‌شود، قابل برداشت نیست و پیش از اعتبار خریداری‌شده مصرف می‌شود. تاریخ انقضای احتمالی آن هنگام تخصیص کمپین اعلام خواهد شد.

راه‌اندازی کیف پول دریافت

1از «تنظیمات درگاه»، بخش «پرداخت مستقیم نهان»، QR اتصال را بسازید و با Trust Wallet اسکن کنید.
2پیام مالکیت را در شبکه BNB Smart Chain امضا کنید. این پیام هیچ تراکنش، Gas یا دسترسی برداشت ایجاد نمی‌کند.
3فعال‌سازی را در پنل با Passkey یا کد Authenticator تأیید کنید.
4پس از فعال‌شدن، پرداخت‌های مستقیم جدید به این مقصد متصل می‌شوند. تعویض کیف پول روی فاکتورهای قبلی اثر ندارد.

نهان فقط آدرس عمومی و مدرک تأیید را نگهداری می‌کند. عبارت بازیابی، کلید خصوصی و مجوز خرج‌کردن هرگز در این فرایند درخواست نمی‌شود. اتصال Trust Wallet نیز مستقیماً از مسیر داخلی نهان انجام می‌شود و به WalletConnect وابسته نیست.

مشتری چگونه فاکتور پرداخت مستقیم را پرداخت می‌کند؟

1مشتری checkout_url همان Payment Session را باز می‌کند و مبلغ، شبکه و کیف پول دریافت پذیرنده را می‌بیند.
2QR آدرس را اسکن یا آدرس را کپی می‌کند و مبلغ اعشاری نمایش‌داده‌شده را بدون گردکردن می‌فرستد.
3نیازی به اتصال کیف پول، امضای پیام یا ثبت هش تراکنش نیست؛ نهان پرداخت را از روی مقصد و مبلغ دقیق پیدا می‌کند.
4صفحه تا پایان تأییدهای شبکه به‌روز می‌شود. وضعیت نهایی را از Payment Session یا Webhook بخوانید و صرفاً بازگشت مشتری به فروشگاه را نشانه پرداخت موفق ندانید.
مبلغ هر فاکتور پرداخت مستقیم چند رقم اعشاری اختصاصی دارد. مشتری باید همان مبلغ را دقیق ارسال کند؛ کم‌پرداخت، بیش‌پرداخت یا پرداخت پس از پایان مهلت ممکن است نیازمند بررسی شود.

نمونه درخواست

ساخت پرداخت مستقیم · cURL
curl -X POST "https://checkout.nahansepehr.ir/api/v1/payment-sessions" \
  -H "Authorization: Bearer ck_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{
    "merchant_order_id": "ORDER-DIRECT-1001",
    "amount": "100.00",
    "currency": "USDT",
    "processing_model": "NON_CUSTODIAL",
    "network": "BSC",
    "asset": "USDT"
  }'

نمونه پاسخ

پاسخ پرداخت مستقیم · JSON
{
  "payment_session_id": "8df6d6d7-0a78-4a83-a062-a7911478142e",
  "invoice_id": "dir_7db7d4bd26e8428e989d6387431fd205",
  "merchant_order_id": "ORDER-DIRECT-1001",
  "processing_model": "NON_CUSTODIAL",
  "product": "NAHAN_DIRECT",
  "environment": "LIVE",
  "livemode": true,
  "status": "WAITING_PAYMENT",
  "gross_token_units": "100000000000000000000",
  "merchant_destination": "0x24e8ed7e1602b5a0b893e7b1dfa25027bc51acdf",
  "service_fee": {
    "mode": "ESTIMATE",
    "policy_version": 1,
    "rate_basis_points": 120,
    "minimum_fee_token_units": "200000000000000000",
    "estimated_fee_token_units": "1200000000000000000"
  },
  "checkout_url": "https://checkout.nahansepehr.ir/checkout/dir_7db7d4bd26e8428e989d6387431fd205"
}

همیشه آدرس دریافت، مبلغ و کارمزد برآوردی را از پاسخ همان Payment Session بخوانید و آدرس کیف پول را جداگانه در سامانه خودتان ذخیره نکنید. هر فاکتور مقصد ثبت‌شده‌ی خودش را حفظ می‌کند.

ارسال دوباره‌ی همان merchant_order_id با همان مبلغ و مدل، همان فاکتور را برمی‌گرداند. استفاده از همان شناسه با مبلغ متفاوت یا مدل Managed با خطای تعارض پاسخ داده می‌شود.

پرداخت مستقیم در نسخه نخست فقط برای USDT روی BNB Smart Chain در دسترس است. اگر دسترسی حساب فعال نباشد direct_not_enabled، اگر کیف پول دریافت آماده نباشد direct_wallet_required و هنگام توقف موقت صدور فاکتور direct_issuance_paused دریافت می‌کنید. ساخت و پردازش پرداخت مدیریت‌شده در توقف محدود پرداخت مستقیم ادامه دارد.
Pricing

مدل‌های پردازش و کارمزد

هنگام ساخت Payment Session روش دریافت را مشخص کنید. هر دو روش برای درگاه‌ها در دسترس‌اند؛ پرداخت مستقیم پیش از صدور اولین فاکتور به کیف پول دریافت تأییدشده و اعتبار خدمات کافی نیاز دارد.

دریافت مدیریت‌شده

کارمزد پردازش برابر مقدار بیشتر بین ۰٫۹۵٪ مبلغ و ۰٫۱۵ USDT است. حداقل مبلغ invoice برای pricing برابر ۱ USDT است و هزینه شبکه تسویه جدا محاسبه می‌شود.

پرداخت مستقیم نهان

کارمزد پردازش برابر مقدار بیشتر بین ۱٫۲۰٪ مبلغ و ۰٫۲۰ USDT است. این مبلغ از اعتبار خدمات پرداخت مستقیم کسر می‌شود و اصل پرداخت مستقیماً به کیف پول پذیرنده می‌رسد.

تخفیف حجمی دریافت مدیریت‌شده براساس حجم ماه قبل اعمال می‌شود: کمتر از ۵۰٬۰۰۰ دلار ۰٫۹۵٪، از ۵۰٬۰۰۰ تا ۲۵۰٬۰۰۰ دلار ۰٫۸۰٪، از ۲۵۰٬۰۰۰ تا ۱ میلیون دلار ۰٫۶۵٪ و بالاتر از آن براساس قرارداد اختصاصی.

تخفیف حجمی پرداخت مستقیم فقط از حجم پرداخت مستقیم ماه قبل محاسبه می‌شود: کمتر از ۵۰٬۰۰۰ دلار ۱٫۲۰٪، از ۵۰٬۰۰۰ تا ۲۵۰٬۰۰۰ دلار ۱٫۰۰٪، از ۲۵۰٬۰۰۰ تا ۱ میلیون دلار ۰٫۸۰٪ و بالاتر از آن براساس قرارداد اختصاصی. حداقل کارمزد هر پرداخت در این نرخ‌ها ۰٫۲۰ USDT است.

نرخ فعال، حجم محاسبه‌شده ماه و نرخ احتمالی ماه بعد در داشبورد پذیرنده نمایش داده می‌شود. نرخ ماه بعد پس از پایان ماه جاری قطعی خواهد شد.

مقدار processing_model را همراه سفارش ذخیره کنید. مبالغ processing_fee_token_units و merchant_net_token_units با واحد صحیح توکن و ۱۸ رقم اعشار ارسال می‌شوند.

در دریافت مدیریت‌شده فقط هزینه واقعی شبکه مربوط به انتقال وجه به کیف پول پذیرنده محاسبه می‌شود. هزینه‌های داخلی جابه‌جایی دارایی در نهان از موجودی پذیرنده کسر نمی‌شوند.

صورتحساب برداشت پیش از تأیید، مبلغ دریافتی، کارمزد خدمت، برآورد هزینه شبکه و حداکثر مبلغ قابل‌کسر را نمایش می‌دهد. پس از انجام تراکنش فقط هزینه واقعی شبکه نهایی می‌شود و مبلغ ذخیره‌نشده به موجودی برمی‌گردد.

برداشت دستی سه مرحله دارد: ورود مبلغ و انتخاب روش امنیتی، بررسی صورتحساب، و تأیید نهایی با Passkey یا Authenticator. مقصد، مبلغ دریافتی و همه هزینه‌ها پیش از تأیید به‌صورت یکجا نمایش داده می‌شوند.

اولین برداشت دستی و اولین برداشت زمان‌بندی‌شده در هر روز UTC کارمزد خدمت ندارد. برداشت‌های بعدی همان نوع مشمول max(0.10%, 0.30 USDT) هستند. هزینه شبکه جداگانه و براساس تراکنش واقعی محاسبه می‌شود.

Settlement

پیگیری برداشت در پنل

هر درخواست برداشت از زمان ثبت تا تأیید شبکه در صفحه تسویه قابل پیگیری است و وضعیت آن به‌صورت خودکار به‌روز می‌شود.

برداشت دستی

پس از تأیید صورتحساب و روش امنیتی، درخواست برای ارسال ثبت می‌شود. هش تراکنش و تعداد تأییدهای شبکه در همان ردیف برداشت نمایش داده خواهد شد.

اختلال موقت

اگر سرویس شبکه یا قیمت‌گذاری موقتاً در دسترس نباشد، برداشت جدید ثبت نمی‌شود و موجودی شما تغییر نمی‌کند. پس از برطرف‌شدن اختلال می‌توانید دوباره صورتحساب بگیرید.

مسیرهای تسویه در /api/merchant/settlement/* فقط توسط خود پنل استفاده می‌شوند و بخشی از API اتصال فروشگاه نیستند.
Transaction Authorization

امنیت برداشت در پنل پذیرنده

کیف پول احرازشده ریشه حساب است و برای فعال‌شدن برداشت، کاربر باید حداقل یک Passkey یا Authenticator نیز فعال کند. برداشت عادی توسط خود پذیرنده تأیید می‌شود، نه Owner پلتفرم.

Passkey؛ روش پیشنهادی

با Passkey می‌توانید برداشت را با اثرانگشت، تشخیص چهره یا قفل امن دستگاه تأیید کنید. تأیید فقط برای همان مبلغ، مقصد و درخواست معتبر است.

Authenticator؛ روش جایگزین

می‌توانید حداکثر پنج برنامه Authenticator نام‌گذاری‌شده ثبت کنید و هرکدام را جداگانه از صفحه امنیت غیرفعال کنید.

با فعال‌سازی Authenticator، ده Recovery Code یک‌بارمصرف فقط یک بار نمایش داده می‌شود. آن‌ها را خارج از حساب خود و در محل امن نگه دارید؛ Recovery Code برای بازیابی Authenticator است و به‌تنهایی مجوز برداشت نیست.

مسیرهای /api/security/* و /api/merchant/settlement/* API داخلی پنل هستند. فروشگاه نباید آن‌ها را به‌عنوان قرارداد integration مصرف کند.
Webhooks

دریافت نتیجه پرداخت

URL باید HTTPS باشد. پیام‌ها با secret اختصاصی پذیرنده امضا می‌شوند و deliveryها در صورت خطا با backoff دوباره ارسال می‌شوند.

X-Checkout-Eventنوع رویداد
X-Checkout-Deliveryشناسه یکتای ارسال
X-Checkout-Timestampزمان ارسال
X-Checkout-Environmentlive یا sandbox
X-Checkout-Signatureامضای HMAC

رویدادها

payment.waitingpayment.confirmedpayment.review_requiredpayment.expiredpayment.failedpayment.create_failedwebhook.test

نمونه payload

Webhook payload · JSON
{
  "id": "evt_8c0f1f",
  "event": "payment.confirmed",
  "created_at": "2026-07-09T10:12:30.000Z",
  "environment": "LIVE",
  "livemode": true,
  "payment": {
    "id": "5f8b6b8e-18df-48c0-8b64-6dddb8a1f6de",
    "merchant_order_id": "ORDER-1001",
    "invoice_id": "cginv_03d37a86680c66f93e300467f7db648f",
    "status": "CONFIRMED",
    "amount": "25.125",
    "currency": "USD",
    "asset": "USDT",
    "network": "BEP20",
    "token_amount": "25.125000",
    "receive_address": "0xa6a17f98e6663309fed38bdb44f17da731e4ddda",
    "tx_hash": "0x...",
    "checkout_url": "https://checkout.nahansepehr.ir/checkout/cginv_03d37a86680c66f93e300467f7db648f",
    "confirmed_at": "2026-07-09T10:12:20.000Z",
    "expires_at": "2026-07-09T10:30:00.000Z",
    "processing_model": "MANAGED_CUSTODIAL",
    "pricing_mode": "SHADOW",
    "pricing_policy_version": 1,
    "processing_fee_token_units": "238687500000000000",
    "merchant_net_token_units": "25125000000000000000",
    "environment": "LIVE",
    "livemode": true
  }
}

در رویداد تأییدشده‌ی پرداخت مستقیم، مقدار processing_model برابر NON_CUSTODIAL است. برای تطبیق مالی، فیلدهای مقصد پذیرنده، فرستنده، هش و شماره log تراکنش، تعداد تأییدها، مبلغ دریافتی پذیرنده و جزئیات کارمزد کسرشده از اعتبار خدمات را ذخیره کنید.

رویداد تست اتصال

وقتی در پنل دکمه تست ارسال را می‌زنید، رویداد webhook.test فرستاده می‌شود. این رویداد سفارش واقعی نیست و فیلد payment ندارد؛ بعد از بررسی امضا باید بدون تغییر وضعیت سفارش، پاسخ 2xx بدهید.

Test event · JSON
{
  "id": "9b2b0f3e-0b6b-4d1a-9fb5-4bbf2b6f34fa",
  "event": "webhook.test",
  "created_at": "2026-07-09T10:12:30.000Z",
  "environment": "LIVE",
  "livemode": true,
  "message": "این پیام برای تست اتصال webhook نهان رمز ارسال شده است."
}
HMAC

بررسی امضای webhook

امضا روی raw body ساخته می‌شود. قبل از parse یا تغییر payload، متن خام درخواست را برای HMAC نگه دارید.

Node.js

Node.js
import crypto from "crypto";

function verifyWebhook(rawBody, signature, secret) {
  const expected = "sha256=" + crypto
    .createHmac("sha256", secret)
    .update(rawBody)
    .digest("hex");

  return crypto.timingSafeEqual(
    Buffer.from(signature),
    Buffer.from(expected)
  );
}

PHP

PHP
function verifyWebhook(string $rawBody, string $signature, string $secret): bool {
    $expected = 'sha256=' . hash_hmac('sha256', $rawBody, $secret);
    return hash_equals($expected, $signature);
}
برای webhook.test فقط امضا و دسترسی endpoint را چک کنید و سفارش را جستجو نکنید. برای رویدادهای پرداخت، فقط بعد از ذخیره امن رویداد پاسخ 2xx بدهید و برای جلوگیری از پردازش تکراری، X-Checkout-Delivery یا payment.invoice_id را idempotent کنید.
Checklist

چک‌لیست production

این موارد حداقل الزامات اتصال امن فروشگاه به درگاه هستند.

API Key را فقط در backend نگه دارید.
پیش از fulfillment واقعی، livemode=true را علاوه بر امضای webhook کنترل کنید.
payment session را سمت سرور بسازید، نه در مرورگر مشتری.
کاربر را فقط به checkout_url برگردانید.
return_url را جایگزین webhook برای تایید سفارش نکنید.
pricing_mode را ذخیره کنید و فقط CHARGE را کسر مالی بدانید.
وضعیت سفارش را فقط با webhook امضاشده تغییر دهید.
برای REVIEW_REQUIRED سفارش را پرداخت‌شده حساب نکنید.
ارسال اشتباه شبکه BEP20 ممکن است برگشت‌پذیر نباشد؛ هشدار checkout را حذف نکنید.