General WebSocket API Information
- The base endpoint is:
wss://ws-api.binance.com:443/ws-api/v3.- If you experience issues with the standard 443 port, alternative port 9443 is also available.
- The base endpoint for testnet is:
wss://ws-api.testnet.binance.vision/ws-api/v3
- A single connection to the API is only valid for 24 hours; expect to be disconnected after the 24-hour mark.
- A
serverShutdownevent will be sent when the server is about to shutdown, resulting in disconnection. Please establish a new connection as soon as possible to prevent interruption. - We support HMAC, RSA, and Ed25519 keys. For more information, please see API Key types.
- Responses are in JSON by default. To receive responses in SBE, refer to the SBE FAQ page.
- If your request contains a symbol name containing non-ASCII characters, then the response may contain non-ASCII characters encoded in UTF-8.
- Some methods may return asset and/or symbol names containing non-ASCII characters encoded in UTF-8 even if the request did not contain non-ASCII characters.
- The WebSocket server will send a
ping frameevery 20 seconds.- If the WebSocket server does not receive a
pong frameback from the connection within a minute the connection will be disconnected. - When you receive a ping, you must send a pong with a copy of ping's payload as soon as possible.
- Unsolicited
pong framesare allowed, but will not prevent disconnection. It is recommended that the payload for these pong frames are empty.
- If the WebSocket server does not receive a
- Data is returned in chronological order, unless noted otherwise.
- Without
startTimeorendTime, returns the most recent items up to the limit. - With
startTime, returns oldest items fromstartTimeup to the limit. - With
endTime, returns most recent items up toendTimeand the limit. - With both, behaves like
startTimebut does not exceedendTime.
- Without
- All timestamps in the JSON responses are in milliseconds in UTC by default. To receive the
information in microseconds, please add the parameter
timeUnit=MICROSECONDortimeUnit=microsecondin the URL. - Timestamp parameters (e.g.
startTime,endTime,timestamp) can be passed in milliseconds or microseconds. - All field names and values are case-sensitive, unless noted otherwise.
- If there are enums or terms you want clarification on, please see SPOT Glossary for more information.
- APIs have a timeout of 10 seconds when processing a request. If a response from the Matching
Engine takes longer than this, the API responds with "Timeout waiting for response from backend
server. Send status unknown; execution status unknown."
(-1007 TIMEOUT)
- This does not always mean that the request failed in the Matching Engine.
- If the status of the request has not appeared in User Data Stream, please perform an API query for its status.
- Please avoid SQL keywords in requests as they may trigger a security block by a WAF (Web Application Firewall) rule. See https://www.binance.com/en/support/faq/detail/360004492232 for more details.
Request format
Requests must be sent as JSON in text frames, one request per frame.
Example of request:
Code
Request fields:
| Name | Type | Mandatory | Description |
|---|---|---|---|
id | INT / STRING / null | YES | Arbitrary ID used to match responses to requests |
method | STRING | YES | Request method name |
params | OBJECT | NO | Request parameters. May be omitted if there are no parameters |
-
Request
idis truly arbitrary. You can use UUIDs, sequential IDs, current timestamp, etc. The server does not interpretidin any way, simply echoing it back in the response.You can freely reuse IDs within a session. However, be careful to not send more than one request at a time with the same ID, since otherwise it might be impossible to tell the responses apart.
-
Request method names may be prefixed with explicit version: e.g.,
"v3/order.place". -
The order of
paramsis not significant.
Response format
Responses are returned as JSON in text frames, one response per frame.
Example of successful response:
Code
Example of failed response:
Code
Response fields:
Status codes
Status codes in the status field are the same as in HTTP.
Here are some common status codes that you might encounter:
200indicates a successful response.4XXstatus codes indicate invalid requests; the issue is on your side.400– your request failed, seeerrorfor the reason.403– you have been blocked by the Web Application Firewall. This can indicate a rate limit violation or a security block. See https://www.binance.com/en/support/faq/detail/360004492232 for more details.409– your request partially failed but also partially succeeded, seeerrorfor details.418– you have been auto-banned for repeated violation of rate limits.429– you have exceeded API request rate limit, please slow down.
5XXstatus codes indicate internal errors; the issue is on Binance's side.- Important: If a response contains 5xx status code, it does not necessarily mean that your request has failed. Execution status is unknown and the request might have actually succeeded. Please use query methods to confirm the status. You might also want to establish a new WebSocket connection for that.
See Error codes for Binance for a list of error codes and messages.
Event format
User Data Stream events for non-SBE sessions are sent as JSON in text frames, one event per frame.
Events in SBE sessions will be sent as binary frames.
Please refer to userDataStream.subscribe for details on how to
subscribe to User Data Stream in WebSocket API.
Example of an event:
Code
Event fields:
| Name | Type | Mandatory | Description |
|---|---|---|---|
event | OBJECT | YES | Event payload. See User Data Streams |
subscriptionId | INT | NO | Identifies which subscription the event is coming from. See User Data Stream subscriptions |
Connection events
Server Shutdown
serverShutdown event is sent when the server is about to shut down.
Code
Please establish a new connection as soon as possible to prevent interruption.
Rate limits
Connection limits
There is a limit of 300 connections per attempt every 5 minutes.
The connection is per IP address.
General information on rate limits
- Current API rate limits can be queried using the
exchangeInforequest. - There are multiple rate limit types across multiple intervals.
- Responses can indicate current rate limit status in the optional
rateLimitsfield. - Requests fail with status
429when unfilled order count or request rate limits are violated.
How to interpret rate limits
A response with rate limit status may look like this:
Code
The rateLimits array describes all currently active rate limits affected by the request.
| Name | Type | Mandatory | Description |
|---|---|---|---|
rateLimitType | ENUM | YES | Rate limit type: REQUEST_WEIGHT, ORDERS |
interval | ENUM | YES | Rate limit interval: SECOND, MINUTE, HOUR, DAY |
intervalNum | INT | YES | Rate limit interval multiplier |
limit | INT | YES | Request limit per interval |
count | INT | YES | Current usage per interval |
Rate limits are accounted by intervals.
For example, a 1 MINUTE interval starts every minute. Request submitted at 00:01:23.456 counts
towards the 00:01:00 minute's limit. Once the 00:02:00 minute starts, the count will reset to zero
again.
Other intervals behave in a similar manner. For example, 1 DAY rate limit resets at 00:00 UTC
every day, and 10 SECOND interval resets at 00, 10, 20... seconds of each minute.
APIs have multiple rate-limiting intervals. If you exhaust a shorter interval but the longer interval still allows requests, you will have to wait for the shorter interval to expire and reset. If you exhaust a longer interval, you will have to wait for that interval to reset, even if shorter rate limit count is zero.
How to show/hide rate limit information
rateLimits field is included with every response by default.
However, rate limit information can be quite bulky. If you are not interested in detailed rate limit
status of every request, the rateLimits field can be omitted from responses to reduce their size.
-
Optional
returnRateLimitsboolean parameter in request.Use
returnRateLimitsparameter to control whether to includerateLimitsfields in response to individual requests.Default request and response:
CodeCodeRequest and response without rate limit status:
CodeCode -
Optional
returnRateLimitsboolean parameter in connection URL.If you wish to omit
rateLimitsfrom all responses by default, usereturnRateLimitsparameter in the query string instead:CodeThis will make all requests made through this connection behave as if you have passed
"returnRateLimits": false.If you want to see rate limits for a particular request, you need to explicitly pass the
"returnRateLimits": trueparameter.
Note: Your requests are still rate limited if you hide the rateLimits field in responses.
IP limits
- Every request has a certain weight, added to your limit as you perform requests.
- The heavier the request (e.g. querying data from multiple symbols), the more weight the request will cost.
- Connecting to WebSocket API costs 2 weight.
- Current weight usage is indicated by the
REQUEST_WEIGHTrate limit type. - Use the
exchangeInforequest to keep track of the current weight limits. - Weight is accumulated per IP address and is shared by all connections from that address.
- If you go over the weight limit, requests fail with status
429.- This status code indicates you should back off and stop spamming the API.
- Rate-limited responses include a
retryAfterfield, indicating when you can retry the request.
- Repeatedly violating rate limits and/or failing to back off after receiving 429s will result in
an automated IP ban and you will be disconnected.
- Requests from a banned IP address fail with status
418. retryAfterfield indicates the timestamp when the ban will be lifted.
- Requests from a banned IP address fail with status
- IP bans are tracked and scale in duration for repeat offenders, from 2 minutes to 3 days.
Successful response indicating that in 1 minute you have used 70 weight out of your 6000 limit:
Code
Failed response indicating that you are banned and the ban will last until epoch 1659146400000:
Code
Unfilled Order Count
- Successfully placed orders update the
ORDERSrate limit type. - Rejected or unsuccessful orders might or might not update the
ORDERSrate limit type. - Please note that if your orders are consistently filled by trades, you can continuously place orders on the API. For more information, please see Spot Unfilled Order Count Rules.
- Use the
account.rateLimits.ordersrequest to keep track of how many orders you have placed within this interval. - If you exceed this, requests fail with status
429.- This status code indicates you should back off and stop spamming the API.
- Responses that have a status
429include aretryAfterfield, indicating when you can retry the request.
- This is maintained per account and is shared by all API keys of the account.
Successful response indicating that you have placed 12 orders in 10 seconds, and 4043 orders in the past 24 hours:
Code
Request security
- Each method has a security type indicating required API key permissions, shown next to the method name (e.g., Place new order (TRADE)).
- If unspecified, the security type is
NONE. - Except for
NONE, all methods with a security type are consideredSIGNEDrequests (i.e. including asignature), except for listenKey management. - Secure methods require a valid API key to be specified and authenticated.
- API keys can be created on the API Management page of your Binance account.
- Both API key and secret key are sensitive. Never share them with anyone. If you notice unusual activity in your account, immediately revoke all the keys and contact Binance support.
- API keys can be configured to allow access only to certain types of secure methods.
- For example, you can have an API key with
TRADEpermission for trading, while using a separate API key withUSER_DATApermission to monitor your order status. - By default, an API key cannot
TRADE. You need to enable trading in API Management first.
- For example, you can have an API key with
| Security type | Description |
|---|---|
NONE | Public market data |
TRADE | Trading on the exchange, placing and canceling orders |
USER_DATA | Private account information, such as order status and your trading history |
USER_STREAM | Managing User Data Stream subscriptions |
SIGNED request security
SIGNEDrequests require an additional parameter:signature, authorizing the request.
Signature Case Sensitivity
- HMAC: Signatures generated using HMAC are not case-sensitive. This means the signature string can be verified regardless of letter casing.
- RSA: Signatures generated using RSA are case-sensitive.
- Ed25519: Signatures generated using ED25519 are also case-sensitive
Please consult SIGNED request example (HMAC), SIGNED request example (RSA), and SIGNED request example (Ed25519) on how to compute signature, depending on which API key type you are using.
Timing security
SIGNEDrequests also require atimestampparameter which should be the current timestamp either in milliseconds or microseconds. (See General API Information)- An additional optional parameter,
recvWindow, specifies for how long the request stays valid and may only be specified in milliseconds.recvWindowsupports up to three decimal places of precision (e.g., 6000.346) so that microseconds may be specified.- If
recvWindowis not sent, it defaults to 5000 milliseconds. - Maximum
recvWindowis 60000 milliseconds.
- Request processing logic is as follows:
Code
Serious trading is about timing. Networks can be unstable and unreliable, which can lead to
requests taking varying amounts of time to reach the servers. With recvWindow, you can specify
that the request must be processed within a certain number of milliseconds or be rejected by the
server.
It is recommended to use a small recvWindow of 5000 or less!
SIGNED request example (HMAC)
Here is a step-by-step guide on how to sign requests using an HMAC secret key.
Example API key and secret key:
| Key | Value |
|---|---|
apiKey | vmPUZE6mv9SD5VNHk4HlWFsOr6aKE2zvsw0MuIgwCIPy6utIco14y7Ju91duEh8A |
secretKey | NhqPtmdSJYdKjVHjA7PZj4Mge3R5YNiP1e3UZjInClVN65XAbvqqM6A7H5fATj0j |
WARNING: DO NOT SHARE YOUR API KEY AND SECRET KEY WITH ANYONE.
The example keys are provided here only for illustrative purposes.
Example of request with a symbol name comprised entirely of ASCII characters:
Code
Example of a request with a symbol name containing non-ASCII characters:
Code
As you can see, the signature parameter is currently missing.
Step 1: Construct the signature payload
Take all request params except signature and sort them in alphabetical order by parameter
name:
For the first set of example parameters (ASCII only):
| Parameter | Value |
|---|---|
apiKey | vmPUZE6mv9SD5VNHk4HlWFsOr6aKE2zvsw0MuIgwCIPy6utIco14y7Ju91duEh8A |
price | 52000.00 |
quantity | 0.01000000 |
recvWindow | 100 |
side | SELL |
symbol | BTCUSDT |
timeInForce | GTC |
timestamp | 1645423376532 |
type | LIMIT |
For the second set of example parameters (some non-ASCII characters):
| Parameter | Value |
|---|---|
apiKey | vmPUZE6mv9SD5VNHk4HlWFsOr6aKE2zvsw0MuIgwCIPy6utIco14y7Ju91duEh8A |
price | 0.10000000 |
quantity | 1.00000000 |
recvWindow | 5000 |
side | BUY |
symbol | 123456 |
timeInForce | GTC |
timestamp | 1645423376532 |
type | LIMIT |
Format parameters as parameter=value pairs separated by &. Values need to be encoded in UTF-8.
For the first set of example parameters (ASCII only), the signature payload should look like this:
Code
For the second set of example parameters (some non-ASCII characters), the signature payload should look like this:
Code
Step 2: Compute the signature
- Use the
secretKeyof your API key as the signing key for the HMAC-SHA-256 algorithm. - Sign the UTF-8 bytes of the signature payload constructed in Step 1.
- Encode the HMAC-SHA-256 output as a hex string.
Note that apiKey, secretKey, and the payload are case-sensitive, while the resulting
signature value is case-insensitive.
You can cross-check your signature algorithm implementation with OpenSSL:
For the first set of example parameters (ASCII only):
Code
For the second set of example parameters (some non-ASCII characters):
Code
Step 3: Add signature to request params
Complete the request by adding the signature parameter with the signature string.
For the first set of example parameters (ASCII only):
Code
For the second set of example parameters (some non-ASCII characters):
Code
SIGNED request example (RSA)
Here is a step-by-step guide on how to sign requests using an RSA private key.
| Key | Value |
|---|---|
apiKey | CAvIjXy3F44yW6Pou5k8Dy1swsYDWJZLeoK2r8G4cFDnE9nosRppc2eKc1T8TRTQ |
These examples assume the private key is stored in the file test-rsa-prv.pem.
WARNING: DO NOT SHARE YOUR API KEY AND PRIVATE KEY WITH ANYONE.
The example keys are provided here only for illustrative purposes.
Example of request with a symbol name comprised entirely of ASCII characters:
Code
Example of a request with a symbol name containing non-ASCII characters:
Code
Step 1: Construct the signature payload
Take all request params except signature and sort them in alphabetical order by parameter
name:
For the first set of example parameters (ASCII only):
| Parameter | Value |
|---|---|
apiKey | CAvIjXy3F44yW6Pou5k8Dy1swsYDWJZLeoK2r8G4cFDnE9nosRppc2eKc1T8TRTQ |
price | 52000.00 |
quantity | 0.01000000 |
recvWindow | 100 |
side | SELL |
symbol | BTCUSDT |
timeInForce | GTC |
timestamp | 1645423376532 |
type | LIMIT |
For the second set of example parameters (some non-ASCII characters):
| Parameter | Value |
|---|---|
apiKey | CAvIjXy3F44yW6Pou5k8Dy1swsYDWJZLeoK2r8G4cFDnE9nosRppc2eKc1T8TRTQ |
price | 0.10000000 |
quantity | 1.00000000 |
recvWindow | 5000 |
side | BUY |
symbol | 123456 |
timeInForce | GTC |
timestamp | 1645423376532 |
type | LIMIT |
Format parameters as parameter=value pairs separated by &. Values need to be encoded in UTF-8.
For the first set of example parameters (ASCII only), the signature payload should look like this:
Code
For the second set of example parameters (some non-ASCII characters), the signature payload should look like this:
Code
Step 2: Compute the signature
- Sign the UTF-8 bytes of the signature payload constructed in Step 1 using the RSASSA-PKCS1-v1_5 algorithm with SHA-256 hash function.
- Encode the output in base64.
Note that apiKey, the payload, and the resulting signature are case-sensitive.
You can cross-check your signature algorithm implementation with OpenSSL:
For the first set of example parameters (ASCII only):
Code
For the second set of example parameters (some non-ASCII characters):
Code
Step 3: Add signature to request params
Complete the request by adding the signature parameter with the signature string.
For the first set of example parameters (ASCII only):
Code
For the second set of example parameters (some non-ASCII characters):
Code
SIGNED Request Example (Ed25519)
Note: It is highly recommended to use Ed25519 API keys as they will provide the best performance and security out of all supported key types.
Here is a step-by-step guide on how to sign requests using an Ed25519 private key.
| Key | Value |
|---|---|
apiKey | 4yNzx3yWC5bS6YTwEkSRaC0nRmSQIIStAUOh1b6kqaBrTLIhjCpI5lJH8q8R8WNO |
These examples assume the private key is stored in the file test-ed25519-prv.pem.
WARNING: DO NOT SHARE YOUR API KEY AND PRIVATE KEY WITH ANYONE.
The example keys are provided here only for illustrative purposes.
Example of request with a symbol name comprised entirely of ASCII characters:
Code
Example of a request with a symbol name containing non-ASCII characters:
Code
Step 1: Construct the signature payload
Take all request params except signature and sort them in alphabetical order by parameter
name:
For the first set of example parameters (ASCII only):
| Parameter | Value |
|---|---|
apiKey | 4yNzx3yWC5bS6YTwEkSRaC0nRmSQIIStAUOh1b6kqaBrTLIhjCpI5lJH8q8R8WNO |
price | 52000.00 |
quantity | 0.01000000 |
recvWindow | 100 |
side | SELL |
symbol | BTCUSDT |
timeInForce | GTC |
timestamp | 1645423376532 |
type | LIMIT |
For the second set of example parameters (some non-ASCII characters):
| Parameter | Value |
|---|---|
apiKey | 4yNzx3yWC5bS6YTwEkSRaC0nRmSQIIStAUOh1b6kqaBrTLIhjCpI5lJH8q8R8WNO |
price | 0.20000000 |
quantity | 1.00000000 |
recvWindow | 5000 |
side | SELL |
symbol | 123456 |
timeInForce | GTC |
timestamp | 1668481559918 |
type | LIMIT |
Format parameters as parameter=value pairs separated by &. Values need to be encoded in UTF-8.
For the first set of example parameters (ASCII only), the signature payload should look like this:
Code
For the second set of example parameters (some non-ASCII characters), the signature payload should look like this:
Code
Step 2: Compute the signature
- Sign the UTF-8 bytes of your signature payload constructed in Step 1 using the Ed25519 private key.
- Encode the output in base64.
Note that apiKey, the payload, and the resulting signature are case-sensitive.
You can cross-check your signature algorithm implementation with OpenSSL:
For the first set of example parameters (ASCII only):
Code
For the second set of example parameters (some non-ASCII characters):
Code
Step 3: Add the signature to request params
For the first set of example parameters (ASCII only):
Code
For the second set of example parameters (some non-ASCII characters):
Code
Here is a sample Python script performing all the steps above:
Code
Session Authentication
Note: Only Ed25519 keys are supported for this feature.
If you do not want to specify apiKey and signature in each individual request, you can
authenticate your API key for the active WebSocket session.
Once authenticated, you no longer have to specify apiKey and signature for those requests that
need them. Requests will be performed on behalf of the account owning the authenticated API key.
Note: You still have to specify the timestamp parameter for SIGNED requests.
Authenticate after connection
You can authenticate an already established connection using session authentication requests:
session.logon– authenticate, or change the API key associated with the connectionsession.status– check connection status and the current API keysession.logout– forget the API key associated with the connection
Regarding API key revocation:
If during an active session the API key becomes invalid for any reason (e.g. IP address is not whitelisted, API key was deleted, API key doesn't have correct permissions, etc), after the next request the session will be revoked with the following error message:
Code
Authorize ad hoc requests
Only one API key can be authenticated with the WebSocket connection. The authenticated API key is
used by default for requests that require an apiKey parameter. However, you can always specify the
apiKey and signature explicitly for individual requests, overriding the authenticated API key
and using a different one to authorize a specific request.
For example, you might want to authenticate your USER_DATA key to be used by default, but specify
the TRADE key with an explicit signature when placing orders.
Data sources
-
The API system is asynchronous. Some delay in the response is normal and expected.
-
Each method has a data source indicating where the data is coming from, and thus how up-to-date it is.
| Data Source | Latency | Description |
|---|---|---|
| Matching Engine | lowest | The Matching Engine produces the response directly |
| Memory | low | Data is fetched from API server's local or external memory cache |
| Database | moderate | Data is retrieved from the database |
-
Some methods have more than one data source (e.g., Memory => Database).
This means that the API will look for the latest data in that order: first in the cache, then in the database.