Skip to content
10 changes: 9 additions & 1 deletion packages/perps-controller/CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,14 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0

## [Unreleased]

### Added

- Add typed Scale analytics property, interaction, and setting constants ([#9989](https://github.com/MetaMask/core/pull/9989))

### Fixed

- Preserve every accepted HyperLiquid Scale rung after a partial batch rejection, including `waitingForFill` and `waitingForTrigger` statuses and responses wrapped in `ApiRequestError`; cancel unclassified rungs by client order ID before returning failure; keep `childOrderIds` limited to resting orders; expose each accepted status through `acceptedChildren`; distinguish `acceptedSize` from the full `submittedSize`; and report `weightedAverageLimitPrice` separately from the fill-weighted `averagePrice` ([#9989](https://github.com/MetaMask/core/pull/9989))

## [13.1.0]

### Added
Expand Down Expand Up @@ -99,7 +107,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
- `OrderType` is a wider union again, so — exactly as for the trigger types added in 11.0.0 — any consumer signature that narrows it back to a smaller set no longer accepts a value typed `OrderType`. Such signatures must widen to `OrderType` or narrow explicitly at the call site.
- A strategy placement expands one request into an execution schedule rather than a single resting order, so `OrderResult.orderId` carries a _handle_ — a venue TWAP id, or a client-generated group/session id — rather than an exchange order id. Its documentation says so; the individual exchange ids are in `childOrderIds`.
- `twap` slices the size over `OrderParams.twapDuration` whole minutes, optionally varying each suborder's size by up to ±20% with `OrderParams.twapRandomize`. On HyperLiquid it is submitted through the venue's own TWAP action, not the order book, and `HYPERLIQUID_TWAP_LIMITS` bounds the window to the pinned SDK's 5–1440-minute range.
- `scale` fans out `OrderParams.scaleNumOrders` limit orders on an inclusive price ladder between `OrderParams.scaleMinPrice` and `OrderParams.scaleMaxPrice`, submitted as a single batch. Sizes are split in whole units of the asset's size grid, so the rungs sum to exactly the submitted size. The batch is not atomic — the venue can rest some rungs and reject othersso `OrderResult.submittedSize` reports only the rungs that actually rested.
- `scale` fans out `OrderParams.scaleNumOrders` limit orders on an inclusive price ladder between `OrderParams.scaleMinPrice` and `OrderParams.scaleMaxPrice`, submitted as a single batch. Sizes are split in whole units of the asset's size grid, so the rungs sum to exactly the submitted size. The batch is not atomic. The venue can accept some rungs and reject others, so `OrderResult.submittedSize` reports the full normalized batch while `acceptedSize`, `acceptedChildren`, and `weightedAverageLimitPrice` describe the accepted rungs. `childOrderIds` remains limited to resting, cancellable orders, and `averagePrice` describes fills only.
- The venue applies its minimum order value to what it receives, not to the strategy total: a `scale` ladder's notional must leave every submitted rung above the per-order minimum, and a `twap`'s total must clear the venue's own minimum TWAP size (`HYPERLIQUID_TWAP_LIMITS.MinNotionalUsd`). Both are rejected locally rather than by the exchange. The ladder check needs the asset's size grid, so it runs during placement — before anything is signed — rather than in `validateOrder`, which cannot see the grid and could only guess.
- A `chase` verifies its order is still live whenever its own price stops showing on the book, so an order that fills without the loop noticing ends the session and releases its concurrency slot instead of holding both until the window closes.
- A `chase` interrupted by `disconnect` resolves as a failure with `ORDER_CHASE_ABANDONED` rather than a success, because no strategy is running behind it. Interrupted anywhere before its submission it signs nothing at all. Interrupted while that submission is in flight — the one window it cannot check ahead of — it tries to take the order back before returning, through the client it signed with rather than one asked for after the teardown, so an account switch cannot strand it. That attempt is best-effort: the venue can refuse the cancel, and the transport underneath the client may already be closing. When it does not take, the order is reported in `OrderResult.childOrderIds`, where the ordinary single-order cancel can still reach it for as long as the provider signs as the account that placed it.
Expand Down
10 changes: 10 additions & 0 deletions packages/perps-controller/src/constants/eventNames.ts
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,10 @@ export const PERPS_EVENT_PROPERTY = {
ORDER_SIZE: 'order_size',
MARGIN_USED: 'margin_used',
ORDER_TYPE: 'order_type', // lowercase per dashboard
SCALE_ORDER_COUNT: 'scale_order_count',
SCALE_RANGE_PCT: 'scale_range_pct',
SCALE_SKEW: 'scale_skew',
REDUCE_ONLY: 'reduce_only',
ORDER_TIMESTAMP: 'order_timestamp',
LIMIT_PRICE: 'limit_price',
FEES: 'fees',
Expand Down Expand Up @@ -478,6 +482,8 @@ export const PERPS_EVENT_VALUE = {
SLIPPAGE_CONFIG_OPENED: 'slippage_config_opened',
SLIPPAGE_CONFIG_CHANGED: 'slippage_config_changed',
SLIPPAGE_LIMIT_BLOCKED_ORDER: 'slippage_limit_blocked_order',
SCALE_CONFIG_CHANGED: 'scale_config_changed',
SCALE_VALIDATION_ERROR_SHOWN: 'scale_validation_error_shown',
// Auto Close TP/SL RoE sign toggle
TPSL_ROE_SIGN_TOGGLED: 'tpsl_roe_sign_toggled',
// Discovery analytics
Expand Down Expand Up @@ -587,6 +593,10 @@ export const PERPS_EVENT_VALUE = {
SETTING_TYPE: {
LEVERAGE: 'leverage',
SLIPPAGE: 'slippage',
SCALE_START_PRICE: 'start_price',
SCALE_END_PRICE: 'end_price',
SCALE_TOTAL_ORDERS: 'total_orders',
SCALE_SIZE_SKEW: 'size_skew',
},
SCREEN_NAME: {
CONNECTION_ERROR: 'connection_error',
Expand Down
1 change: 1 addition & 0 deletions packages/perps-controller/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -198,6 +198,7 @@ export type {
TPSLTrackingData,
OrderParams,
OrderResult,
ScaleOrderChild,
ChaseOrder,
ChaseOrderMaxDistanceReached,
ChaseOrderStatus,
Expand Down
Loading