集成指南
余额查询
概述
余额查询端点允许您实时获取已认证账户余额的详细信息。响应包含三种类型的余额:
- 总余额(Gross Balance):账户中的总金额
- 冻结余额(Blocked Balance):为待处理操作预留的金额
- 可用余额(Net Balance):可立即使用的金额
此端点需要有效的 Bearer token。详情请参阅认证文档。
端点
GET /api/balance
返回已认证账户的当前余额。
必需请求头
Authorization: Bearer {token}请求
curl -X GET https://api.ntxpay.com/api/balance \
-H "Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9..."响应 (200 OK)
{
"grossBalance": 48734.90,
"blockedBalance": 0.00,
"netBalance": 48734.90,
"consultedAt": "2025-11-19T20:18:29.384Z"
}响应结构
grossBalancenumbersempre presente账户总余额(可用余额 + 冻结余额)
示例: 48734.90
blockedBalancenumbersempre presente因待处理操作被冻结的金额(正在处理的付款、等待确认的收款等)
示例: 0.00
netBalancenumbersempre presente可立即使用的可用余额(grossBalance - blockedBalance)
示例: 48734.90
consultedAtstringsempre presente查询的日期和时间,ISO 8601 格式 (UTC)
示例: 2025-11-19T20:18:29.384Z
实现示例
Node.js / TypeScript
import axios from 'axios';
interface BalanceResponse {
grossBalance: number;
blockedBalance: number;
netBalance: number;
consultedAt: string;
}
async function getBalance(token: string): Promise<BalanceResponse> {
try {
const response = await axios.get<BalanceResponse>(
'https://api.ntxpay.com/api/balance',
{
headers: {
'Authorization': `Bearer ${token}`
}
}
);
console.log('=== Account Balance ===');
console.log(`Gross Balance: R$ ${response.data.grossBalance.toFixed(2)}`);
console.log(`Blocked Balance: R$ ${response.data.blockedBalance.toFixed(2)}`);
console.log(`Net Balance: R$ ${response.data.netBalance.toFixed(2)}`);
console.log(`Queried at: ${new Date(response.data.consultedAt).toLocaleString('pt-BR')}`);
return response.data;
} catch (error) {
if (axios.isAxiosError(error)) {
console.error('Error querying balance:', error.response?.data);
throw new Error(error.response?.data?.message || 'Error querying balance');
}
throw error;
}
}
// Usage
const token = 'your_token_here';
getBalance(token);Python
import requests
from datetime import datetime
from typing import Dict
def get_balance(token: str) -> Dict:
"""
Query the account balance
Args:
token: Valid Bearer token
Returns:
Dictionary with balance information
"""
url = 'https://api.ntxpay.com/api/balance'
headers = {
'Authorization': f'Bearer {token}'
}
try:
response = requests.get(url, headers=headers)
response.raise_for_status()
data = response.json()
print('=== Account Balance ===')
print(f"Gross Balance: R$ {data['grossBalance']:.2f}")
print(f"Blocked Balance: R$ {data['blockedBalance']:.2f}")
print(f"Net Balance: R$ {data['netBalance']:.2f}")
consulted_at = datetime.fromisoformat(data['consultedAt'].replace('Z', '+00:00'))
print(f"Queried at: {consulted_at.strftime('%d/%m/%Y %H:%M:%S')}")
return data
except requests.exceptions.RequestException as e:
print(f'Error querying balance: {e}')
if hasattr(e.response, 'json'):
print(f'Details: {e.response.json()}')
raise
# Usage
token = 'your_token_here'
balance = get_balance(token)PHP
<?php
function getBalance(string $token): array
{
$url = 'https://api.ntxpay.com/api/balance';
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_HTTPHEADER, [
'Authorization: Bearer ' . $token
]);
$response = curl_exec($ch);
$httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);
if ($httpCode !== 200) {
throw new Exception("Error querying balance: HTTP $httpCode");
}
$data = json_decode($response, true);
echo "=== Account Balance ===" . PHP_EOL;
echo "Gross Balance: R$ " . number_format($data['grossBalance'], 2, ',', '.') . PHP_EOL;
echo "Blocked Balance: R$ " . number_format($data['blockedBalance'], 2, ',', '.') . PHP_EOL;
echo "Net Balance: R$ " . number_format($data['netBalance'], 2, ',', '.') . PHP_EOL;
echo "Queried at: " . date('d/m/Y H:i:s', strtotime($data['consultedAt'])) . PHP_EOL;
return $data;
}
// Usage
$token = 'your_token_here';
$balance = getBalance($token);使用场景
1. 财务管理仪表板
在管理仪表板上实时显示余额:
// Update balance every 30 seconds
setInterval(async () => {
const balance = await getBalance(token);
// Update UI
document.getElementById('gross-balance').textContent =
`R$ ${balance.grossBalance.toLocaleString('pt-BR', { minimumFractionDigits: 2 })}`;
document.getElementById('net-balance').textContent =
`R$ ${balance.netBalance.toLocaleString('pt-BR', { minimumFractionDigits: 2 })}`;
// Low balance alert
if (balance.netBalance < 1000) {
showLowBalanceAlert();
}
}, 30000);2. 付款前验证
在付款前验证余额是否充足:
async function processPayment(amount: number, token: string) {
// Query current balance
const balance = await getBalance(token);
// Validate available balance
if (balance.netBalance < amount) {
throw new Error(
`Insufficient balance. Available: R$ ${balance.netBalance.toFixed(2)} | ` +
`Required: R$ ${amount.toFixed(2)}`
);
}
// Proceed with payment
return await createPixPayment(amount, token);
}3. 对账报告
生成包含当前余额的对账报告:
def generate_reconciliation_report(token: str):
"""Generate reconciliation report"""
balance = get_balance(token)
report = {
'report_date': datetime.now().isoformat(),
'balance_snapshot': balance,
'status': 'OK' if balance['netBalance'] > 0 else 'ALERT',
'blocked_percentage': (
balance['blockedBalance'] / balance['grossBalance'] * 100
if balance['grossBalance'] > 0 else 0
)
}
# Save report
with open(f"reconciliation_{datetime.now().strftime('%Y%m%d')}.json", 'w') as f:
json.dump(report, f, indent=2)
return report理解冻结余额
冻结余额 表示因以下原因暂时不可用的金额:
响应状态码
| 状态码 | 描述 | 含义 |
|---|---|---|
200 | 成功 | 余额查询成功 |
401 | 令牌无效 | 未提供令牌、令牌已过期或无效 |
请参阅 API 参考 获取响应字段的完整详情。
注意事项
返回的余额反映的是查询瞬间的状态。对于关键操作,请始终在交易前立即查询余额。
- 缓存: 不建议将余额缓存超过 1 分钟
- 精度: 值以 2 位小数返回
- 货币: 所有值均为巴西雷亚尔 (BRL)
监控和告警
实现余额告警
class BalanceMonitor {
constructor(token, thresholds) {
this.token = token;
this.thresholds = {
critical: thresholds.critical || 500,
warning: thresholds.warning || 2000,
high: thresholds.high || 10000
};
}
async checkAndAlert() {
const balance = await getBalance(this.token);
const netBalance = balance.netBalance;
if (netBalance < this.thresholds.critical) {
this.sendAlert('CRITICAL', `Critical balance: R$ ${netBalance.toFixed(2)}`);
} else if (netBalance < this.thresholds.warning) {
this.sendAlert('WARNING', `Low balance: R$ ${netBalance.toFixed(2)}`);
}
// High blocked balance alert
const blockedPercentage = (balance.blockedBalance / balance.grossBalance) * 100;
if (blockedPercentage > 50) {
this.sendAlert('WARNING', `${blockedPercentage.toFixed(1)}% of balance is blocked`);
}
return balance;
}
sendAlert(level, message) {
console.log(`[${level}] ${message}`);
// Integrate with alerting system (email, SMS, Slack, etc.)
}
}
// Usage
const monitor = new BalanceMonitor(token, {
critical: 1000,
warning: 5000
});
// Run every 5 minutes
setInterval(() => monitor.checkAndAlert(), 5 * 60 * 1000);