tgpay cryptoAPI
crypto-payapireferencetokens

Tài liệu Merchant API

7 phút đọcCập nhật lần cuối: 22 thg 8, 2026

Các quy ước chung của mọi phương thức, cùng các phương thức tra cứu chỉ đọc. Trang chi tiết từng nhóm: hóa đơn và hoàn tiền, chuyển tiền và Lì xì, gói đăng ký, webhook.

API tương thích với Crypto Bot: một tích hợp Crypto Bot sẵn có chạy được chỉ sau khi đổi base URL và token. Mọi thứ nằm ngoài hợp đồng đó đều được đánh dấu phần mở rộng ở dưới.

Bản đặc tả OpenAPI 3.1 máy đọc được của toàn bộ API — mọi phương thức, đối tượng, tên lỗi và webhook — được đăng kèm các trang này: crypto-pay-openapi.yaml · crypto-pay-openapi.json. Hãy nạp nó vào trình sinh code, API client hoặc các công cụ AI của bạn.

Base URL và xác thực

Mọi phương thức đều nằm ở https://crypto.tgpaybot.com/pay/api/<methodName>.

Hãy xác thực mọi yêu cầu bằng token đặt trong header TgCryptoPay-API-Token (Crypto-Pay-API-Token được chấp nhận như tên gọi thay thế để tương thích; nếu gửi cả hai thì bản chuẩn thắng). Token thiếu, sai hoặc đã bị thu hồi — hoặc token của một ứng dụng đã xóa — trả về 401 unauthorized.

Token có dạng <app_id>:<secret> và chỉ hiện một lần, lúc tạo hoặc lúc đổi token mới; máy chủ chỉ lưu bản băm của nó. Xem Bắt đầu dành cho lập trình viên.

Token và scope

Hai loại thông tin xác thực dùng chung một cách xác thực:

  • Token chính — toàn quyền với mọi phương thức, và là khóa duy nhất ký webhook.
  • Token giới hạn quyền (phần mở rộng) — tối đa 10 token còn hiệu lực cho mỗi ứng dụng, tạo ở Thêm → Merchant API trong mục Token giới hạn quyền, mỗi token có một nhãn và một tập scope con. Thu hồi một token là tức thì và không đụng tới các token khác; đổi token chính cũng không đụng tới chúng.
ScopePhương thức mà nó mở
(mọi token hợp lệ)getMe, getCurrencies, getExchangeRates
readgetBalance, getStats, getInvoices, getChecks, getTransfers, getSubscriptionPlans, getSubscriptions
invoicescreateInvoice, deleteInvoice
refundsrefundInvoice
payoutstransfer, transferBatch
checkscreateCheck, deleteCheck
subscriptionscreateSubscriptionPlan, archiveSubscriptionPlan, cancelSubscription

Các scope cộng dồn và độc lập với nhau — invoices không kéo theo read, nên một máy chủ chỉ tạo hóa đơn có thể cầm một token không đọc được gì cả. Gọi một phương thức mà token không bao gồm sẽ trả về 403 scope_required. getMe cho biết scopes của token đang dùng (null với token chính) và token_name, nên lúc nào bạn cũng kiểm tra được mình đang cầm cái gì.

Yêu cầu và phản hồi

  • Các phương thức đọc dùng GET với tham số trên query string. Các phương thức động tới tiền chỉ nhận POST — tham số truyền dưới dạng JSON body, form-urlencoded hoặc query param (body thắng khi xung đột); multipart/form-data bị từ chối.
  • Mọi phản hồi đều là JSON với cùng một envelope: thành công {"ok": true, "result": …}, lỗi {"ok": false, "error": {"code": <HTTP status>, "name": "<error_name>"}}. Hãy rẽ nhánh theo error.name — đó là chuỗi máy đọc ổn định.
  • Một trường hợp biên: giá trị query sai kiểu trên phương thức GET (ví dụ offset=abc) trả về HTTP 422 kèm body {"detail": …} nằm ngoài envelope. Hãy gửi giá trị query đúng kiểu.

Số tiền

  • Số tiền crypto là chuỗi thập phân theo đơn vị coin nguyên ("10.5") — không bao giờ là số JSON. Phản hồi còn kèm amount_minor (phần mở rộng): giá trị nguyên theo đơn vị nhỏ nhất, dưới dạng chuỗi, vì số nguyên cỡ wei tràn kiểu Number của JavaScript.
  • decimals của từng tài sản lấy từ getCurrencies — hãy để phần tính toán số tiền chạy theo đó thay vì gán cứng.
  • Số tiền pháp định có tối đa 2 chữ số thập phân.
  • Tỷ giá là chuỗi thập phân, không bao giờ là số.

Phân trang

Các phương thức danh sách (getInvoices, getChecks, getTransfers, getSubscriptions) nhận offset (mặc định 0) và count (mặc định 100, tối đa 1000; getSubscriptions tối đa 500) và trả về {"items": […]}, mới nhất trước. Bộ lọc theo ID (invoice_ids, check_ids, transfer_ids) là danh sách số nguyên phân tách bằng dấu phẩy. Mọi dấu thời gian đều là chuỗi ISO 8601.

Idempotency: spend_id

Các phương thức động tới tiền nhận một khóa spend_id do bên gọi tự sinh (1–64 ký tự): bắt buộc với transfer và với từng phần tử của transferBatch, tùy chọn với createCheckrefundInvoice (phần mở rộng — vẫn nên dùng). Thử lại với cùng khóa và cùng tham số sẽ phát lại kết quả gốc thay vì chuyển tiền hai lần, nên một yêu cầu hết thời gian chờ luôn an toàn để thử lại. Cùng khóa nhưng khác tham số trả về 409 idempotency_conflict; thử lại trong lúc lần gọi gốc còn đang chạy trả về 409 idempotency_in_progress.

Giới hạn tần suất

Tính theo từng ứng dụng, dùng chung cho mọi token của nó; vượt quá thì trả về 429 rate_limited:

Phương thứcGiới hạn
createInvoice, createCheck60 lần mỗi phút
refundInvoice, transfer30 lần mỗi phút
transferBatch10 lần mỗi phút

Các phương thức đọc không bị giới hạn tần suất. Trong lúc nền tảng bảo trì, các phương thức ghi trả về 503 maintenance còn các phương thức đọc vẫn chạy bình thường.

Phương thức tra cứu và tài khoản

getMe

GET /pay/api/getMe — không có tham số. Trả về danh tính của ứng dụng: app_id, name, payment_processing_bot_username, webhook_url, webhook_events (các loại webhook mở rộng mà ứng dụng đã bật), và hai trường soi token scopes / token_name nói ở trên.

getBalance

GET /pay/api/getBalance — không có tham số. Trả về một mảng, mỗi tài sản được hỗ trợ một dòng, kể cả khi bằng không: currency_code, available (số dư khả dụng), onhold (tiền đang tạm giữ trong các Lì xì của bạn chưa có ai nhận) và amount_minor.

getCurrencies

GET /pay/api/getCurrencies — không có tham số. Danh sách chuẩn những gì API hỗ trợ: các dòng crypto (is_blockchain: true) và các loại tiền pháp định mà hóa đơn có thể định giá theo (is_fiat: true). Mỗi dòng mang code, name, decimals và cờ is_stablecoin.

getExchangeRates

GET /pay/api/getExchangeRates — không có tham số. Tỷ giá crypto sang tiền pháp định: source, target, rate (chuỗi thập phân) và is_validfalse nghĩa là cả bảng đang được lấy từ bộ nhớ đệm cũ; hãy coi các tỷ giá đó chỉ mang tính tham khảo.

getStats

GET /pay/api/getStats — tùy chọn start_at / end_at (ISO 8601; cửa sổ mặc định là 24 giờ gần nhất). Trả về volume (giá trị USD của các hóa đơn đã thanh toán trong cửa sổ), conversion (đã trả/đã tạo, theo phần trăm), unique_users_count, created_invoice_count, paid_invoice_count, và hai mốc thực tế của cửa sổ. Ngày không đọc được sẽ trả về 400 invalid_date.

Lỗi mà mọi phương thức đều có thể trả về

HTTPerror.nameKhi nào
401unauthorizedtoken thiếu, sai hoặc đã bị thu hồi
403scope_requiredtoken không có scope của phương thức
400invalid_requesttham số không đọc được hoặc không hợp lệ (POST)
429rate_limitedvượt giới hạn tần suất
503maintenancenền tảng đang bảo trì (các phương thức ghi)
500internal_errorlỗi máy chủ ngoài dự kiến

Các lỗi riêng của từng phương thức được liệt kê trên trang của phương thức đó.