Z Zise Developers
稳定币账户 › 指南

提现是两段式:提交那一刻钱就从可用余额扣走,之后只有确认或失败两条路。

发起提现

链上出款由你自己执行merchant_hosted 模型下资金在你手上)。我方做的是扣账 —— 让会员的余额在我方账本上真的减少。


POST /v1/withdrawals               ← 扣账(钱立刻从可用扣走)
POST /v1/withdrawals/{id}/confirm  ← 你确认链上已出款
POST /v1/withdrawals/{id}/fail     ← 你确认出款失败,钱退回

为什么必须先扣账再上链

会员的余额得在我方账本上真的减少,否则同一笔钱能在我方产品上(汇款、兑换、发卡、理财)再花一次 —— 而那时链上那笔已经出去了。


状态机:三档,只有两条出路


        ┌── confirm ──► settled  (终态)
locked ─┤
        └── fail    ──► failed   (终态,钱退回 available)
状态钱在哪谁能推进
lockedmember.withdrawing只有你,调 confirm 或 fail
settled已出账,merchant.custody 相应减少— 终态
failed退回 member.available— 终态

没有第三条路。钱不会自己从 withdrawing 里出来。

你不推它,它就永远停在那里 —— 会员看不到、花不了,

而我方运营也碰不到那个桶(它不在解冻操作的范围里)。

这是刻意的:如果它是普通的「冻结」,那么任何一个能解冻的接口都能

把这笔钱放回去,而那笔钱可能已经在链上了。

重复调用与调错方向

你调的当前状态结果
confirmlocked200,转 settled
confirm已经是 settled200 + replayed: true,幂等回放
confirm已经是 failed400 order_not_cancellable
fail已经是 settled400 order_not_cancellable
任意单不存在 / 属于别的商户404 not_found两种同一响应

fail 不是「取消」。它的语义是「我确认链上没出去,请把钱退回」。

在你确认之前调它,风险是钱其实已经在链上了,而余额被退了回去 ——

那笔差额没有任何自动化能补回来。


收款地址

to_address 由你在请求体里给

⚠⚠ 已知偏差,别照着它设计产品。

这个端点目前不查地址簿、不判 24 小时冷静期、不要求强认证 ——

而同一条线的设计纪律是「地址簿是提现主线里唯一的地址来源」。

代码与纪律在这一处不一致,且这个端点后续可能下线

(所有者已决定把会员充值提现从商户面撤掉)。

在那之前请这样写:先调 GET /v1/withdraw-addresses

取该会员已备案且 usable=true 的地址,把它填进 to_address

不要把这里当成「可以填任意地址」的接口用。

地址簿


GET  /v1/withdraw-addresses?asset=USDT
POST /v1/withdraw-addresses     ← 挂强认证 + 24 小时冷静期

地址是会员的,不是你的 —— 在这个模型下你托管资金,但不代管身份与安全。

字段要点
usable冷静期未过时是 false
usable_at什么时候能用
upstream_valid1 上游确认可用 · -1 上游没答上来(照常放行并留痕

冷静期内的地址会列出来,别把它们滤掉。 刚加完地址的用户看不到它

会以为添加失败,然后再加一次。正确做法是列出来 + 置灰 + 显示 usable_at

⚠ 列表不分页next_cursor 恒为 nullhas_more 恒为 false

那两个字段在只是为了让你的通用翻页器不用为它开特例。

network 过滤大小写敏感、原样匹配(库里存 BSC 这类大写机读码),

asset 会被转成大写。两个参数规则不一样。


幂等键是唯一的防重保护

POST /v1/withdrawalsx-idempotency-key 与入金那条线不同:这里没有 reference 那样的业务流水号

换了新键重发就是第二次真实扣账。用你系统里那笔提现的唯一标识。


这条线可以被我方停掉

线没开、被人工停售、或你的预付余额掉进低水位触发自动停售时,POST /v1/withdrawals 一律回 400 service_unavailable不排队 ——它是即时成交线,扣账要么当场成功要么当场失败。

处置:先看 GET /v1/merchant/lineshalted=true 的会随着预付充值在下一轮巡检自己解除;enabled=false 只能找客户经理。

已经 locked 的单不受影响 —— confirm / fail 照常可调。

停售的意思是「别再开新的了」,不是把在途的钉死在 withdrawing 里。

其它可能的失败

意思
asset_not_allowed资产不在平台目录里,或已停用
insufficient_balance会员可用余额不够
limit_exceeded撞了限额(limit_scope 说明是哪一层)
request_rejected会员被封禁 / 拉黑 / 冻结

相关端点