订单
创建出金订单
创建加密货币到法币的出金订单。加密货币从商户的加密资产余额中扣除,本地法币将支付给已登记的收款人。
POST
/
v2
/
order
/
crypto_to_fiat
创建出金订单
curl --request POST \
--url https://api-test.velafi.com/v2/order/crypto_to_fiat \
--header 'Content-Type: application/json' \
--header 'X-BH-TOKEN: <api-key>' \
--data '
{
"country": "<string>",
"crypto": "<string>",
"fiat": "<string>",
"userPaymentId": 123,
"clientId": "<string>",
"merchantId": 123,
"cryptoAmount": 123,
"fiatAmount": 123,
"remark": "<string>",
"quoteId": "<string>"
}
'import requests
url = "https://api-test.velafi.com/v2/order/crypto_to_fiat"
payload = {
"country": "<string>",
"crypto": "<string>",
"fiat": "<string>",
"userPaymentId": 123,
"clientId": "<string>",
"merchantId": 123,
"cryptoAmount": 123,
"fiatAmount": 123,
"remark": "<string>",
"quoteId": "<string>"
}
headers = {
"X-BH-TOKEN": "<api-key>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {'X-BH-TOKEN': '<api-key>', 'Content-Type': 'application/json'},
body: JSON.stringify({
country: '<string>',
crypto: '<string>',
fiat: '<string>',
userPaymentId: 123,
clientId: '<string>',
merchantId: 123,
cryptoAmount: 123,
fiatAmount: 123,
remark: '<string>',
quoteId: '<string>'
})
};
fetch('https://api-test.velafi.com/v2/order/crypto_to_fiat', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));HttpResponse<String> response = Unirest.post("https://api-test.velafi.com/v2/order/crypto_to_fiat")
.header("X-BH-TOKEN", "<api-key>")
.header("Content-Type", "application/json")
.body("{\n \"country\": \"<string>\",\n \"crypto\": \"<string>\",\n \"fiat\": \"<string>\",\n \"userPaymentId\": 123,\n \"clientId\": \"<string>\",\n \"merchantId\": 123,\n \"cryptoAmount\": 123,\n \"fiatAmount\": 123,\n \"remark\": \"<string>\",\n \"quoteId\": \"<string>\"\n}")
.asString();{
"code": 123,
"msg": "<string>",
"data": {
"data.orderId": 123
}
}加密货币到法币的出金 (Off-Ramp) 功能让你的用户可以将加密货币兑换为本地法币,然后支付给由
对于处于
userPaymentId 标识的收款人。调用此接口前,请确保目标收款人已通过 POST /v2/payments 登记,且 status: 1(有效)。金额可以用加密货币(cryptoAmount)或法币(fiatAmount)指定;如果同时发送,则以 fiatAmount 为准。如需锁定汇率,请传入 quoteId;否则订单将按创建时的当前汇率定价。加密货币从商户的加密资产余额中扣除(参见为订单注资)。
接口地址
POST https://api.velafi.com/v2/order/crypto_to_fiat
在沙盒环境中测试时,请使用
https://api-test.velafi.com/v2/order/crypto_to_fiat。请求头
| 请求头 | 值 |
|---|---|
X-BH-TOKEN | 通过 GET /v2/token/generate 获取的令牌 |
Content-Type | application/json |
请求体参数
string
必填
出金国家的完整名称(例如
"Mexico"、"Argentina")。必须与所选 userPaymentId 关联的国家一致。string
必填
要兑换的加密货币代码(例如
"USDT"、"USDC")。string
必填
收款人将收到的法币的 ISO 4217 代码(例如
"MXN"、"ARS"、"BRL")。integer
必填
接收法币付款的收款人(用户支付方式)的数字 ID。可通过
GET /v2/payments 获取。string
你自己的订单参考 ID,最长 40 个字符。它在你账户下的所有
fiat_to_crypto 和 crypto_to_fiat 订单中必须唯一;使用相同 clientId 的第二次创建请求将被拒绝。该值会在查询订单响应中返回,并可代替 orderId 用于查询订单。参见幂等性与重试。integer
必填
订单所属商户的数字 ID。加密货币从该商户的余额中扣除。未提供有效
merchantId 的请求将被拒绝。decimal
要兑换的加密货币数量(例如
1000.00)。如果同时发送了正数的 fiatAmount,则忽略此值。decimal
收款人应收到的法币金额(例如
21000.00)。请提供 fiatAmount 或 cryptoAmount;如果同时发送,则以 fiatAmount 为准。string
附加到订单的可选自由文本备注。
string
来自报价 API 的报价 ID,用于锁定特定汇率。省略则使用实时现货汇率。
响应字段
integer
响应状态码。
200 表示成功。string
可读的响应信息。
示例
curl -X POST "https://api.velafi.com/v2/order/crypto_to_fiat" \
-H "X-BH-TOKEN: YOUR_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"country": "Mexico",
"clientId": "my-offramp-2024-001",
"merchantId": 3,
"crypto": "USDT",
"fiat": "MXN",
"cryptoAmount": 1000.00,
"userPaymentId": 91,
"remark": "Payout to supplier",
"quoteId": "e46836d68a4a4a6f8f2f609352cffb2f"
}'
{
"code": 200,
"msg": "SUCCESS",
"data": {
"orderId": 1123123123
}
}
为订单注资
出金订单所需的加密货币来自请求中crypto 和 merchantId 对应的商户加密资产余额。可通过加密资产余额查询余额,并通过商户的充值地址进行充值。
- 余额足以覆盖订单: VelaFi 在创建订单时从余额中扣除加密货币。
- 余额不足: 请求将被拒绝并返回余额不足错误,除非你的账户已开通后注资出金(开通情况可能因法币币种而异)。
开通后注资出金后,资金不足的订单会停留在
status: 32(等待加密货币充值)。如果订单需要先进行合规审核(status: 10 或 11),审核通过后会进入 32。订单处于 32 状态期间,订单详情会返回 orderExpireTimestamp,即以秒为单位的 Unix 时间戳形式的注资截止时间。VelaFi 每分钟检查一次商户余额;当同一商户和加密货币下有多个订单在等待时,余额会按从早到晚的顺序分配给这些订单。一旦余额足以覆盖某个订单,VelaFi 会扣除加密货币,订单进入 status: 40,如需补充证明文件则进入 31。如果先到达截止时间,订单将被取消(status: 70)。status: 50(已支付)的 crypto_to_fiat 订单,调用 POST /v2/order/confirm 可完成订单(status: 60)。
幂等性与重试
使用clientId 可以让订单创建请求安全地重试。
clientId为可选参数。发送时,其长度不得超过 40 个字符,且必须在你账户下所有商户的全部fiat_to_crypto和crypto_to_fiat订单中唯一。- 重复使用已有
clientId的创建请求将被拒绝并返回重复提交错误,不会创建新订单。响应不会返回原订单;请改为查询该订单。 clientId会永久绑定到其订单,即使订单被取消也是如此。新订单请使用新的clientId。- 通过
GET /v2/order/detail?orderType=crypto_to_fiat&clientId={clientId}按clientId查询订单。
- 使用相同的
orderType和clientId调用GET /v2/order/detail。 - 如果找到订单,说明原请求已成功。不要再次创建。
- 如果未找到,使用相同的
clientId重试。如果第一次请求在此期间确实已创建订单,重试将作为重复请求被拒绝,而不会创建第二个订单。
quoteId 可能会被一个随后被拒绝的创建请求消耗。重试前请重新申请报价。⌘I
创建出金订单
curl --request POST \
--url https://api-test.velafi.com/v2/order/crypto_to_fiat \
--header 'Content-Type: application/json' \
--header 'X-BH-TOKEN: <api-key>' \
--data '
{
"country": "<string>",
"crypto": "<string>",
"fiat": "<string>",
"userPaymentId": 123,
"clientId": "<string>",
"merchantId": 123,
"cryptoAmount": 123,
"fiatAmount": 123,
"remark": "<string>",
"quoteId": "<string>"
}
'import requests
url = "https://api-test.velafi.com/v2/order/crypto_to_fiat"
payload = {
"country": "<string>",
"crypto": "<string>",
"fiat": "<string>",
"userPaymentId": 123,
"clientId": "<string>",
"merchantId": 123,
"cryptoAmount": 123,
"fiatAmount": 123,
"remark": "<string>",
"quoteId": "<string>"
}
headers = {
"X-BH-TOKEN": "<api-key>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {'X-BH-TOKEN': '<api-key>', 'Content-Type': 'application/json'},
body: JSON.stringify({
country: '<string>',
crypto: '<string>',
fiat: '<string>',
userPaymentId: 123,
clientId: '<string>',
merchantId: 123,
cryptoAmount: 123,
fiatAmount: 123,
remark: '<string>',
quoteId: '<string>'
})
};
fetch('https://api-test.velafi.com/v2/order/crypto_to_fiat', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));HttpResponse<String> response = Unirest.post("https://api-test.velafi.com/v2/order/crypto_to_fiat")
.header("X-BH-TOKEN", "<api-key>")
.header("Content-Type", "application/json")
.body("{\n \"country\": \"<string>\",\n \"crypto\": \"<string>\",\n \"fiat\": \"<string>\",\n \"userPaymentId\": 123,\n \"clientId\": \"<string>\",\n \"merchantId\": 123,\n \"cryptoAmount\": 123,\n \"fiatAmount\": 123,\n \"remark\": \"<string>\",\n \"quoteId\": \"<string>\"\n}")
.asString();{
"code": 123,
"msg": "<string>",
"data": {
"data.orderId": 123
}
}
