CCXT vs the raw WEEX API
WEEX publishes no client library. CCXT compared on passphrase signing, weight-based rate limits, dual WebSocket hosts and typed errors.
WEEX documents its API at weex.com/api-doc — spot, futures, broker, partner and copy-trading sections, with a signature page and an access-restrictions page. What it does not publish is a client library. There is no WEEX SDK repository, and the exchange's documentation does not reference one. A weex-sdk package exists on PyPI, published under Apache-2.0 by "Weex SDK Contributors", but its listed repository URL does not resolve and it is not referenced from WEEX's own documentation.
So the comparison is between CCXT and the client you write yourself. The question that decides it: how much of the plumbing do you want to own?
TL;DR
- Go direct if you call a handful of public endpoints, want field names identical to the docs, or need one of the endpoint families the unified API does not model — broker, partner or copy-trading.
- Pick CCXT if you want spot and futures from one client, four-header passphrase signing built for you, weight accounting on by default, and streaming methods that return the same structures as the REST calls.
- CCXT is not a subset. All 80 WEEX endpoints are generated as implicit methods, signed and throttled like the unified ones.
At a glance
| CCXT | Raw WEEX API | |
|---|---|---|
| Exchanges covered | 104 (WEEX is one of them) | WEEX only |
| Languages | TypeScript, JavaScript, Python, PHP, C#/.NET, Go, Java — one API | whatever you write it in |
| Official client library | — | none published by the exchange |
| Install | pip install ccxt / npm i ccxt | your own HTTP and WebSocket client |
| Products in one client | spot and perpetual swap | separate endpoint trees and separate WebSocket hosts |
| Unified market data + trading API | yes — same method names on every exchange | no — WEEX's own request and response shapes |
| WebSockets | yes — 25 watch* / unWatch* methods implemented | two socket hosts, subscription and merge logic yours |
| Raw endpoint access | yes — 80 WEEX endpoints as implicit methods | yes, it is the whole product |
| Built-in rate limiter | yes, per-endpoint weights, on by default (rateLimit 20 ms) | your code, against X-USED-WEIGHT-* headers |
| Unified error types | yes — 41 typed exceptions in one hierarchy | HTTP 429 plus WEEX error codes |
| Testnet / sandbox | yes — set_sandbox_mode(True) switches the private contract endpoints to WEEX demo trading | no |
| Licence | MIT | — |
| Support | Discord, Telegram, GitHub issues — usually same-day | exchange support channels |
Figures verified September 2026 against CCXT v4.5.77, ts/src/pro/weex.ts in the CCXT source tree, and WEEX's published spot API documentation.
CCXT implements 92 unified capabilities for WEEX, 40 of them fetch* methods — the widest coverage of any venue on this page.
What streaming covers
ts/src/pro/weex.ts implements 25 streaming methods and flags all 25 in the class's has block, so exchange.has['watchOrderBook'] and the rest report True and capability-gated tooling picks them up. They are watchTicker, watchTickers, watchTrades, watchTradesForSymbols, watchOHLCV, watchOHLCVForSymbols, watchOrderBook, watchOrderBookForSymbols, watchBidsAsks, watchOrders, watchMyTrades, watchPositions, watchBalance and their twelve unWatch* counterparts.
Order-book streaming subscribes to WEEX's depth channel (<marketId>@depth200, with a depth option of '200' or '15') and merges the book for you; watchOrderBook delegates to watchOrderBookForSymbols for a single symbol.
The same job, written both ways
Fetch a ticker
import ccxt
exchange = ccxt.weex()
ticker = exchange.fetch_ticker('BTC/USDT')
print(ticker['last'], ticker['baseVolume'])Note the User-Agent. CCXT's weex implementation sets one explicitly on public REST calls and on the WebSocket handshake, with a source comment that the exchange requires headers — the kind of detail you discover from a failed call rather than from the reference.
Place a limit order
import ccxt
exchange = ccxt.weex({
'apiKey': '...',
'secret': '...',
'password': '...', # WEEX requires an API passphrase as well
})
order = exchange.create_order('BTC/USDT', 'limit', 'buy', 0.001, 60000)
print(order['id'], order['status'])WEEX signs a Base64-encoded HMAC-SHA256 over timestamp + METHOD + requestPath + "?" + queryString + body — not the hex digest most venues use — and requires a fourth credential, the API passphrase, in ACCESS-PASSPHRASE. The timestamp is rejected if it drifts more than 30 seconds from server time. Get the encoding, the concatenation order or the passphrase wrong and every private call fails identically.
Stream trades
import ccxt.pro
import asyncio
async def main():
exchange = ccxt.pro.weex()
while True:
trades = await exchange.watch_trades('BTC/USDT')
for t in trades:
print(t['symbol'], t['side'], t['amount'], t['price'])
asyncio.run(main())Spot and contract markets live on two different WebSocket hosts — wss://ws-spot.weex.com/v3/ws and wss://ws-contract.weex.com/v3/ws. CCXT picks the right one from the market you pass and keeps one client per URL, so a strategy that watches a spot pair and a perpetual at the same time does not have to manage two connection pools.
Where the differences actually bite
Four credentials, one constructor
WEEX private requests need an API key, a secret and a passphrase. In CCXT they are apiKey, secret and password on the constructor, and the library assembles ACCESS-KEY, ACCESS-SIGN, ACCESS-PASSPHRASE and ACCESS-TIMESTAMP on every call, with the Base64 signature over the correct concatenation.
Spot and swap in one client
ccxt.weex covers WEEX spot and perpetual swap markets in one instance. Unified symbols keep them apart — 'BTC/USDT' for spot, 'BTC/USDT:USDT' for the linear perpetual — and the method names do not change. Going direct means two endpoint trees, two signing hosts and two socket hosts.
Rate limits you do not have to model
WEEX meters most endpoints by IP and order-placement endpoints by account (userId), reports usage in X-USED-WEIGHT-* and X-REMAINING-WEIGHT-* headers (and X-ORDER-COUNT-* for order endpoints), and answers 429 with a 10-second ban when you cross a limit. Public endpoints are documented at 20 requests per 2 seconds.
CCXT encodes per-endpoint costs in the exchange definition and ships a token-bucket throttler that is on by default (enableRateLimit = True, rateLimit = 20 ms). You call methods in a loop and the library paces them rather than reading headers and backing off yourself.
WebSockets that look like REST
watch_trades returns the same structure as fetch_trades; watch_orders the same as fetch_orders. Swapping polling for streaming is a one-word change, and the code downstream is untouched. Underneath, CCXT handles connection pooling per URL, ping/pong keep-alive with miss detection, automatic reconnect and resubscribe, and bounded caches.
WEEX also gets unWatch* counterparts for ten of those streams, so a symbol universe that changes at runtime can be unsubscribed cleanly rather than by tearing down the connection. And watchBalance and watchPositions seed themselves from a REST snapshot first (fetchBalanceSnapshot, fetchPositionsSnapshot), so the first value you receive is complete rather than the first delta that happens to arrive.
Precision, rounding and string math
WEEX rejects orders that violate a symbol's tick size, step size or minimum notional. CCXT loads that metadata with the markets and gives you helpers backed by the Precise string-arithmetic class, so quantities do not drift through float rounding:
amount = exchange.amount_to_precision('BTC/USDT', 0.0012345678)
price = exchange.price_to_precision('BTC/USDT', 61234.56789)One error hierarchy
CCXT maps WEEX's error codes onto a typed exception tree — InsufficientFunds, InvalidOrder, OrderNotFound, RateLimitExceeded, AuthenticationError, NetworkError and 35 more, all descending from BaseError. You catch ccxt.RateLimitExceeded once instead of matching on codes and re-doing it on the next venue.
Nothing is hidden — the implicit API
Alongside the 92 unified capabilities, all 80 WEEX endpoints are generated as callable implicit methods, with signing, rate-limit accounting and error mapping applied. Browse them on the WEEX implicit API page.
What going direct does better
An honest list:
- Field names match the docs exactly. When you are reading
weex.com/api-docwhile debugging, a raw payload lines up with the reference one field at a time. CCXT's unified names are a deliberate abstraction and one hop away from it. - Endpoint families the unified API does not model. WEEX's documentation has broker, partner and copy-trading sections. CCXT covers 80 endpoints as implicit methods, but anything outside that set — and anything published after the last release — you call yourself.
- Weight headers are visible.
X-USED-WEIGHT-*andX-REMAINING-WEIGHT-*tell you exactly how much budget is left. CCXT's throttler is predictive: it paces from a per-endpoint cost table rather than from the response headers, which is more portable but less exact than reading the counter the exchange actually keeps. - Both socket hosts, on your terms. WEEX splits spot and contract streams across two hosts with separate
/publicand/privatepaths. CCXT picks the host from the market and hides the split; going direct, you decide how many connections to open and how to shard symbols across them. - A smaller dependency. Three endpoints and thirty lines of signing code is less than all of CCXT.
If WEEX is your only venue and you mostly read public data, going direct is perfectly reasonable.
Migrating from the raw WEEX API to CCXT
| What you are doing | Raw WEEX API | CCXT |
|---|---|---|
| Credentials | ACCESS-KEY + ACCESS-SIGN + ACCESS-PASSPHRASE + ACCESS-TIMESTAMP | apiKey, secret, password on the constructor |
| Signature | Base64 HMAC-SHA256 of ts + METHOD + path + ?query + body | built for you |
| Symbols | BTCUSDT | 'BTC/USDT' (spot), 'BTC/USDT:USDT' (linear swap) |
| Symbol list | GET api/v3/exchangeInfo, GET capi/v3/market/exchangeInfo | load_markets() |
| Ticker | GET api/v3/market/ticker/24hr, GET capi/v3/market/ticker/24hr | fetch_ticker() / fetch_tickers() |
| Order book | GET api/v3/market/depth, GET capi/v3/market/depth | fetch_order_book() |
| Candles | GET api/v3/market/klines, GET capi/v3/market/klines | fetch_ohlcv() |
| New order | POST api/v3/order, POST capi/v3/order | create_order() |
| Cancel order | DELETE api/v3/order, DELETE capi/v3/order | cancel_order() |
| Open orders | GET api/v3/openOrders, GET capi/v3/openOrders | fetch_open_orders() |
| Balance | GET api/v3/account/, GET capi/v3/account/balance | fetch_balance() |
| Positions | GET capi/v3/account/position/allPosition | fetch_positions() |
| Streams | wss://ws-spot.weex.com/v3/ws and wss://ws-contract.weex.com/v3/ws, each with /public and /private | watch_* on ccxt.pro.weex |
| Anything not listed | the endpoint | the same endpoint as an implicit method |
FAQ
Does WEEX have an official SDK?
No. WEEX publishes API documentation but no client library, and its documentation does not reference one. A weex-sdk package exists on PyPI under Apache-2.0, but its listed repository URL does not resolve and it is not referenced from WEEX's documentation. CCXT is the maintained option.
How does WEEX authenticate API requests?
Four headers: ACCESS-KEY, ACCESS-SIGN, ACCESS-PASSPHRASE and ACCESS-TIMESTAMP. The signature is a Base64-encoded HMAC-SHA256 over timestamp + METHOD + requestPath + "?" + queryString + body, and the timestamp is rejected if it drifts more than 30 seconds from server time. In CCXT the passphrase is the password constructor field.
Does CCXT support WEEX order-book streaming?
Yes. watchOrderBook and watchOrderBookForSymbols subscribe to WEEX's depth channel and maintain the merged book, with unWatch* counterparts for tearing the subscription down. Both are flagged in has, so exchange.has['watchOrderBook'] reports True.
Does CCXT cover WEEX futures as well as spot?
Yes. One ccxt.weex instance covers both, and CCXT selects the right REST and WebSocket host from the market. Use 'BTC/USDT' for spot and 'BTC/USDT:USDT' for the linear perpetual.
Does CCXT support a WEEX sandbox?
Yes. WEEX runs demo trading on its live hosts rather than a separate testnet domain, and set_sandbox_mode(True) swaps the private contract endpoints to their simulated variants for you. Nothing else in your code changes.
Is CCXT free? Yes. MIT-licensed, including the WebSocket support.
Next steps
- Install CCXT in your language
- Manual — the unified API, structures and conventions
- weex unified API reference
- weex implicit API — all 80 raw endpoints
- CCXT Pro manual — WebSocket methods
- More comparisons
CCXT vs the raw Toobit API
Toobit publishes signing examples, not an SDK. CCXT compared on signing, weight-based rate limits, spot and swap coverage and streaming.
CCXT vs the raw WOO X API
WOO X publishes no SDK and signs v1 and v3 endpoints differently. CCXT compared on signing, rate limits, WebSocket budgets and errors.