binance_transfer_between_wallets
Move funds between your own Binance wallets (Spot, Funding, Margin, Futures) with a single internal transfer. Specify the FROM_TO wallet pair, asset, and amount to rebalance or fund trading accounts without withdrawing from Binance.
Instructions
Move funds between the account's OWN wallets (Spot ⇄ Funding ⇄ Margin ⇄ Futures).
Calls POST /sapi/v1/asset/transfer (SIGNED, UID weight 300 of the 180000/min
UID budget). The funds stay inside this Binance account: this is an internal move
between wallets, never a transfer to another user and never a withdrawal off the
platform. No tool in this server can send funds out of Binance.
Kill-switch. This call is refused with Error: … trading is disabled … unless
the server runs with BINANCE_ALLOW_TRADING=1. The gate lives in the HTTP client,
so no tool can bypass it. If you see that error, the operator has deliberately put
the server in read-only mode — report it, do not try to work around it.
Key permission. The API key additionally needs the "Permits Universal
Transfer" flag; without it Binance rejects the call even with the kill-switch on.
binance_get_api_restrictions (wallet_account.py) reports it as
permitsUniversalTransfer.
The isolated-margin directions need the pair named — from_symbol for
ISOLATEDMARGIN_MARGIN and ISOLATEDMARGIN_ISOLATEDMARGIN, to_symbol for
MARGIN_ISOLATEDMARGIN and ISOLATEDMARGIN_ISOLATEDMARGIN. Both rules are checked
locally, so a malformed transfer fails before anything is signed or sent.
When to Use:
After a human has approved this specific movement of this specific amount.
To fund Binance Pay (MAIN_FUNDING) or to sweep Funding back to Spot (FUNDING_MAIN).
When NOT to Use:
To send crypto to another exchange or wallet — this server never withdraws.
To swap one asset for another — that is the convert tools (convert.py) or a spot order (
binance_place_order).To check what a past transfer did — use
binance_get_transfer_history.
Returns:
A confirmation echoing exactly what Binance returned, which is only the tranId.
Binance sends no status field on this endpoint, so the confirmation says the transfer
was accepted and points at binance_get_transfer_history /
binance_get_wallet_balances to verify it settled. It never claims a balance changed.
Examples: params = {"type": "MAIN_FUNDING", "asset": "USDT", "amount": "25.5"} params = {"type": "FUNDING_MAIN", "asset": "BNB", "amount": "0.1"} params = {"type": "MARGIN_ISOLATEDMARGIN", "asset": "USDT", "amount": "100", "to_symbol": "BTCUSDT"}
Error Handling:
Error: … trading is disabled …→ the kill-switch is off; nothing was sent.-2015 / "permission denied" → the key lacks "Permits Universal Transfer", or this IP is not allowlisted.
-3020 / insufficient balance → the source wallet does not hold the amount.
A 5xx or a timeout means the transfer status is UNKNOWN — it may have gone through. Check
binance_get_transfer_historyfor the same type before retrying; never resend blindly.
Input Schema
| Name | Required | Description | Default |
|---|---|---|---|
| params | Yes |
Output Schema
| Name | Required | Description | Default |
|---|---|---|---|
| result | Yes |