Exchange mechanics
How take-profit and stop-loss orders work on Binance, OKX, Bybit and Hyperliquid
Updated Ninja Terminal team
Short answer
Each exchange builds take-profit and stop-loss orders differently. Binance uses algo orders at /fapi/v1/algoOrder. OKX uses algo orders at /api/v5/trade/order-algo. Bybit uses position-level trading-stop or conditional orders. Hyperliquid uses trigger orders with a tp or sl flag. What happens to them when the position closes also differs by venue.
A take-profit order and a stop-loss order look the same in most trading screens. Underneath, the four venues use different order objects, different endpoints and different cleanup rules. These differences decide whether a protective order survives a partial close, reverses your position, or stays behind after the trade ends.
How do the venues compare?
| Binance USD-M | OKX swaps | Bybit linear | Hyperliquid | |
|---|---|---|---|---|
| Object | Algo order | Algo order | Position setting, or conditional order | Trigger order |
| Endpoint | POST /fapi/v1/algoOrder |
POST /api/v5/trade/order-algo |
POST /v5/position/trading-stop or /v5/order/create |
order action, t.trigger |
| Order types | STOP_MARKET, TAKE_PROFIT_MARKET, STOP, TAKE_PROFIT |
conditional, oco, trigger |
triggerPrice on the order, or takeProfit / stopLoss |
tpsl: tp or sl |
| Trigger price | MARK_PRICE or CONTRACT_PRICE |
last, mark or index |
LastPrice, MarkPrice, IndexPrice |
Mark price |
| Market on trigger | Yes, for *_MARKET types |
tpOrdPx or slOrdPx of -1 |
Market order type |
isMarket: true |
How does Binance handle TP/SL?
Binance moved conditional orders to its Algo Service on 2025-12-09. Sending STOP_MARKET, TAKE_PROFIT_MARKET, STOP, TAKE_PROFIT or TRAILING_STOP_MARKET to POST /fapi/v1/order now returns error -4120 (STOP_ORDER_SWITCH_ALGO). The replacement is POST /fapi/v1/algoOrder with algoType=CONDITIONAL.
Points to know:
closePosition=truecloses the whole position when triggered. It works withSTOP_MARKETandTAKE_PROFIT_MARKET, and it cannot be combined withquantityorreduceOnly.- In hedge mode
positionSideis required. See hedge mode vs one-way mode. - There is no margin check before a conditional order triggers, and an untriggered conditional order cannot be modified. Cancel and place it again.
- The user data stream reports these orders as
ALGO_UPDATEevents, not as normal order updates. The triggered child order arrives as a regular order update. - A close-position order protects whatever position exists when it fires. After the position is gone, Binance cancels leftover close-position orders, which appear with an expired status. Confirm in open orders after a close, because the public API reference does not describe this rule.
How does OKX handle TP/SL?
OKX places standalone TP/SL at POST /api/v5/trade/order-algo. Use ordType=conditional for a single take-profit or stop-loss, and oco when you want both legs to cancel each other. The OKX documentation notes that a net-mode conditional request with both take-profit and stop-loss fields only runs the stop-loss logic.
Key fields: tpTriggerPx and tpOrdPx, slTriggerPx and slOrdPx, and a trigger type of last, mark or index. An order price of -1 means market.
What causes OKX error 51000 on a TP/SL close?
Error 51000 is OKX’s generic “Parameter error”. On close orders there is one pitfall worth checking first. cxlOnClosePos=true ties the TP/SL to the position, so OKX cancels it when the position is fully closed, and it requires reduceOnly=true. In our testing, sending cxlOnClosePos=true together with an explicit sz was rejected with 51000.
A safe pattern for net mode:
- Send
reduceOnly: truewithsz. A triggered leg can then only reduce the position and never flips it. - Leave out
cxlOnClosePoswhen you passsz. - For a full close you can instead use
closeFraction: "1". The docs say this is the only accepted value, and in net modereduceOnlymust betrue. - In long/short mode send
posSideand do not sendreduceOnly.
Always read the sMsg field of the response. It names the field OKX rejected.
How does Bybit handle TP/SL?
Bybit has two designs:
- Position TP/SL.
POST /v5/position/trading-stopsetstakeProfitandstopLosson the position. WithtpslMode=Fullthe order covers the whole position, and the docs say the system cancels these orders if the position is closed. Set a value to0to cancel it. - Conditional orders.
POST /v5/order/createwithtriggerPrice,triggerDirection(1rise,2fall) andtriggerBy. On spot, useorderFilter=StopOrderand no direction.
A conditional order moves from Untriggered to Triggered almost instantly, then to New, PartiallyFilled and Filled, with the same orderId. The stopOrderType stays set, so only status Untriggered means “still waiting”. A spot conditional order cancelled before it triggers shows as Deactivated.
How does Hyperliquid handle TP/SL?
Hyperliquid has no separate TP/SL endpoint. It uses trigger orders inside the normal order action: t: { trigger: { isMarket, triggerPx, tpsl } }. The tpsl value is tp or sl. The grouping field can be na, normalTpsl or positionTpsl.
The documentation states that mark price triggers TP/SL orders, that market TP/SL orders have a slippage tolerance of 10%, and that a configured size is fixed and does not resize with the position. The documentation does not say what happens to them when the position closes, so check open orders after you flatten.
How Ninja Terminal handles this
- Binance: TP and SL go out as algo orders with
closePosition=true, so no quantity is sent. - OKX: net-mode accounts send a conditional order with
reduceOnlyandsz, and nocxlOnClosePos. Hedge accounts sendposSide. The error message includes OKX’ssMsgso the rejected field is visible. - Bybit: TP/SL is set on the position through trading-stop in
Fullmode, so Bybit removes it when the position closes. - Hyperliquid: TP/SL goes out as trigger orders grouped as
positionTpsl.
Protective orders reduce risk but do not remove it. Fast markets can fill a stop far from its trigger. This guide is not investment advice.
Frequently asked questions
Why does OKX return error 51000 on my TP/SL order?
Error 51000 is a generic parameter error. One cause on net-mode close orders is combining cxlOnClosePos with an explicit sz. In our testing OKX rejected that pair. Use reduceOnly with sz instead, or use closeFraction for a full close.
Why does Binance return -4120 for STOP_MARKET orders?
Since 2025-12-09 Binance USD-M Futures no longer accepts STOP_MARKET, TAKE_PROFIT_MARKET, STOP, TAKE_PROFIT and TRAILING_STOP_MARKET at POST /fapi/v1/order. Error -4120 tells you to use the Algo Order endpoints instead.
Does Bybit treat a triggered stop order as a conditional order?
No. Bybit conditional orders keep the same orderId and a stopOrderType after they trigger, but only the status Untriggered means the order is still waiting for its trigger. Triggered orders move on to New, PartiallyFilled or Filled.
Are TP/SL orders cancelled when I close the position?
It depends on the venue and order type. Bybit cancels position-level TP/SL when the position closes. OKX does this only if cxlOnClosePos is true. Binance documents it for strategy TP/SL in its app. Check open orders after a close.
Sources
- Binance — New Algo Order
- Binance — Derivatives change log (Algo Service migration)
- Binance — USDⓈ-M Futures error codes
- Binance — Limit TP/SL orders FAQ
- OKX API v5 — Place algo order
- Bybit V5 — Set trading stop
- Bybit V5 — Place order (conditional orders)
- Bybit V5 — Enums (orderStatus, stopOrderType)
- Hyperliquid — Order types
- Hyperliquid — Take profit and stop loss orders
- Hyperliquid — Exchange endpoint