EMC Perps: show liquidation risk and account health #102

Open
opened 2026-10-24 20:10:30 +02:00 by minimons · 0 comments
Owner

Problem and purpose

EMC shows position size, capital, leverage, uPnL and TWAP progress, but it does not clearly show whether a perpetual position or shared Cross account is comfortably collateralized, under pressure or eligible for liquidation. uPnL and leverage alone do not answer that question.

Add a read-only Risk column to the Perps tab, using venue-provided risk data wherever available. This protects Evelyn's capital by making the latest observed liquidation risk visible at the correct account/position level.

Proposed presentation

Illustrative labels, not agreed warning thresholds:

Row Risk display
Jupiter isolated position 8.4% to liq. with a status indicator when a justified warning policy has been defined
Phoenix isolated position Venue risk status plus liquidation distance where available
Phoenix Cross account OK · MM 19.5%, or the venue's more severe risk state
Position belonging to a Cross account Shared, with a tooltip identifying the owning Cross account
Missing, failed or expired observation Explicit Unknown / Stale indication

Keep the existing Long/Short row backgrounds. Convey risk with text and a distinct indicator in the Risk cell, so users do not have to distinguish risk from direction by color alone.

Isolated positions: Jupiter and Phoenix

  • Prefer each venue's reported liquidation price and the corresponding venue price used for risk calculations. Do not use an unrelated Ticker price or last traded price.
  • Show the adverse price movement to the reported liquidation boundary as a signed percentage of the current venue reference price:
Long:  100 × (current price - liquidation price) / current price
Short: 100 × (liquidation price - current price) / current price
  • Positive distance means the reported boundary is still ahead in the adverse direction. Zero/negative distance indicates the observed boundary has been reached/crossed; do not take an absolute value or describe this as proof that liquidation has already occurred.
  • Tooltip: venue status where supplied, current reference price, reported liquidation price, distance, observation time and any limitations.
  • Missing, nonpositive or sentinel liquidation prices (including Phoenix -1) are unavailable. They must not be interpreted as infinite safety or zero risk. An independently valid account risk classification may still be displayed.
  • Profitability is separate from liquidation risk. Do not use uPnL sign or a generic leverage cutoff to assign a healthy state.

Phoenix Cross: assess the shared account

  • Risk belongs to the actual trader subaccount and its shared collateral pool. Display the main indicator on the existing Cross account row; do not invent independent collateral or a standalone safety rating for each child position.
  • Prefer Phoenix's own riskTier: safe, atRisk, cancellable, liquidatable, backstopLiquidatable, highRisk. Suggested mapping: green OK/Safe, yellow At risk, orange Cancellable, red Liquidatable or worse. Preserve the specific venue tier in the tooltip.
  • Show maintenance-margin utilization as:
MM utilization = 100 × maintenanceMargin / effectiveCollateral
USD headroom   = effectiveCollateral - maintenanceMargin
  • This percentage measures margin utilization, not liquidation probability or a price-movement buffer. Around 100% is the maintenance boundary; exact eligibility follows the venue's risk classification and comparison rules.
  • Use Phoenix's effective collateral, which can include funding and risk discounts. Do not substitute EMC's closing Value, undiscounted equity or raw collateral balance.
  • Handle zero/negative effective collateral, zero maintenance requirement and accounts without positions explicitly; never divide by zero or invent a percentage.
  • Tooltip: exact venue tier, effective collateral, maintenance requirement, USD headroom, observation time and any limitations. Cross position tooltips must explain the shared risk scope. Any optional per-market liquidation estimate for Cross must state its assumptions about the other positions; it is not an independent position guarantee.

Group summaries and observation freshness

  • Collapsed venue, wallet and root rows must still expose the worst known descendant risk plus the number of unknown/stale risk scopes. Count a shared Cross account once, not once per child position.
  • Never average liquidation distances, severity classifications or account MM percentages. A partial group must not appear unconditionally healthy when some required observations are unknown.
  • Preserve last-success values with their original observation timestamps after read failures. Show failed/expired risk as retained or stale rather than fresh green. Keep a previously observed critical state visible with its age/uncertainty instead of concealing it.
  • Display risk as latest observed risk, not a live safety guarantee. The existing service refresh cycle can take several minutes.
  • Age-based expiration must work even when the service returns an unchanged snapshot and no new read error. Existing UI snapshot polling must be able to update the freshness indication when the observation crosses the chosen age limit.
  • Failures and unknown risk data must remain isolated between wallets/venues. Existing position identities, totals, expansion, selection and TWAP behavior must be preserved.

Available data and investigation findings

Read-only checks confirmed:

  • The Jupiter overview response already contains markPriceUsd and liquidationPriceUsd. The current RestJupiterPerpsOverview DTO mapping drops them; extend the overview path rather than changing the separate signing/trading/alarm integration. Validate their units and matching identities before display.
  • Phoenix GET /v1/view/trader/{pubkey} returns riskState, riskTier, effectiveCollateral, maintenanceMargin, related margin thresholds and positions with liquidationPrice. This endpoint takes the trader account public key, not merely the wallet authority. Resolve and validate authority/PDA/subaccount membership using official account derivation/data; risk must not depend on having an active TWAP.
  • Actual Phoenix responses use amount objects with raw value and decimals; some position liquidation prices are -1. Validate the deployed response rather than assuming every price is actionable or all fields use the same scale.
  • Prefer these reported account risk values over implementing a new liquidation engine. If an essential value is absent or cannot be verified, expose it as unavailable instead of falling back to an unverified formula.
  • Reuse the existing background service/snapshot architecture, exact decimal arithmetic, bounded timeouts and Phoenix shared pacing/429 cooldown. EMC must not make venue requests directly.

Sources:

Decisions to resolve in OpenSpec before implementation

  1. Define defensible warning bands for isolated liquidation distance. No universal green/yellow/red thresholds have been agreed; illustrative percentages above are not policy. Consider market characteristics and keep the smallest justified solution without adding a general policy/configuration platform.
  2. Define and document the maximum acceptable observation age and behavior for incomplete/mixed-age observations, taking the actual refresh cycle into account.
  3. Finalize compact cell labels and tooltip formatting while retaining the distinct meanings of liquidation distance and Cross maintenance utilization.

These open design choices do not prevent recording this issue. If a warning policy cannot be justified from the available information, request a concrete owner decision before assigning safety colors; do not silently invent thresholds.

Acceptance and scope

  • Verify Long/Short distance, boundary crossing, invalid/sentinel prices, exact units, separate isolated/Cross scopes, Phoenix risk tiers, nonpositive collateral and zero maintenance requirements.
  • Verify group worst-status/unknown counts, preserved view state and expiration of unchanged snapshots, failed reads and recovery. No missing or outdated observation may create a false all-clear.
  • Use OpenSpec for implementation. Update relevant existing project documentation and r35157_docs, removing obsolete claims and documenting the risk metric definitions, warning policy and freshness limitations.
  • This is a display and read-only data integration change. Faster polling/streaming, notifications, automatic collateral changes, liquidation avoidance trades and a new liquidation-price calculation engine are outside scope.
  • Do not commit or push implementation changes unless separately authorized. Creating this issue does not authorize starting implementation now.

Related: #100 (capital and valuation overview), #101 (TWAP display). The older #24/#25 concern the separate Jupiter calculation/alarm path and are not substitutes for this EMC feature.

## Problem and purpose EMC shows position size, capital, leverage, uPnL and TWAP progress, but it does not clearly show whether a perpetual position or shared Cross account is comfortably collateralized, under pressure or eligible for liquidation. uPnL and leverage alone do not answer that question. Add a read-only **Risk** column to the Perps tab, using venue-provided risk data wherever available. This protects Evelyn's capital by making the latest observed liquidation risk visible at the correct account/position level. ## Proposed presentation Illustrative labels, not agreed warning thresholds: | Row | Risk display | | --- | --- | | Jupiter isolated position | `8.4% to liq.` with a status indicator when a justified warning policy has been defined | | Phoenix isolated position | Venue risk status plus liquidation distance where available | | Phoenix Cross account | `OK · MM 19.5%`, or the venue's more severe risk state | | Position belonging to a Cross account | `Shared`, with a tooltip identifying the owning Cross account | | Missing, failed or expired observation | Explicit `Unknown` / `Stale` indication | Keep the existing Long/Short row backgrounds. Convey risk with text and a distinct indicator in the Risk cell, so users do not have to distinguish risk from direction by color alone. ## Isolated positions: Jupiter and Phoenix - Prefer each venue's reported liquidation price and the corresponding venue price used for risk calculations. Do not use an unrelated Ticker price or last traded price. - Show the adverse price movement to the reported liquidation boundary as a signed percentage of the current venue reference price: ```text Long: 100 × (current price - liquidation price) / current price Short: 100 × (liquidation price - current price) / current price ``` - Positive distance means the reported boundary is still ahead in the adverse direction. Zero/negative distance indicates the observed boundary has been reached/crossed; do not take an absolute value or describe this as proof that liquidation has already occurred. - Tooltip: venue status where supplied, current reference price, reported liquidation price, distance, observation time and any limitations. - Missing, nonpositive or sentinel liquidation prices (including Phoenix `-1`) are unavailable. They must not be interpreted as infinite safety or zero risk. An independently valid account risk classification may still be displayed. - Profitability is separate from liquidation risk. Do not use uPnL sign or a generic leverage cutoff to assign a healthy state. ## Phoenix Cross: assess the shared account - Risk belongs to the actual trader subaccount and its shared collateral pool. Display the main indicator on the existing **Cross** account row; do not invent independent collateral or a standalone safety rating for each child position. - Prefer Phoenix's own `riskTier`: `safe`, `atRisk`, `cancellable`, `liquidatable`, `backstopLiquidatable`, `highRisk`. Suggested mapping: green OK/Safe, yellow At risk, orange Cancellable, red Liquidatable or worse. Preserve the specific venue tier in the tooltip. - Show maintenance-margin utilization as: ```text MM utilization = 100 × maintenanceMargin / effectiveCollateral USD headroom = effectiveCollateral - maintenanceMargin ``` - This percentage measures margin utilization, not liquidation probability or a price-movement buffer. Around 100% is the maintenance boundary; exact eligibility follows the venue's risk classification and comparison rules. - Use Phoenix's **effective collateral**, which can include funding and risk discounts. Do not substitute EMC's closing `Value`, undiscounted equity or raw collateral balance. - Handle zero/negative effective collateral, zero maintenance requirement and accounts without positions explicitly; never divide by zero or invent a percentage. - Tooltip: exact venue tier, effective collateral, maintenance requirement, USD headroom, observation time and any limitations. Cross position tooltips must explain the shared risk scope. Any optional per-market liquidation estimate for Cross must state its assumptions about the other positions; it is not an independent position guarantee. ## Group summaries and observation freshness - Collapsed venue, wallet and root rows must still expose the worst known descendant risk plus the number of unknown/stale risk scopes. Count a shared Cross account once, not once per child position. - Never average liquidation distances, severity classifications or account MM percentages. A partial group must not appear unconditionally healthy when some required observations are unknown. - Preserve last-success values with their original observation timestamps after read failures. Show failed/expired risk as retained or stale rather than fresh green. Keep a previously observed critical state visible with its age/uncertainty instead of concealing it. - Display risk as **latest observed risk**, not a live safety guarantee. The existing service refresh cycle can take several minutes. - Age-based expiration must work even when the service returns an unchanged snapshot and no new read error. Existing UI snapshot polling must be able to update the freshness indication when the observation crosses the chosen age limit. - Failures and unknown risk data must remain isolated between wallets/venues. Existing position identities, totals, expansion, selection and TWAP behavior must be preserved. ## Available data and investigation findings Read-only checks confirmed: - The Jupiter overview response already contains `markPriceUsd` and `liquidationPriceUsd`. The current `RestJupiterPerpsOverview` DTO mapping drops them; extend the overview path rather than changing the separate signing/trading/alarm integration. Validate their units and matching identities before display. - Phoenix `GET /v1/view/trader/{pubkey}` returns `riskState`, `riskTier`, `effectiveCollateral`, `maintenanceMargin`, related margin thresholds and positions with `liquidationPrice`. This endpoint takes the **trader account public key**, not merely the wallet authority. Resolve and validate authority/PDA/subaccount membership using official account derivation/data; risk must not depend on having an active TWAP. - Actual Phoenix responses use amount objects with raw `value` and `decimals`; some position liquidation prices are `-1`. Validate the deployed response rather than assuming every price is actionable or all fields use the same scale. - Prefer these reported account risk values over implementing a new liquidation engine. If an essential value is absent or cannot be verified, expose it as unavailable instead of falling back to an unverified formula. - Reuse the existing background service/snapshot architecture, exact decimal arithmetic, bounded timeouts and Phoenix shared pacing/429 cooldown. EMC must not make venue requests directly. Sources: - [Phoenix Trader API](https://docs.phoenix.trade/api/trader/get-trader) - [Phoenix account health and risk tiers](https://docs.phoenix.trade/phoenix/margin-and-risk/account-health) - [Phoenix liquidation rules](https://docs.phoenix.trade/phoenix/margin-and-risk/liquidations) - [Phoenix effective collateral and margin math](https://docs.phoenix.trade/phoenix/margin-and-risk/margin-math) - [Phoenix SDK trader response types](https://github.com/Ellipsis-Labs/rise-public/blob/master/ts/src/types/trader.ts) ## Decisions to resolve in OpenSpec before implementation 1. Define defensible warning bands for isolated liquidation distance. No universal green/yellow/red thresholds have been agreed; illustrative percentages above are not policy. Consider market characteristics and keep the smallest justified solution without adding a general policy/configuration platform. 2. Define and document the maximum acceptable observation age and behavior for incomplete/mixed-age observations, taking the actual refresh cycle into account. 3. Finalize compact cell labels and tooltip formatting while retaining the distinct meanings of liquidation distance and Cross maintenance utilization. These open design choices do not prevent recording this issue. If a warning policy cannot be justified from the available information, request a concrete owner decision before assigning safety colors; do not silently invent thresholds. ## Acceptance and scope - Verify Long/Short distance, boundary crossing, invalid/sentinel prices, exact units, separate isolated/Cross scopes, Phoenix risk tiers, nonpositive collateral and zero maintenance requirements. - Verify group worst-status/unknown counts, preserved view state and expiration of unchanged snapshots, failed reads and recovery. No missing or outdated observation may create a false all-clear. - Use OpenSpec for implementation. Update relevant existing project documentation and `r35157_docs`, removing obsolete claims and documenting the risk metric definitions, warning policy and freshness limitations. - This is a display and read-only data integration change. Faster polling/streaming, notifications, automatic collateral changes, liquidation avoidance trades and a new liquidation-price calculation engine are outside scope. - Do not commit or push implementation changes unless separately authorized. Creating this issue does not authorize starting implementation now. Related: #100 (capital and valuation overview), #101 (TWAP display). The older #24/#25 concern the separate Jupiter calculation/alarm path and are not substitutes for this EMC feature.
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: r35157/com_r35157_nenjim-hubd-impl_ref#102