正式商戶 API
以下只列公開商戶可串接的正式 API;查詢、餘額、銀行列表、回調重送與相容功能都已納入正式 API 說明。
正式 Base URL:
https://api.wattt.asia。此網域只開放公開文件與正式商戶 API,不開放後台、登入頁、APP API、Mock 或內部 Bridge。| 功能 | Method | 路徑 | 狀態 | 說明 |
|---|---|---|---|---|
| 建立收單 | POST | /api/v1/merchant/collections |
已開放 | 正式商戶收單建立;支援 snake_case 與 v6.0 欄位相容、IP 白名單與簽名驗證。 |
| 收單查詢 | POST | /api/v1/merchant/collections/status |
已開放 | 依 orderid、merchant_order_no、tradeNo 查詢收單狀態。 |
| 建立代付 | POST | /api/v1/merchant/payouts |
已開放 | 正式商戶代付建立;支援 notify_url / reverse_url、snake_case 與 v6.0 欄位相容。 |
| 代付查詢 | POST | /api/v1/merchant/payouts/status |
已開放 | 依 serial_no、merchant_order_no、tradeNo 查詢代付狀態。 |
| 商戶餘額 | POST | /api/v1/merchant/balance |
已開放 | 回傳可用餘額、凍結金額、收單/代付統計與通道餘額。 |
| 銀行列表 | GET | /api/v1/merchant/banks |
已開放 | 回傳台灣銀行代碼清單;也支援 q 參數搜尋。 |
| 回調重送 | POST | /api/v1/merchant/callbacks/retry |
已開放 | 依訂單重新送出 notify_url / reverse_url,商戶端回傳純文字 success 視為成功。 |
| 商品列表 | GET | /api/v1/products |
已開放 | 可用 merchant_uid 過濾商戶商品與平台通用商品。 |
| IP 白名單限制 | 安全 | MerchantApiIpWhitelist |
已啟用 | 商戶設定 ip_whitelist 時會限制來源 IP;未設定時維持原串接行為。 |
| v6.0 欄位相容 | 相容 | merchantNo / orderNo / time / notifyUrl |
已啟用 | 正式 API 會自動轉換參考 HTML 欄位至目前系統欄位。 |
| v6.0 簽名相容 | 相容 | Legacy sign compatible |
已啟用 | 正式 API 保留目前簽名規則,也支援參考 HTML 舊簽名送法。 |
正式 API 已包含:收單查詢、代付查詢、商戶餘額、銀行列表、回調重送、IP 白名單限制、參考 HTML 欄位相容與 v6.0 簽名相容。公開文件不再另外拆出完成狀態區塊,也不顯示單數相容路由、Mock、APP、後台或內部 Bridge。
金鑰與簽名規則
商戶必要資訊
商戶需向平台取得
商戶需向平台取得
uid 與 API Secret。正式請求必須帶 timestamp 與 sign。安全提醒
API Secret 不可放在前端網頁、APP、GitHub 或任何公開位置;簽名必須由商戶後端產生。簽名步驟
- 取所有要送出的參數,排除
sign。 - 排除
null與空字串''。 - 若參數是物件或陣列,例如
extra,簽名時轉成 JSON 字串。 - 參數名稱依 A-Z / ASCII 排序。
- 組成
key=value&key2=value2。 - 最後接上
&key=API_SECRET。 - 做 MD5,並轉成大寫 32 碼。
PHP 簽名範例
function makeSign(array $params, string $secret): string
{
unset($params['sign']);
$data = [];
foreach ($params as $key => $value) {
if ($value === null || $value === '') continue;
$data[$key] = is_array($value)
? json_encode($value, JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES)
: $value;
}
ksort($data, SORT_STRING);
$pairs = [];
foreach ($data as $key => $value) {
$pairs[] = $key . '=' . $value;
}
return strtoupper(md5(implode('&', $pairs) . '&key=' . $secret));
}
Node.js 簽名範例
const crypto = require('crypto');
function makeSign(params, secret) {
const data = {};
Object.keys(params).forEach((key) => {
const value = params[key];
if (key === 'sign') return;
if (value === null || value === undefined || value === '') return;
data[key] = typeof value === 'object' ? JSON.stringify(value) : String(value);
});
const base = Object.keys(data)
.sort()
.map((key) => `${key}=${data[key]}`)
.join('&');
return crypto.createHash('md5')
.update(`${base}&key=${secret}`)
.digest('hex')
.toUpperCase();
}
1. 建立收單
POST
https://api.wattt.asia/api/v1/merchant/collections用於商戶建立一筆代收 / 收單資料,資料會寫入收單列表,並可進入 APP 代理賣幣流程。
Request 欄位
| 參數 | 必填 | 格式 | 說明 |
|---|---|---|---|
uid | 是 | string <= 20 | 商戶 UID。 |
orderid | 是 | string <= 64 | 平台收單唯一單號;同一商戶不可重複。 |
merchant_order_no | 否 | string <= 64 | 商戶端訂單號;未填時預設等於 orderid。 |
gateway_code | 否 | string <= 30 | 網關代碼;預設 gateway_c。 |
channel | 否 | string <= 30 | 通道名稱 / 通道代碼。 |
currency | 否 | string <= 10 | 幣別;目前建議固定 TWD。 |
amount | 是 | numeric >= 0.01 | 收單金額,台幣。 |
paid_amount | 否 | numeric >= 0 | 已付款金額;status=succeeded 且未填時預設等於 amount。 |
status | 否 | pending / succeeded / manual | pending=未付,succeeded=已付,manual=已補。 |
collection_status | 否 | pending / matched / exception | 收單流程狀態;一般建單可送 pending。 |
collection_account_name | 否 | string <= 120 | 平台收款戶名。 |
collection_account_no | 否 | string <= 80 | 平台收款帳號。 |
collection_bank_name | 否 | string <= 120 | 平台收款銀行。 |
counterparty_account | 建議 | string <= 120 | 付款人銀行帳號;APP 代理確認末五碼會使用。 |
member_bank_name | 否 | string <= 120 | 付款人銀行名稱。 |
user_id | 否 | string <= 64 | 商戶會員 ID。 |
user_name | 否 | string <= 120 | 商戶會員名稱。 |
notify_url | 否 | url <= 255 | 商戶異步通知網址。 |
return_url | 否 | url <= 255 | 付款完成返回網址。 |
paid_at | 否 | date/datetime | 已付時間;status=succeeded 時可帶。 |
timestamp | 是 | integer | UNIX timestamp。 |
extra | 否 | object/string | 自訂資料;JSON 物件或 v6.0 字串皆可。 |
sign | 是 | string(32) | 簽名。 |
狀態值
pending:未付 / 待處理succeeded:已付 / 成功manual:後台補單 / 已補collection_status=pending:待匹配collection_status=matched:已匹配collection_status=exception:異常
JSON Request 範例
{
"uid": "ABCDE",
"orderid": "COL202605200001",
"merchant_order_no": "M-COL202605200001",
"gateway_code": "gateway_c",
"channel": "API",
"currency": "TWD",
"amount": 2500,
"paid_amount": 0,
"status": "pending",
"collection_status": "pending",
"collection_account_name": "測試收款戶",
"collection_account_no": "80844397416179",
"collection_bank_name": "中信銀行",
"counterparty_account": "0040000256001018003",
"member_bank_name": "台灣銀行",
"user_id": "U1001",
"user_name": "測試會員",
"notify_url": "https://merchant.example.com/notify/collection",
"return_url": "https://merchant.example.com/return",
"timestamp": 1779214673,
"sign": "2C4605785AD325985337770959CEFB42"
}
cURL 範例
curl -X POST "https://api.wattt.asia/api/v1/merchant/collections" \
-H "Accept: application/json" \
-H "Content-Type: application/json" \
-d '{"uid":"ABCDE","orderid":"COL202605200001","merchant_order_no":"M-COL202605200001","gateway_code":"gateway_c","channel":"API","currency":"TWD","amount":2500,"paid_amount":0,"status":"pending","collection_status":"pending","collection_account_name":"測試收款戶","collection_account_no":"80844397416179","collection_bank_name":"中信銀行","counterparty_account":"0040000256001018003","member_bank_name":"台灣銀行","user_id":"U1001","user_name":"測試會員","notify_url":"https://merchant.example.com/notify/collection","return_url":"https://merchant.example.com/return","timestamp":1779214673,"sign":"2C4605785AD325985337770959CEFB42"}'
Response 成功範例
{
"ok": 1,
"message": "收單模擬資料已建立",
"data": {
"id": 123,
"orderid": "COL202605200001",
"merchant_order_no": "M-COL202605200001",
"status": "pending",
"amount": 2500,
"paid_amount": 0,
"payment_bank_account": "0040000256001018003",
"counterparty_account": "0040000256001018003"
}
}
2. 建立代付
POST
https://api.wattt.asia/api/v1/merchant/payouts用於商戶建立一筆代付資料,資料會寫入代付列表,並可進入 APP 代理買幣流程。
Request 欄位
| 參數 | 必填 | 格式 | 說明 |
|---|---|---|---|
uid | 是 | string <= 20 | 商戶 UID。 |
serial_no | 是 | string <= 40 | 代付唯一流水號;同一流水號不可重複。 |
merchant_order_no | 否 | string <= 80 | 商戶端訂單號;未填時預設等於 serial_no。 |
channel | 否 | string <= 30 | 通道名稱;預設代付。 |
amount | 是 | numeric >= 0.01 | 代付金額。 |
actual_amount | 否 | numeric >= 0 | 實際代付金額;未填預設等於 amount。 |
status | 否 | pending / processed / cancelled | pending=待處理,processed=已處理,cancelled=已撤銷。 |
payee_name | 是 | string <= 120 | 收款人姓名。 |
payee_bank | 否 | string <= 120 | 收款銀行。 |
payee_account | 否 | string <= 80 | 收款帳號。 |
payment_tag | 否 | string <= 60 | 代付標籤 / 備註標籤。 |
beneficiary_name | 否 | string <= 120 | 受款人名稱;未填預設等於 payee_name。 |
requested_at | 否 | date/datetime | 請求時間;未填預設 now()。 |
processed_at | 否 | date/datetime | 處理完成時間;status=processed 時可帶。 |
voucher_no | 否 | string <= 80 | 憑證號。 |
note | 否 | text | 備註。 |
is_delayed | 否 | boolean | 是否延遲處理。 |
notify_url | 否 | url <= 255 | 代付完成異步通知網址。 |
reverse_url | 否 | url <= 255 | 代付失敗 / 撤銷異步通知網址。 |
timestamp | 是 | integer | UNIX timestamp。 |
extra | 否 | object/string | 自訂資料;JSON 物件或 v6.0 字串皆可。 |
sign | 是 | string(32) | 簽名。 |
狀態值
pending:待處理processed:已處理 / 成功cancelled:已撤銷 / 失敗 / 駁回success、succeeded會轉為processedfailed、rejected會轉為cancelled
JSON Request 範例
{
"uid": "ABCDE",
"serial_no": "PO202605200001",
"merchant_order_no": "M-PO202605200001",
"channel": "代付",
"amount": 3000,
"actual_amount": 3000,
"status": "pending",
"payee_name": "王小明",
"payee_bank": "中國信託",
"payee_account": "822123456789012",
"payment_tag": "PAYOUT-TEST",
"beneficiary_name": "王小明",
"notify_url": "https://merchant.example.com/notify/payout",
"timestamp": 1779214673,
"sign": "EE6E4F93675344E8ADE95266EEC1A2E9"
}
cURL 範例
curl -X POST "https://api.wattt.asia/api/v1/merchant/payouts" \
-H "Accept: application/json" \
-H "Content-Type: application/json" \
-d '{"uid":"ABCDE","serial_no":"PO202605200001","merchant_order_no":"M-PO202605200001","channel":"代付","amount":3000,"actual_amount":3000,"status":"pending","payee_name":"王小明","payee_bank":"中國信託","payee_account":"822123456789012","payment_tag":"PAYOUT-TEST","beneficiary_name":"王小明","notify_url":"https://merchant.example.com/notify/payout","timestamp":1779214673,"sign":"EE6E4F93675344E8ADE95266EEC1A2E9"}'
Response 成功範例
{
"ok": 1,
"message": "代付模擬資料已建立",
"data": {
"id": 456,
"serial_no": "PO202605200001",
"merchant_order_no": "M-PO202605200001",
"status": "pending",
"amount": 3000
}
}
3. 訂單查詢
收單與代付皆可用商戶單號或平台交易號查詢;回應同時提供目前系統欄位與 v6.0 常見欄位。
收單查詢
POST
https://api.wattt.asia/api/v1/merchant/collections/status{
"uid": "ABCDE",
"orderid": "COL202605200001",
"timestamp": 1779214673,
"sign": "89A8629D66DD0F00578AF485E71FA3B0"
}
代付查詢
POST
https://api.wattt.asia/api/v1/merchant/payouts/status{
"uid": "ABCDE",
"serial_no": "PO202605200001",
"timestamp": 1779214673,
"sign": "F7BDCA65EC468E3CAEB8C0A03446F5AA"
}
Response 範例
{
"ok": 1,
"code": 0,
"text": "success",
"status": "PAID",
"paid": 2500,
"tradeNo": "123",
"orderNo": "M-COL202605200001",
"data": {
"system_status": "succeeded",
"amount": 2500,
"paid_amount": 2500,
"callback_status": "succeeded"
}
}
4. 餘額查詢 / 銀行列表
商戶餘額查詢
POST
https://api.wattt.asia/api/v1/merchant/balance{
"uid": "ABCDE",
"timestamp": 1779214673,
"sign": "170F0B101AFD1C4BA4B45A7DEBCCDB01"
}
回傳欄位包含 balance、balance0、balance1、balance2,以及 data.summary 內的收單、代付、凍結與可用餘額明細。
銀行列表
GET
https://api.wattt.asia/api/v1/merchant/bankshttps://api.wattt.asia/api/v1/merchant/banks?q=中國信託
回調重送
POST
https://api.wattt.asia/api/v1/merchant/callbacks/retry{
"uid": "ABCDE",
"type": "collection",
"orderid": "COL202605200001",
"timestamp": 1779214673,
"sign": "29480AC603978CFC082D754DBE5A39B1"
}
5. 商品查詢
GET
https://api.wattt.asia/api/v1/products可帶 merchant_uid 過濾商戶商品與平台通用商品。
https://api.wattt.asia/api/v1/products?merchant_uid=ABCDE
Response 範例
{
"ok": 1,
"items": [
{
"id": "1",
"uid": "PRODUCT_UID",
"sku": "SKU001",
"name": "商品名稱",
"currency": "TWD",
"price_hkd_cents": 100000
}
]
}
6. 異步通知 / 回調
建單可帶 notify_url,代付也可帶 reverse_url。如需人工重送,可呼叫 POST /api/v1/merchant/callbacks/retry。商戶收到通知後請回應純文字 success。
建議代收回調格式
{
"type": "collection",
"uid": "ABCDE",
"orderid": "COL202605200001",
"merchant_order_no": "M-COL202605200001",
"trade_no": "123",
"amount": 2500,
"paid_amount": 2500,
"status": "succeeded",
"paid_at": "2026-05-18 15:30:00",
"timestamp": 1779214673,
"sign": "MD5SIGN"
}
建議代付回調格式
{
"type": "payout",
"uid": "ABCDE",
"serial_no": "PO202605200001",
"merchant_order_no": "M-PO202605200001",
"amount": 3000,
"actual_amount": 3000,
"status": "processed",
"processed_at": "2026-05-18 15:35:00",
"timestamp": 1779214673,
"sign": "MD5SIGN"
}
回調重送屬於正式商戶 API;系統會依商戶回應是否為
success 更新重送結果。7. 參考 HTML 欄位對照
你提供的參考 HTML 文件有部分欄位命名與目前系統不同。公開文件保留對照表,讓商戶知道目前正式 API 應送哪個欄位。
| 參考文件欄位 | 目前系統欄位 | 狀態 | 說明 |
|---|---|---|---|
merchantNo | uid | 已相容 | 目前請送 uid。 |
orderNo(收單) | orderid | 已相容 | 目前收單唯一單號使用 orderid。 |
orderNo(代付) | serial_no | 已相容 | 目前代付唯一流水號使用 serial_no。 |
time | timestamp | 已相容 | 目前使用 UNIX timestamp。 |
notifyUrl | notify_url | 已相容 | 目前使用 snake_case。 |
userNo | user_id | 已相容 | 付款會員 ID。 |
userName | user_name | 已相容 | 付款會員名稱。 |
name(代付) | payee_name | 已相容 | 收款人姓名。 |
bankName | payee_bank / member_bank_name | 已相容 | 依代付 / 收單情境不同。 |
bankAccount | payee_account / counterparty_account | 已相容 | 依代付 / 收單情境不同。 |
8. 錯誤碼 / 回應格式
| HTTP / ok | 訊息 | 原因 | 處理方式 |
|---|---|---|---|
422 / ok=0 | 商戶不存在或未啟用 | uid 錯誤、商戶停用或未建立。 | 確認商戶 UID 與後台商戶狀態。 |
422 / ok=0 | 簽名錯誤 | sign 與平台計算結果不一致。 | 檢查參數排序、空值處理、extra JSON 與 Secret。 |
422 / ok=0 | 此商戶訂單號已存在 | 收單 orderid 重複。 | 每筆訂單使用唯一 orderid。 |
422 / ok=0 | 代付流水號已存在 | 代付 serial_no 重複。 | 每筆代付使用唯一 serial_no。 |
422 | validation error | 缺少必填或格式錯誤。 | 依照 Request 欄位表修正。 |