@0xmonaco/core 1.0.46 → 1.0.48
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/api/trading/api.js
CHANGED
|
@@ -668,6 +668,10 @@ export class TradingAPIImpl extends BaseAPI {
|
|
|
668
668
|
strategyKey: options.strategyKey,
|
|
669
669
|
useMasterBalance: options.useMasterBalance,
|
|
670
670
|
clientTwapId: options.clientTwapId,
|
|
671
|
+
executionStyle: options.executionStyle,
|
|
672
|
+
triggerPrice: options.triggerPrice,
|
|
673
|
+
triggerDirection: options.triggerDirection,
|
|
674
|
+
conditionalExpiry: options.conditionalExpiry,
|
|
671
675
|
};
|
|
672
676
|
return await this.makeAuthenticatedRequest(perpRoutes.orders.createTwap(), {
|
|
673
677
|
method: "POST",
|
|
@@ -1,6 +1,5 @@
|
|
|
1
|
-
import type {
|
|
2
|
-
export type { ResyncHandler, StatusHandler, WebSocketResyncInfo } from "@0xmonaco/types";
|
|
3
|
-
export type MessageHandler<T> = (data: T) => void;
|
|
1
|
+
import type { MonacoWebSocketConfig, SessionCredentials } from "@0xmonaco/types";
|
|
2
|
+
export type { MessageHandler, MonacoWebSocket, ResyncHandler, StatusHandler, WebSocketResyncInfo } from "@0xmonaco/types";
|
|
4
3
|
/**
|
|
5
4
|
* Options for {@link createMonacoWebSocket}. The reconnect/resync knobs and
|
|
6
5
|
* callbacks are shared with the main SDK config via {@link MonacoWebSocketConfig}
|
|
@@ -11,45 +10,3 @@ export interface MonacoWebSocketOptions extends MonacoWebSocketConfig {
|
|
|
11
10
|
/** Session keypair for authenticated channels (orders, balances, etc.) */
|
|
12
11
|
session?: SessionCredentials;
|
|
13
12
|
}
|
|
14
|
-
export interface MonacoWebSocket {
|
|
15
|
-
/** Connect to the WebSocket server */
|
|
16
|
-
connect: () => Promise<void>;
|
|
17
|
-
/** Disconnect from the WebSocket server */
|
|
18
|
-
disconnect: () => void;
|
|
19
|
-
/** Check if currently connected */
|
|
20
|
-
isConnected: () => boolean;
|
|
21
|
-
/** Get current websocket connection status */
|
|
22
|
-
getStatus: () => WebSocketStatus;
|
|
23
|
-
/** Set (or clear) the session keypair used to authenticate the connection */
|
|
24
|
-
setSessionKeypair: (credentials: SessionCredentials | undefined) => void;
|
|
25
|
-
/** Subscribe to order events (requires authentication) */
|
|
26
|
-
orders: (tradingPairId: string, tradingMode: TradingMode, handler: MessageHandler<OrderEvent>) => () => void;
|
|
27
|
-
/** Subscribe to orderbook events (public) */
|
|
28
|
-
orderbook: (tradingPairId: string, tradingMode: TradingMode, magnitude: number, quotationMode: OrderbookQuotationMode, handler: MessageHandler<OrderbookEvent>) => () => void;
|
|
29
|
-
/** Subscribe to OHLCV candlestick events (public) */
|
|
30
|
-
ohlcv: (tradingPairId: string, tradingMode: TradingMode, interval: Interval, handler: MessageHandler<OHLCVEvent>, priceType?: OHLCVPriceType) => () => void;
|
|
31
|
-
/** Subscribe to trade events (public) */
|
|
32
|
-
trades: (tradingPairId: string, handler: MessageHandler<TradeEvent>) => () => void;
|
|
33
|
-
/** Subscribe to user movement events (requires authentication) */
|
|
34
|
-
movements: (handler: MessageHandler<UserMovementEvent>) => () => void;
|
|
35
|
-
/** Subscribe to user order events for all trading pairs (requires authentication) */
|
|
36
|
-
userOrders: (handler: MessageHandler<OrderEvent>) => () => void;
|
|
37
|
-
/** Subscribe to user balance events (requires authentication) */
|
|
38
|
-
balances: (handler: MessageHandler<UserBalanceEvent>) => () => void;
|
|
39
|
-
/** Subscribe to conditional TP/SL lifecycle events (requires authentication) */
|
|
40
|
-
conditionalOrders: (handler: MessageHandler<ConditionalOrderEvent>, tradingPairId?: string) => () => void;
|
|
41
|
-
/** Subscribe to TWAP parent-order lifecycle events (requires authentication) */
|
|
42
|
-
twapOrders: (handler: MessageHandler<TwapOrderEvent>, tradingPairId?: string) => () => void;
|
|
43
|
-
/** Subscribe to position state updates (requires authentication); omit `tradingPairId` for all pairs */
|
|
44
|
-
positions: (handler: MessageHandler<PositionEvent>, tradingPairId?: string) => () => void;
|
|
45
|
-
/** Subscribe to liquidation alerts (requires authentication); omit `tradingPairId` for all pairs */
|
|
46
|
-
liquidations: (handler: MessageHandler<LiquidationEvent>, tradingPairId?: string) => () => void;
|
|
47
|
-
/** Subscribe to account-level margin health updates for the authenticated user (requires authentication) */
|
|
48
|
-
account: (handler: MessageHandler<AccountEvent>) => () => void;
|
|
49
|
-
/** Subscribe to market lifecycle + config changes (public); omit `tradingPairId` for all markets */
|
|
50
|
-
instruments: (handler: MessageHandler<InstrumentEvent>, tradingPairId?: string) => () => void;
|
|
51
|
-
/** Subscribe to per-market statistics for one trading pair (public) */
|
|
52
|
-
marketStats: (tradingPairId: string, handler: MessageHandler<MarketStatsEvent>) => () => void;
|
|
53
|
-
/** Subscribe to the all-markets statistics summary (public) */
|
|
54
|
-
marketStatsAll: (handler: MessageHandler<MarketStatsAllEvent>) => () => void;
|
|
55
|
-
}
|
|
@@ -7,11 +7,6 @@ const CONNECTION_TIMEOUT = 10000;
|
|
|
7
7
|
const HEARTBEAT_INTERVAL = 15000;
|
|
8
8
|
const MAX_RECONNECT_DELAY = 30000;
|
|
9
9
|
const RECONNECT_BASE_DELAY = 1000;
|
|
10
|
-
const CONDITIONAL_ORDER_REASONS = ["created", "activated", "cancelled", "parent_cancelled", "triggered", "failed", "oco_cancelled"];
|
|
11
|
-
const CONDITIONAL_ORDER_CONDITION_TYPES = ["STOP_LOSS", "TAKE_PROFIT"];
|
|
12
|
-
const CONDITIONAL_ORDER_TRIGGER_SOURCES = ["MARK_PRICE"];
|
|
13
|
-
const CONDITIONAL_ORDER_STATES = ["PENDING_PARENT", "ACTIVE", "TRIGGERING", "TRIGGERED", "CANCELLED", "EXPIRED", "FAILED"];
|
|
14
|
-
const CONDITIONAL_ORDER_ASSOCIATION_TYPES = ["POSITION", "PARENT_ORDER"];
|
|
15
10
|
const TWAP_ORDER_STATES = ["PENDING", "ACTIVE", "COMPLETED", "CANCELLED"];
|
|
16
11
|
const INSTRUMENT_CHANGE_KINDS = ["listing", "delisting", "halt", "unhalt", "config_change"];
|
|
17
12
|
function isRecord(value) {
|
|
@@ -40,6 +35,19 @@ function readBoolean(source, field) {
|
|
|
40
35
|
}
|
|
41
36
|
return value;
|
|
42
37
|
}
|
|
38
|
+
/**
|
|
39
|
+
* Read a wire sequence counter: a non-negative safe integer. The server
|
|
40
|
+
* serializes Rust `u64` sequence fields as plain JSON numbers, so a negative,
|
|
41
|
+
* fractional, or unsafe (> 2^53 - 1) value is a malformed frame that would
|
|
42
|
+
* corrupt ordering/dedup logic — reject it rather than pass it through.
|
|
43
|
+
*/
|
|
44
|
+
function readSequence(source, field) {
|
|
45
|
+
const value = source[field];
|
|
46
|
+
if (typeof value !== "number" || !Number.isSafeInteger(value) || value < 0) {
|
|
47
|
+
throw new Error(`Invalid WebSocket event: ${field} must be a non-negative safe integer`);
|
|
48
|
+
}
|
|
49
|
+
return value;
|
|
50
|
+
}
|
|
43
51
|
function readOptionalNumber(source, field) {
|
|
44
52
|
const value = source[field];
|
|
45
53
|
if (value === undefined || value === null)
|
|
@@ -63,14 +71,20 @@ function readEnum(source, field, allowed) {
|
|
|
63
71
|
}
|
|
64
72
|
return value;
|
|
65
73
|
}
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
+
/**
|
|
75
|
+
* Read an optional wire enum leniently.
|
|
76
|
+
*
|
|
77
|
+
* Absent, `null`, and a present-but-empty string all mean "not set": server
|
|
78
|
+
* side these fields are `Option<..>` over closed enums, so `""` is a malformed
|
|
79
|
+
* value rather than a variant this SDK version predates, and letting it through
|
|
80
|
+
* would put a string the union does not contain onto the typed surface. It is
|
|
81
|
+
* mapped to absent rather than thrown on, because throwing would drop the whole
|
|
82
|
+
* frame over one optional field. A non-empty value is passed through untouched,
|
|
83
|
+
* whether or not the SDK recognizes it.
|
|
84
|
+
*/
|
|
85
|
+
function readOptionalEnumValue(source, field) {
|
|
86
|
+
const value = readOptionalString(source, field);
|
|
87
|
+
return value === undefined || value.length === 0 ? undefined : value;
|
|
74
88
|
}
|
|
75
89
|
function parseConditionalOrderEvent(rawData) {
|
|
76
90
|
if (!isRecord(rawData)) {
|
|
@@ -81,6 +95,13 @@ function parseConditionalOrderEvent(rawData) {
|
|
|
81
95
|
}
|
|
82
96
|
const data = keysToCamelCase(rawData.data);
|
|
83
97
|
return {
|
|
98
|
+
// event_type is the event-class discriminator, validated strictly so a
|
|
99
|
+
// mis-routed frame is rejected rather than parsed as a conditional order.
|
|
100
|
+
// The value fields below stay lenient — read as strings and cast, never
|
|
101
|
+
// checked against an allow-list — so an unexpected *value* never drops the
|
|
102
|
+
// whole update (0XM-2627). The parse throw is swallowed by the
|
|
103
|
+
// message-handler catch, so a strict enum here means a silently lost frame
|
|
104
|
+
// with nothing surfaced to the consumer.
|
|
84
105
|
eventType: readEnum(rawData, "event_type", ["conditional_order_update"]),
|
|
85
106
|
userId: readString(rawData, "user_id"),
|
|
86
107
|
data: {
|
|
@@ -89,27 +110,29 @@ function parseConditionalOrderEvent(rawData) {
|
|
|
89
110
|
marginAccountId: readString(data, "marginAccountId"),
|
|
90
111
|
positionId: readOptionalString(data, "positionId"),
|
|
91
112
|
parentOrderId: readOptionalString(data, "parentOrderId"),
|
|
92
|
-
associationType:
|
|
113
|
+
associationType: readOptionalEnumValue(data, "associationType"),
|
|
93
114
|
linkedGroupId: readOptionalString(data, "linkedGroupId"),
|
|
94
|
-
conditionType:
|
|
95
|
-
triggerSource:
|
|
115
|
+
conditionType: readString(data, "conditionType"),
|
|
116
|
+
triggerSource: readString(data, "triggerSource"),
|
|
96
117
|
triggerPrice: readString(data, "triggerPrice"),
|
|
97
|
-
side:
|
|
98
|
-
positionSide:
|
|
99
|
-
orderType:
|
|
118
|
+
side: readString(data, "side"),
|
|
119
|
+
positionSide: readString(data, "positionSide"),
|
|
120
|
+
orderType: readString(data, "orderType"),
|
|
100
121
|
limitPrice: readOptionalString(data, "limitPrice"),
|
|
101
122
|
quantity: readOptionalString(data, "quantity"),
|
|
102
123
|
slippageToleranceBps: readOptionalNumber(data, "slippageToleranceBps"),
|
|
103
124
|
reduceOnly: readBoolean(data, "reduceOnly"),
|
|
104
|
-
timeInForce:
|
|
105
|
-
state:
|
|
125
|
+
timeInForce: readOptionalEnumValue(data, "timeInForce"),
|
|
126
|
+
state: readString(data, "state"),
|
|
106
127
|
triggeredOrderId: readOptionalString(data, "triggeredOrderId"),
|
|
107
128
|
triggeredAt: readOptionalString(data, "triggeredAt"),
|
|
108
129
|
activatedAt: readOptionalString(data, "activatedAt"),
|
|
109
130
|
cancelledAt: readOptionalString(data, "cancelledAt"),
|
|
110
131
|
expiresAt: readOptionalString(data, "expiresAt"),
|
|
111
132
|
failureReason: readOptionalString(data, "failureReason"),
|
|
112
|
-
|
|
133
|
+
// Free-form on the wire (the server field is a plain string), so it is
|
|
134
|
+
// passed through untouched rather than matched against a value list.
|
|
135
|
+
reason: readString(data, "reason"),
|
|
113
136
|
updatedAt: readString(data, "updatedAt"),
|
|
114
137
|
},
|
|
115
138
|
};
|
|
@@ -194,6 +217,10 @@ function parseAccountEvent(rawData) {
|
|
|
194
217
|
userId: readString(rawData, "user_id"),
|
|
195
218
|
data: {
|
|
196
219
|
marginAccountId: readString(data, "marginAccountId"),
|
|
220
|
+
// Monotonic per-account publish counter (0XM-2498): a plain JSON number on
|
|
221
|
+
// the wire, used to order/dedupe frames across reconnect races. Must be a
|
|
222
|
+
// non-negative safe integer — anything else is a malformed frame.
|
|
223
|
+
sequence: readSequence(data, "sequence"),
|
|
197
224
|
equity: readString(data, "equity"),
|
|
198
225
|
collateral: readString(data, "collateral"),
|
|
199
226
|
freeCollateral: readString(data, "freeCollateral"),
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@0xmonaco/core",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.48",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"homepage": "https://docs.0xmonaco.com/sdk/typescript",
|
|
6
6
|
"main": "./dist/index.js",
|
|
@@ -19,8 +19,8 @@
|
|
|
19
19
|
"viem": "^2.45.2"
|
|
20
20
|
},
|
|
21
21
|
"dependencies": {
|
|
22
|
-
"@0xmonaco/contracts": "1.0.
|
|
23
|
-
"@0xmonaco/types": "1.0.
|
|
22
|
+
"@0xmonaco/contracts": "1.0.48",
|
|
23
|
+
"@0xmonaco/types": "1.0.48",
|
|
24
24
|
"@noble/curves": "^1.9.1",
|
|
25
25
|
"@noble/hashes": "^1.8.0",
|
|
26
26
|
"http-status-codes": "^2.3.0"
|