AI Guide Map
Position Management with Bybit APIs & WebSockets
Track positions. Combine startup/recovery hydration with private account-level WebSockets, then produce risk-gated DCA, take-profit, and stop-loss intents.
Default Scope
- Runtime: Node.js LTS
- Recommended language: TypeScript
- Package: bybit-api
- Implement execution for when EXECUTION_MODE=DEMO, TESTNET, or LIVE is enabled and all gates pass, but keep that path disabled by default.
- EXECUTION_MODE=DRY_RUN_PRIVATE is the default local mode for bounded Bybit order mutation candidates.
- EXECUTION_MODE=DEMO uses demoTrading=true/testnet=false; EXECUTION_MODE=TESTNET uses Bybit testnet routing
- Credentials: scoped API keys from environment variables only
Resources
Start with the task-specific resources below, then use SDK and exchange docs to verify exact method names, request fields, topics, and product rules.
Start here
Use this short route for the default Bybit position-manager build path before opening heavier machine artifacts.
Exact Bybit details
Open these when implementation needs exact Bybit request fields, event shapes, retCode handling, or SDK method names.
Validation after implementation
A Conformance Pack is a versioned, machine-readable set of behavior-contract fixtures, expected outcomes, and runner requirements for a generated integration. Use conformance packs after the implementation exists as validation sources, not the first design input.
Advanced reusable-runtime material
Use these when generating shared runtime modules, manifests, reusable contracts, or deeper agent scaffolding. They are not the default first-read path.
Implementation Steps
Follow these in order; use the linked artifacts only where they clarify the current step.
1. Follow the simple route
Start from the primary spec, prompt artifact, and recipe. Use integration kits for exact Bybit details and behavior-contract fixtures after implementation.
- Read /ai/exchange-state, then /.well-known/prompts/bybit-position-manager/latest.md, then /.well-known/recipes/bybit-position-manager.json.
- Open the Bybit integration kit only when exact fields, event shapes, SDK surfaces, or retCode handling are needed.
- Use these when generating shared runtime modules, manifests, reusable contracts, or deeper agent scaffolding. They are not the default first-read path.
- Use installed bybit-api declarations and current Bybit docs for exact request fields, retCode behavior, private topics, and product limits.
2. Hydrate and listen
REST Hydration seeds Account State. Private account streams keep it current after the service is running.
- Hydrate Bybit instruments, account mode, positions, active orders, historic orders, executions, wallet/balance state, and risk limits before planning.
- For Bybit linear startup/restart hydration, call getPositionInfo with settleCoin for each configured settlement coin, defaulting to USDT and USDC. Never call getPositionInfo with only category=linear; use symbol only for deliberately narrow scoped recovery, and filter configuredSymbols locally after settleCoin hydration.
- For Bybit linear active-order startup/restart hydration, either capture and preserve a redacted raw getActiveOrders({ category: "linear", settleCoin, openOnly: 0 }) response proving regular and conditional StopOrder rows are both returned for the account mode, or defensively fetch orderFilter="Order" and orderFilter="StopOrder" separately for each settleCoin and merge by orderId/orderLinkId.
- Subscribe to product-relevant private order, execution, position, and wallet topics after credentials and product scope are explicit.
- Follow the Event-Driven Workflow: During normal private event bursts, apply every event to Account State immediately, then use a short event-burst wait before planning. Do not enter REST recovery just because private order, execution, fill, or position events arrived. If the private stream is healthy and Account State has ingested the matching order evidence plus the matching position or account evidence, continue from private-stream account state without REST hydration. For products without exchange-provided position rows, locally derived position evidence fills the same role.
3. Track owned slots
orderLinkId values follow the shared lookup-key rule. Custom Order IDs are lookup keys into durable local order context, not state containers.
- Generate unique random orderLinkId values. Bybit does not need a generic prefix unless current docs or config explicitly require one.
- Store category, symbol, positionIdx, managed side, role, step, order kind, request summary, and pending action before submit.
- Durable context persistence is default for order-capable projects; if disabled, require an explicit acknowledgement and follow a deterministic startup cleanup policy.
- Prefer observed Account State for position mode when evidence is clear; block only while identity evidence is unresolved or contradictory.
- Treat saved Durable Context without matching trusted active-order evidence as unresolved until Scoped Recovery. If active app-owned orders have no saved context, refuse mutation unless explicit adoption is configured and tested.
- Terminal order rows are not active protective confirmations. Completed DCA step identity survives restart and is not treated as an active order.
4. Choose one action family
One workflow owner follows the Runtime Workflows model: drain one product/symbol-side scope and choose one action family per pass.
- Each reconciliation pass chooses one action family only: recover uncertain state, clean up stale app-owned orders, repair/place protection, place/repair DCA, do nothing, or wait because required evidence or configuration is missing.
- A fresh managed position places protective SL/TP before exposure-increasing DCA. SL and TP are separate orders and may dispatch concurrently after contexts are registered.
- Accepted place/amend/cancel responses create pending confirmations and duplicate-submit protection, but they do not unlock dependent action families until private confirmation or scoped recovery proves account state.
- RecoveryRequired or syncRequired blocks normal cleanup, protective, DCA, and EXECUTION_MODE=DEMO, TESTNET, or LIVE submission until scoped REST hydration plus buffered replay restores trusted account state. Deterministic stale-target no-ops avoid entering recovery when account state already proves convergence.
- Filter-only recovery does not prune Durable Context. Open-order recovery may confirm or prune contexts only with explicit active-order evidence.
- Flat hedge rows are state rows, not close lifecycle events unless the same scoped side was previously open.
- Hedge-risk controls block exposure-increasing DCA while allowing protective SL/TP repair.
5. Apply Bybit specifics
Shared runtime modules handle lifecycle behavior. Bybit-specific code handles request shapes, event fields, and retCode handling.
- Prefer RestClientV5 with throwExceptions=true for order workflows. If disabled, classify submit, cancel, amend, and preCheck responses by retCode === 0.
- For linear products, verify and use ws.subscribeV5(["order", "execution", "position", "wallet"], "linear", true). For Spot, verify the product-specific private topics and category before subscribing.
- Bybit linear managed SL defaults to close-all market StopOrder: qty=0, reduceOnly=true, closeOnTrigger=true, triggerBy=MarkPrice unless configured, matching positionIdx, triggerDirection=2 for long SL below price, triggerDirection=1 for short SL above price, and no price field.
- Converge app-owned orders by actionable slot fields, including positionIdx and triggerDirection where relevant, not raw hydrated defaults.
Runtime sequence
Keep these transitions visible in logs and tests.
- Load config, credentials, product scope, Bybit endpoint settings, and EXECUTION_MODE.
- Create RestClientV5 and WebsocketClient, preferring throwExceptions=true for order workflows.
- Startup hydration loads filters, positions or inputs for local position tracking, open orders, fills or executions, wallet or margin state, account mode, risk/readiness state, and stored contexts.
- Load Durable Context and classify app-owned orders from stored context plus Trusted State.
- Subscribe to private order, execution, position, and wallet topics and replay buffered events before management readiness.
- Drain affected scopes through one workflow owner and one action family per pass.
- On timeout, retCode rejection, reconnect, conflict, or sync-required state, run Scoped Recovery, replay buffered events, then replan.
Bybit Request FieldsReference
Bybit-specific code extends the shared runtime modules with exchange request fields, identity fields, and rejection handling.
- category: product family, such as spot or linear.
- orderLinkId: app-owned order identity field.
- positionIdx: position-side identity, where 0 is one-way, 1 is hedge long, and 2 is hedge short.
- triggerDirection: required for linear conditional stop-loss logic.
- retCode and retMsg: Bybit REST business-level acceptance and rejection fields.
Local test setReference
After implementation, run the applicable behavior-contract fixtures locally before enabling EXECUTION_MODE=DEMO, TESTNET, or LIVE submission. conformance packs are the machine-readable fixture sources for these checks.
- Use /.well-known/conformance/exchange-state-management/latest.json for reusable workflow fixtures.
- Use /.well-known/conformance/bybit-position-manager/latest.json for Bybit request, stream, and retCode fixtures.
- Keep EXECUTION_MODE=DEMO, TESTNET, or LIVE submission disabled until startup hydration, private confirmation races, pending-confirmation gating, recovery hydration, protective SL/TP, close-all SL shape, amend-first convergence, and identity mismatch/recovery cases pass locally.
Manager invariants
- Use EXECUTION_MODE=DRY_RUN_PRIVATE for order-capable local runs.
- The manager never cancels or amends orders that are not app-owned orders unless manual-order takeover is explicitly configured.
- orderLinkId values follow the Custom Order ID rule. They are not state containers.
- Bybit REST order clients prefer throwExceptions=true for simpler error handling.
- RecoveryRequired or syncRequired blocks normal cleanup, protective, DCA, and EXECUTION_MODE=DEMO, TESTNET, or LIVE submission until scoped REST hydration plus buffered replay restores trusted account state. Deterministic stale-target no-ops avoid entering recovery when account state already proves convergence.
- Durable Context, active-order, positionIdx, and late-event conflicts recover or refuse mutation before exchange calls.
- A fresh managed position places protective SL/TP before exposure-increasing DCA. SL and TP are separate orders and may dispatch concurrently after contexts are registered.
- Bybit linear managed SL defaults to close-all market StopOrder unless fixed-quantity SL is explicitly configured and tested.
- Convergence compares actionable slot fields, not raw hydrated defaults.