VERSION 1.1 · HMAC-SHA256

API dành cho Đại lý

Kết nối sản phẩm LUONGMMO vào bot bán hàng đang có. Khách trả tiền cho Đại lý; hệ thống nguồn chỉ trừ ví nhập hàng theo giá sỉ và giao sản phẩm trực tiếp bằng bot shop đã liên kết.

Base URLhttps://www.luongmmo.io.vn/api/v1/index.php
Kích hoạtTạo key và nhận Connection URL trong bot
Xác thực4 header HMAC + IP binding

Kích hoạt từ A đến Z

Registration Key chỉ dùng một lần, hết hạn sau 10 phút. API key và secret chỉ trả đúng một lần khi kích hoạt thành công.

Mở bot nguồn

Vào /start → API / Đại lý, đọc Base URL và tài liệu.

Tạo key kích hoạt

Bấm Tạo key kết nối. Sao chép key, Connection URL và thời gian hết hạn.

Đăng ký từ VPS bot Đại lý

Gửi POST HTTPS từ đúng máy production. IP gọi lần đầu sẽ được ràng buộc.

Lưu credentials

Lưu api_url, api_key, api_secret ngoài web root với quyền 0600.

Đồng bộ và đặt giá

Gọi products, lưu namespace riêng và đặt giá bán không thấp hơn giá sỉ.

Thử đơn nhỏ

Chỉ gọi create_order sau khi bot Đại lý xác nhận đã nhận tiền khách.

Request kích hoạt

Bot sẽ gửi một CONNECTION_URL riêng. Không thay nó bằng tên miền tài liệu này.

POST CONNECTION_URL_DO_BOT_GUI
Content-Type: application/json

{
  "registration_key": "REG-KEY_VUA_TAO",
  "client_id": "bot-dai-ly-id-on-dinh-32-ky-tu",
  "version": "connector-1.0",
  "delivery_bot_token": "BOT_TOKEN_DANG_CHAY_CUA_DAI_LY",
  "shop_name": "Tên shop Đại lý",
  "owner_telegram_id": "123456789",
  "owner_username": "username_khong_co_dau_at"
}
Không gửi Bot Token qua chat công khai. Token chỉ đi trong request HTTPS kích hoạt, được kiểm tra với Telegram rồi mã hóa trước khi lưu.

Ký mỗi request bằng HMAC

raw_json  = chuỗi JSON chính xác sẽ gửi
timestamp = Unix time hiện tại
nonce     = chuỗi ngẫu nhiên mới cho từng request
body_hash = SHA256(raw_json)
canonical = timestamp + "\n" + nonce + "\n" + body_hash
signature = HMAC_SHA256(canonical, api_secret)

Gửi các header: X-ML612-Key, X-ML612-Timestamp, X-ML612-Nonce, X-ML612-Signature và tùy chọn X-ML612-Client-Version.

Timestamp được lệch tối đa 5 phút. Mỗi nonce chỉ dùng một lần. Chuỗi được ký phải giống byte-for-byte với body gửi đi.

Các action được phép

ActionMục đíchField chính
productsĐọc sản phẩm được Admin cấp, giá sỉ/giá bán.Không cần field thêm.
balanceĐọc số dư ví nhập hàng.Không cần field thêm.
shop_configĐọc tên shop, hỗ trợ và trạng thái nhận đơn.Không cần field thêm.
set_retail_priceĐặt giá bán của Đại lý.product_id, retail_price
create_orderTrừ ví giá sỉ và giao qua bot shop.ID đơn, idempotency, sản phẩm, số lượng, khách.
order_statusTra đơn khi timeout hoặc theo dõi giao hàng.external_order_id hoặc order_code
commission_summaryĐối soát doanh thu, giá vốn và lãi.from, to
Ví dụ: products / balance
{"action":"products"}
{"action":"balance"}
Ví dụ: đặt giá bán
{
  "action": "set_retail_price",
  "product_id": 12,
  "retail_price": 150000
}
Ví dụ: báo cáo lãi
{
  "action": "commission_summary",
  "from": "2026-08-01",
  "to": "2026-08-29"
}

Luồng tạo đơn đúng

  1. Bot Đại lý tạo đơn local và nhận tiền khách theo giá bán.
  2. Lưu cố định external_order_ididempotency_key trước lần gọi đầu.
  3. Gọi create_order. Retry phải dùng lại đúng hai giá trị cũ và body cũ.
  4. Nếu timeout, gọi order_status; không sinh một đơn mới.
  5. Hệ thống nguồn giao trực tiếp cho khách bằng bot Đại lý đã liên kết.
{
  "action": "create_order",
  "external_order_id": "SHOP-ORDER-20260829-0001",
  "idempotency_key": "order-20260829-0001-product-12-qty-1",
  "product_id": 12,
  "quantity": 1,
  "buyer_telegram_id": 123456789,
  "buyer_username": "khachhang"
}
Retry cùng nội dung trả lại đơn cũ, không trừ ví, lấy kho hoặc giao lần hai.

Code PHP hoàn chỉnh

Trong gói tích hợp có sẵn examples/register_connector.phpexamples/reseller_client.php. Ví dụ ký request tối thiểu:

<?php
$body = ['action' => 'balance'];
$raw = json_encode($body, JSON_UNESCAPED_UNICODE|JSON_UNESCAPED_SLASHES);
$timestamp = (string)time();
$nonce = bin2hex(random_bytes(16));
$canonical = $timestamp."\n".$nonce."\n".hash('sha256', $raw);
$signature = hash_hmac('sha256', $canonical, getenv('ML612_API_SECRET'));

// POST $raw tới https://www.luongmmo.io.vn/api/v1/index.php với 4 header HMAC.

Hai file mẫu đầy đủ nằm trong gói bàn giao tại examples/reseller_client.phpexamples/register_connector.php. Không đặt source chứa secret trong thư mục web công khai.

Xử lý lỗi

HTTP / codeCách xử lý
401 AUTH_REQUIRED / INVALID_SIGNATUREKiểm tra key, secret, timestamp, nonce và raw JSON đã ký.
403 IP_NOT_ALLOWEDConnector đang gọi từ IP khác. Tạo key mới và kích hoạt lại từ VPS đúng.
402 INSUFFICIENT_BALANCENạp thêm ví nhập hàng; không tạo mã đơn mới khi retry.
409 IDEMPOTENCY_CONFLICTID/key cũ đang gắn với body khác. Dừng và đối chiếu đơn local.
409 RETAIL_PRICE_OUTDATEDĐồng bộ sản phẩm và đặt lại giá bán ≥ giá sỉ mới.
429 RATE_LIMITEDBackoff có giới hạn, không spam retry.
5xx / timeoutGiữ nguyên idempotency và gọi order_status.

Quy tắc bảo mật bắt buộc

  • Không commit Registration Key, API key, API secret hoặc Bot Token.
  • Secret file nằm ngoài web root, quyền 0600.
  • Không log raw body chứa credential, chữ ký hoặc nội dung giao hàng.
  • Luôn xác minh TLS; không tự đi theo redirect với request đã ký.
  • Đồng bộ giờ VPS bằng NTP. Timeout đề xuất: connect 5 giây, tổng 20 giây.
  • Sản phẩm nguồn nằm trong namespace riêng; không ghi đè sản phẩm cũ của bot Đại lý.

Checklist nghiệm thu

☐ Domain/HTTPS và health endpoint hoạt động · ☐ Kích hoạt từ VPS production thành công · ☐ Credentials lưu riêng · ☐ Sản phẩm cũ không bị đổi · ☐ Đồng bộ sản phẩm nguồn · ☐ Giá bán không dưới giá sỉ · ☐ Đọc đúng số dư · ☐ Đơn nhỏ giao đúng bot · ☐ Retry không trừ/giao lặp · ☐ Báo cáo lãi đúng.