क्रिप्टो पेमेंट API इंटीग्रेशन: इनवॉइस, सिग्नेचर और Webhooks
डेवलपर्स के लिए व्यावहारिक गाइड: इनवॉइस बनाने के लिए एक साइन की हुई रिक्वेस्ट, स्टेटस पाने के लिए एक webhook endpoint, और वे सुरक्षा बारीकियाँ जो इसे भरोसेमंद बनाती हैं।

क्रिप्टो पेमेंट API इंटीग्रेशन के लिए दो चीज़ें चाहिए: सर्वर-साइड से भेजी गई एक रिक्वेस्ट जो हर ऑर्डर के लिए इनवॉइस बनाए और चेकआउट URL लौटाए, और एक webhook endpoint जो पेमेंट ऑन-चेन डिटेक्ट और कन्फ़र्म होने पर साइन किए गए स्टेटस अपडेट प्राप्त करे। mistKET में दोनों सीधे HTTPS और JSON हैं, HMAC-SHA256 से साइन किए हुए — किसी SDK की ज़रूरत नहीं।
यह गाइड कोड के साथ पूरा फ़्लो समझाती है, फिर उन सुरक्षा और भरोसेमंदी की बारीकियों को कवर करती है जो डेमो को प्रोडक्शन से अलग करती हैं।
एक नज़र में आर्किटेक्चर
हर क्रिप्टो पेमेंट API इंटीग्रेशन एक ही पाँच-स्टेप लूप पर चलता है:
- ऑर्डर बनता है — आपका बैकएंड अमाउंट, करेंसी, ऑर्डर ID और callback URL के साथ
POST /api/v1/invoicesकॉल करता है। - रीडायरेक्ट — आप ग्राहक को मिले हुए
checkout_urlपर भेजते हैं। - पेमेंट — ग्राहक होस्टेड पेज पर नेटवर्क चुनकर पेमेंट करता है; इनवॉइस की अवधि तक रेट लॉक रहता है।
- Webhook — mistKET आपके callback URL पर
invoice.paid,invoice.confirmedया कोई अपवाद इवेंट POST करता है। - फ़ुलफ़िलमेंट — आप सिग्नेचर वेरिफ़ाई करते हैं, ऑर्डर को पेड मार्क करते हैं और डिलीवर करते हैं।
अकाउंट मंज़ूर होने के बाद आपकी API key, API secret और webhook secret मर्चेंट पैनल में जारी होते हैं। पूरा रेफ़रेंस पैनल में API सेक्शन के तहत है।
स्टेप 1: इनवॉइस रिक्वेस्ट साइन करें और भेजें
हर API रिक्वेस्ट में तीन हेडर होते हैं। सिग्नेचर आपके API secret से स्ट्रिंग {timestamp}.{raw body} का hex HMAC-SHA256 है:
POST /api/v1/invoices
X-Api-Key: mp_live_…
X-Api-Timestamp: 1760000000
X-Api-Signature: hex(hmac_sha256("{ts}.{body}", secret))
{
"amount": "184.50",
"currency": "USD",
"order_id": "2041",
"callback_url": "https://yourstore.com/webhooks/mistket"
} एक न्यूनतम PHP वर्ज़न ऐसा दिखता है:
$body = json_encode([
'amount' => '184.50', 'currency' => 'USD',
'order_id' => '2041',
'callback_url' => 'https://yourstore.com/webhooks/mistket',
]);
$ts = (string) time();
$sig = hash_hmac('sha256', $ts . '.' . $body, $apiSecret);
// send $body with X-Api-Key, X-Api-Timestamp, X-Api-Signature ठीक वही बाइट्स साइन करें जो आप भेजते हैं। साइन करने के बाद JSON को दोबारा एनकोड करना (अलग स्पेसिंग या की का क्रम) सिग्नेचर एरर की सबसे बड़ी वजह है।
स्टेप 2: होस्टेड चेकआउट पर रीडायरेक्ट करें
सफल कॉल 201 Created लौटाती है जिसमें इनवॉइस UUID, उसका स्टेटस (new) और एक checkout_url होता है। UUID को अपने ऑर्डर के साथ सेव करें और ग्राहक को रीडायरेक्ट करें। होस्टेड पेज सटीक रकम, QR कोड, काउंटडाउन और लाइव स्टेटस दिखाता है, और मोबाइल पर भी काम करता है। ग्राहक वहीं नेटवर्क चुनते हैं — TRON, BNB Smart Chain, Ethereum या Arbitrum पर USDT, साथ में TRX, BNB और ETH — जब तक आप API कॉल में नेटवर्क फ़िक्स न करें।
इनवॉइस बनाने के अलावा API से आप उन्हें लिस्ट, फ़ेच और कैंसल भी कर सकते हैं, जो कार्ट बदलने या ऑर्डर अधूरा छूटने पर काम आता है।
स्टेप 3: webhooks प्राप्त करें और वेरिफ़ाई करें
स्टेटस बदलने पर mistKET आपके callback URL पर इन हेडर्स के साथ JSON POST करता है:
| हेडर | उद्देश्य |
|---|---|
X-Mistket-Event | इवेंट का नाम, जैसे invoice.confirmed |
X-Mistket-Timestamp | सिग्नेचर में इस्तेमाल हुआ Unix time |
X-Mistket-Signature | sha256= + आपके webhook secret से {timestamp}.{raw body} का HMAC-SHA256 |
X-Mistket-Delivery | डिलीवरी ID, लॉगिंग के लिए उपयोगी |
PHP में वेरिफ़िकेशन:
$raw = file_get_contents('php://input');
$ts = $_SERVER['HTTP_X_MISTKET_TIMESTAMP'] ?? '';
$got = $_SERVER['HTTP_X_MISTKET_SIGNATURE'] ?? '';
$exp = 'sha256=' . hash_hmac('sha256', $ts . '.' . $raw, $webhookSecret);
if (!hash_equals($exp, $got) || abs(time() - (int) $ts) > 300) {
http_response_code(401); exit;
}
$event = json_decode($raw, true); Constant-time तुलना इस्तेमाल करें (PHP में hash_equals, Python में hmac.compare_digest, Node.js में crypto.timingSafeEqual) और रीप्ले रोकने के लिए पुराने timestamp रिजेक्ट करें। इस तकनीक की पृष्ठभूमि के लिए देखें RFC 2104 (HMAC)।
Webhook payload का उदाहरण
कन्फ़र्म पेमेंट एक छोटे JSON डॉक्यूमेंट के रूप में आता है। आप सबसे ज़्यादा इवेंट, अपना ऑर्डर ID, स्टेटस और अपेक्षित व प्राप्त रकम वाले फ़ील्ड इस्तेमाल करेंगे:
POST https://yourstore.com/webhooks/mistket
X-Mistket-Event: invoice.confirmed
X-Mistket-Signature: sha256=…
{ "event": "invoice.confirmed", "data": {
"order_id": "2041", "status": "confirmed",
"pay_amount": "184.5", "paid_amount": "184.5",
"pay_currency": "USDT", "network": "TRC20" } } pay_currency और network को ऑर्डर के साथ सेव करें। ये अकाउंटिंग और बाद में सपोर्ट की बातचीत में काम आते हैं।
Node.js और Python में वेरिफ़िकेशन
यही जाँच दो और लोकप्रिय भाषाओं में:
// Node.js (Express with express.raw for this route)
const exp = 'sha256=' + crypto.createHmac('sha256', secret)
.update(ts + '.' + rawBody).digest('hex');
const ok = crypto.timingSafeEqual(Buffer.from(exp), Buffer.from(sig));
# Python
exp = 'sha256=' + hmac.new(secret.encode(), f'{ts}.{raw}'.encode(),
hashlib.sha256).hexdigest()
ok = hmac.compare_digest(exp, sig) दोनों मामलों में रिक्वेस्ट की raw body ही पढ़ें। कई फ़्रेमवर्क JSON को अपने-आप पार्स कर देते हैं; पार्स होकर दोबारा सीरियलाइज़ होने के बाद बाइट्स सिग्नेचर से मेल नहीं खाते।
लोकल टेस्टिंग
Webhooks को पब्लिक HTTPS URL चाहिए, इसलिए लोकल लैपटॉप उन्हें सीधे प्राप्त नहीं कर सकता। दो व्यावहारिक विकल्प हैं: हैंडलर को जल्दी किसी स्टेजिंग सर्वर पर डिप्लॉय करें, या टनलिंग टूल से अपना लोकल पोर्ट अस्थायी रूप से एक्सपोज़ करें। स्टेजिंग callback की ओर इशारा करते छोटे इनवॉइस बनाएँ, फिर मर्चेंट डैशबोर्ड में डिलीवरी लॉग देखें कि ठीक-ठीक क्या भेजा गया और आपके सर्वर ने क्या जवाब दिया।
टेस्टिंग के दौरान हर इवेंट टाइप को कम से कम एक बार ट्रिगर करने की कोशिश करें: paid, confirmed, underpaid और expired। जब आपके हैंडलर की हर शाखा असली webhook पर चल चुकी हो, तो प्रोडक्शन में चौंकाने वाला बहुत कम बचता है, और कुछ गड़बड़ होने पर आपको पता होता है कि डिलीवरी लॉग कैसे दिखते हैं।
स्टेप 4: हर स्टेटस को संभालें
Webhook payload में ऑर्डर ID, स्टेटस, अपेक्षित रकम (pay_amount), प्राप्त रकम (paid_amount), करेंसी और नेटवर्क होते हैं। हर इवेंट को एक एक्शन से जोड़ें:
| इवेंट | मतलब | आम एक्शन |
|---|---|---|
invoice.paid | ट्रांसफ़र डिटेक्ट हुआ, कन्फ़र्मेशन बाकी | “पेमेंट मिला, कन्फ़र्म हो रहा है” दिखाएँ |
invoice.confirmed | ज़रूरी कन्फ़र्मेशन पूरे | पेड मार्क करें और डिलीवर करें |
invoice.underpaid | आपकी टॉलरेंस से कम | टॉप-अप का इंतज़ार करें या ग्राहक से संपर्क करें |
invoice.overpaid | अपेक्षा से ज़्यादा | डिलीवर करें; अंतर पर फ़ैसला लें |
invoice.expired | समय पर कोई वैध पेमेंट नहीं | स्टॉक रिलीज़ करें, ऑर्डर अनपेड रखें |
अंडरपेमेंट टॉलरेंस, जुड़कर पूरे होने वाले आंशिक पेमेंट और ग्रेस विंडो में देर से आए पेमेंट mistKET संभालता है; आपके कोड को सिर्फ़ अंतिम नतीजे पर प्रतिक्रिया देनी है।
भरोसेमंदी: retries और idempotency
अगर आपका endpoint डाउन है या एरर लौटाता है, तो webhooks घंटों तक बढ़ते अंतराल पर दोबारा भेजे जाते हैं। यानी कभी-कभी एक ही इवेंट दो बार मिलेगा। ऑर्डर ID के आधार पर अपने हैंडलर को idempotent बनाएँ:
- जल्दी 2xx लौटाएँ, फिर भारी काम क्यू में प्रोसेस करें।
- डिलीवर करने से पहले जाँचें कि ऑर्डर पहले से पेड मार्क तो नहीं है।
- समस्याएँ ट्रेस करने के लिए डिलीवरी ID और इवेंट लॉग करें; डैशबोर्ड में भी webhook डिलीवरी लॉग दिखते हैं।
सुरक्षा चेकलिस्ट
क्रिप्टो पेमेंट API इंटीग्रेशन पैसे से जुड़ा है, इसलिए इसे किसी भी दूसरे पेमेंट कोड की तरह गंभीरता से लें:
- API secret और webhook secret सिर्फ़ सर्वर-साइड रखें — कभी फ़्रंट-एंड कोड या मोबाइल ऐप में नहीं।
- पैनल में IP allow-list से API एक्सेस सीमित करें।
- छोटी timestamp विंडो से बाहर की रिक्वेस्ट रिजेक्ट करें।
- इनवॉइस एक्सपायरी को अपने स्टॉक-रिज़र्वेशन लॉजिक के हिसाब से सेट करें।
- रकम को string या decimal की तरह रखें, कभी float नहीं।
आगे क्या पढ़ें
यही है पूरा क्रिप्टो पेमेंट API इंटीग्रेशन: एक साइन की हुई रिक्वेस्ट, एक वेरिफ़ाई किया हुआ webhook और एक स्टेटस मैप। इसी फ़्लो को नॉन-डेवलपर नज़रिए से समझने के लिए पढ़ें वेबसाइट पर क्रिप्टो पेमेंट कैसे स्वीकार करें। वेबसाइट के बजाय बॉट बना रहे हैं? देखें Telegram बॉट में क्रिप्टो पेमेंट स्वीकार करना। Telegram @mistnetwork पर आवेदन करके अपनी API कीज़ माँगें, डेवलपर सेक्शन में उदाहरण देखें, और कीज़ मर्चेंट लॉगिन से मैनेज करें।


