hedgequantx 2.9.31 → 2.9.32
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/package.json +1 -1
- package/src/pages/ai-agents-ui.js +25 -14
- package/src/services/rithmic/protobuf.js +54 -46
package/package.json
CHANGED
|
@@ -334,32 +334,43 @@ const drawConnectionTest = async (agents, boxWidth, clearWithBanner) => {
|
|
|
334
334
|
|
|
335
335
|
const W = boxWidth - 2;
|
|
336
336
|
|
|
337
|
-
// Show loading box with
|
|
337
|
+
// Show loading box with spinner inside
|
|
338
338
|
clearWithBanner();
|
|
339
339
|
console.log(chalk.cyan('╔' + '═'.repeat(W) + '╗'));
|
|
340
340
|
console.log(chalk.cyan('║') + chalk.yellow.bold(centerText('AI AGENTS CONNECTION TEST', W)) + chalk.cyan('║'));
|
|
341
341
|
console.log(chalk.cyan('╠' + '═'.repeat(W) + '╣'));
|
|
342
|
-
console.log(chalk.cyan('║') + ' '.repeat(W) + chalk.cyan('║'));
|
|
343
|
-
console.log(chalk.cyan('║') + ' '.repeat(W) + chalk.cyan('║'));
|
|
344
|
-
console.log(chalk.cyan('╚' + '═'.repeat(W) + '╝'));
|
|
345
|
-
console.log('');
|
|
346
342
|
|
|
347
|
-
// Spinner
|
|
343
|
+
// Spinner inside the box - use custom rendering
|
|
344
|
+
const spinnerFrames = ['⠋', '⠙', '⠹', '⠸', '⠼', '⠴', '⠦', '⠧', '⠇', '⠏'];
|
|
348
345
|
const spinnerText = 'Testing connections...';
|
|
349
|
-
|
|
346
|
+
let frameIdx = 0;
|
|
347
|
+
|
|
348
|
+
const renderSpinnerLine = () => {
|
|
349
|
+
const frame = spinnerFrames[frameIdx % spinnerFrames.length];
|
|
350
|
+
const content = chalk.yellow(frame + ' ' + spinnerText);
|
|
351
|
+
const contentLen = frame.length + 1 + spinnerText.length;
|
|
352
|
+
const leftPad = Math.floor((W - contentLen) / 2);
|
|
353
|
+
const rightPad = W - contentLen - leftPad;
|
|
354
|
+
return chalk.cyan('║') + ' '.repeat(leftPad) + content + ' '.repeat(rightPad) + chalk.cyan('║');
|
|
355
|
+
};
|
|
356
|
+
|
|
357
|
+
// Initial draw
|
|
358
|
+
console.log(renderSpinnerLine());
|
|
359
|
+
console.log(chalk.cyan('╚' + '═'.repeat(W) + '╝'));
|
|
350
360
|
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
361
|
+
// Start spinner animation
|
|
362
|
+
const spinnerInterval = setInterval(() => {
|
|
363
|
+
frameIdx++;
|
|
364
|
+
process.stdout.write('\x1b[2A'); // Move up 2 lines
|
|
365
|
+
console.log(renderSpinnerLine());
|
|
366
|
+
console.log(chalk.cyan('╚' + '═'.repeat(W) + '╝'));
|
|
367
|
+
}, 80);
|
|
357
368
|
|
|
358
369
|
// Run pre-flight check
|
|
359
370
|
const results = await runPreflightCheck(agents);
|
|
360
371
|
|
|
361
372
|
// Stop spinner
|
|
362
|
-
|
|
373
|
+
clearInterval(spinnerInterval);
|
|
363
374
|
|
|
364
375
|
// Clear and redraw with results
|
|
365
376
|
clearWithBanner();
|
|
@@ -124,74 +124,78 @@ function skipField(buffer, offset, wireType) {
|
|
|
124
124
|
|
|
125
125
|
/**
|
|
126
126
|
* Manually decode AccountPnL from raw bytes
|
|
127
|
+
* Skips 4-byte length prefix if present
|
|
127
128
|
*/
|
|
128
129
|
function decodeAccountPnL(buffer) {
|
|
130
|
+
// Skip 4-byte length prefix
|
|
131
|
+
const data = buffer.length > 4 ? buffer.slice(4) : buffer;
|
|
132
|
+
|
|
129
133
|
const result = {};
|
|
130
134
|
let offset = 0;
|
|
131
135
|
|
|
132
|
-
while (offset <
|
|
136
|
+
while (offset < data.length) {
|
|
133
137
|
try {
|
|
134
|
-
const [tag, tagOffset] = readVarint(
|
|
138
|
+
const [tag, tagOffset] = readVarint(data, offset);
|
|
135
139
|
const wireType = tag & 0x7;
|
|
136
140
|
const fieldNumber = tag >>> 3;
|
|
137
141
|
offset = tagOffset;
|
|
138
142
|
|
|
139
143
|
switch (fieldNumber) {
|
|
140
144
|
case PNL_FIELDS.TEMPLATE_ID:
|
|
141
|
-
[result.templateId, offset] = readVarint(
|
|
145
|
+
[result.templateId, offset] = readVarint(data, offset);
|
|
142
146
|
break;
|
|
143
147
|
case PNL_FIELDS.IS_SNAPSHOT:
|
|
144
|
-
const [isSnap, snapOffset] = readVarint(
|
|
148
|
+
const [isSnap, snapOffset] = readVarint(data, offset);
|
|
145
149
|
result.isSnapshot = isSnap !== 0;
|
|
146
150
|
offset = snapOffset;
|
|
147
151
|
break;
|
|
148
152
|
case PNL_FIELDS.FCM_ID:
|
|
149
|
-
[result.fcmId, offset] = readLengthDelimited(
|
|
153
|
+
[result.fcmId, offset] = readLengthDelimited(data, offset);
|
|
150
154
|
break;
|
|
151
155
|
case PNL_FIELDS.IB_ID:
|
|
152
|
-
[result.ibId, offset] = readLengthDelimited(
|
|
156
|
+
[result.ibId, offset] = readLengthDelimited(data, offset);
|
|
153
157
|
break;
|
|
154
158
|
case PNL_FIELDS.ACCOUNT_ID:
|
|
155
|
-
[result.accountId, offset] = readLengthDelimited(
|
|
159
|
+
[result.accountId, offset] = readLengthDelimited(data, offset);
|
|
156
160
|
break;
|
|
157
161
|
case PNL_FIELDS.ACCOUNT_BALANCE:
|
|
158
|
-
[result.accountBalance, offset] = readLengthDelimited(
|
|
162
|
+
[result.accountBalance, offset] = readLengthDelimited(data, offset);
|
|
159
163
|
break;
|
|
160
164
|
case PNL_FIELDS.CASH_ON_HAND:
|
|
161
|
-
[result.cashOnHand, offset] = readLengthDelimited(
|
|
165
|
+
[result.cashOnHand, offset] = readLengthDelimited(data, offset);
|
|
162
166
|
break;
|
|
163
167
|
case PNL_FIELDS.MARGIN_BALANCE:
|
|
164
|
-
[result.marginBalance, offset] = readLengthDelimited(
|
|
168
|
+
[result.marginBalance, offset] = readLengthDelimited(data, offset);
|
|
165
169
|
break;
|
|
166
170
|
case PNL_FIELDS.MIN_ACCOUNT_BALANCE:
|
|
167
|
-
[result.minAccountBalance, offset] = readLengthDelimited(
|
|
171
|
+
[result.minAccountBalance, offset] = readLengthDelimited(data, offset);
|
|
168
172
|
break;
|
|
169
173
|
case PNL_FIELDS.OPEN_POSITION_PNL:
|
|
170
|
-
[result.openPositionPnl, offset] = readLengthDelimited(
|
|
174
|
+
[result.openPositionPnl, offset] = readLengthDelimited(data, offset);
|
|
171
175
|
break;
|
|
172
176
|
case PNL_FIELDS.CLOSED_POSITION_PNL:
|
|
173
|
-
[result.closedPositionPnl, offset] = readLengthDelimited(
|
|
177
|
+
[result.closedPositionPnl, offset] = readLengthDelimited(data, offset);
|
|
174
178
|
break;
|
|
175
179
|
case PNL_FIELDS.DAY_PNL:
|
|
176
|
-
[result.dayPnl, offset] = readLengthDelimited(
|
|
180
|
+
[result.dayPnl, offset] = readLengthDelimited(data, offset);
|
|
177
181
|
break;
|
|
178
182
|
case PNL_FIELDS.DAY_OPEN_PNL:
|
|
179
|
-
[result.dayOpenPnl, offset] = readLengthDelimited(
|
|
183
|
+
[result.dayOpenPnl, offset] = readLengthDelimited(data, offset);
|
|
180
184
|
break;
|
|
181
185
|
case PNL_FIELDS.DAY_CLOSED_PNL:
|
|
182
|
-
[result.dayClosedPnl, offset] = readLengthDelimited(
|
|
186
|
+
[result.dayClosedPnl, offset] = readLengthDelimited(data, offset);
|
|
183
187
|
break;
|
|
184
188
|
case PNL_FIELDS.AVAILABLE_BUYING_POWER:
|
|
185
|
-
[result.availableBuyingPower, offset] = readLengthDelimited(
|
|
189
|
+
[result.availableBuyingPower, offset] = readLengthDelimited(data, offset);
|
|
186
190
|
break;
|
|
187
191
|
case PNL_FIELDS.SSBOE:
|
|
188
|
-
[result.ssboe, offset] = readVarint(
|
|
192
|
+
[result.ssboe, offset] = readVarint(data, offset);
|
|
189
193
|
break;
|
|
190
194
|
case PNL_FIELDS.USECS:
|
|
191
|
-
[result.usecs, offset] = readVarint(
|
|
195
|
+
[result.usecs, offset] = readVarint(data, offset);
|
|
192
196
|
break;
|
|
193
197
|
default:
|
|
194
|
-
offset = skipField(
|
|
198
|
+
offset = skipField(data, offset, wireType);
|
|
195
199
|
}
|
|
196
200
|
} catch (error) {
|
|
197
201
|
break;
|
|
@@ -203,95 +207,99 @@ function decodeAccountPnL(buffer) {
|
|
|
203
207
|
|
|
204
208
|
/**
|
|
205
209
|
* Manually decode InstrumentPnLPositionUpdate from raw bytes
|
|
210
|
+
* Skips 4-byte length prefix if present
|
|
206
211
|
*/
|
|
207
212
|
function decodeInstrumentPnL(buffer) {
|
|
213
|
+
// Skip 4-byte length prefix
|
|
214
|
+
const data = buffer.length > 4 ? buffer.slice(4) : buffer;
|
|
215
|
+
|
|
208
216
|
const result = {};
|
|
209
217
|
let offset = 0;
|
|
210
218
|
|
|
211
|
-
while (offset <
|
|
219
|
+
while (offset < data.length) {
|
|
212
220
|
try {
|
|
213
|
-
const [tag, tagOffset] = readVarint(
|
|
221
|
+
const [tag, tagOffset] = readVarint(data, offset);
|
|
214
222
|
const wireType = tag & 0x7;
|
|
215
223
|
const fieldNumber = tag >>> 3;
|
|
216
224
|
offset = tagOffset;
|
|
217
225
|
|
|
218
226
|
switch (fieldNumber) {
|
|
219
227
|
case INSTRUMENT_PNL_FIELDS.TEMPLATE_ID:
|
|
220
|
-
[result.templateId, offset] = readVarint(
|
|
228
|
+
[result.templateId, offset] = readVarint(data, offset);
|
|
221
229
|
break;
|
|
222
230
|
case INSTRUMENT_PNL_FIELDS.IS_SNAPSHOT:
|
|
223
|
-
const [isSnap, snapOffset] = readVarint(
|
|
231
|
+
const [isSnap, snapOffset] = readVarint(data, offset);
|
|
224
232
|
result.isSnapshot = isSnap !== 0;
|
|
225
233
|
offset = snapOffset;
|
|
226
234
|
break;
|
|
227
235
|
case INSTRUMENT_PNL_FIELDS.FCM_ID:
|
|
228
|
-
[result.fcmId, offset] = readLengthDelimited(
|
|
236
|
+
[result.fcmId, offset] = readLengthDelimited(data, offset);
|
|
229
237
|
break;
|
|
230
238
|
case INSTRUMENT_PNL_FIELDS.IB_ID:
|
|
231
|
-
[result.ibId, offset] = readLengthDelimited(
|
|
239
|
+
[result.ibId, offset] = readLengthDelimited(data, offset);
|
|
232
240
|
break;
|
|
233
241
|
case INSTRUMENT_PNL_FIELDS.ACCOUNT_ID:
|
|
234
|
-
[result.accountId, offset] = readLengthDelimited(
|
|
242
|
+
[result.accountId, offset] = readLengthDelimited(data, offset);
|
|
235
243
|
break;
|
|
236
244
|
case INSTRUMENT_PNL_FIELDS.SYMBOL:
|
|
237
|
-
[result.symbol, offset] = readLengthDelimited(
|
|
245
|
+
[result.symbol, offset] = readLengthDelimited(data, offset);
|
|
238
246
|
break;
|
|
239
247
|
case INSTRUMENT_PNL_FIELDS.EXCHANGE:
|
|
240
|
-
[result.exchange, offset] = readLengthDelimited(
|
|
248
|
+
[result.exchange, offset] = readLengthDelimited(data, offset);
|
|
241
249
|
break;
|
|
242
250
|
case INSTRUMENT_PNL_FIELDS.PRODUCT_CODE:
|
|
243
|
-
[result.productCode, offset] = readLengthDelimited(
|
|
251
|
+
[result.productCode, offset] = readLengthDelimited(data, offset);
|
|
244
252
|
break;
|
|
245
253
|
case INSTRUMENT_PNL_FIELDS.BUY_QTY:
|
|
246
|
-
[result.buyQty, offset] = readVarint(
|
|
254
|
+
[result.buyQty, offset] = readVarint(data, offset);
|
|
247
255
|
break;
|
|
248
256
|
case INSTRUMENT_PNL_FIELDS.SELL_QTY:
|
|
249
|
-
[result.sellQty, offset] = readVarint(
|
|
257
|
+
[result.sellQty, offset] = readVarint(data, offset);
|
|
250
258
|
break;
|
|
251
259
|
case INSTRUMENT_PNL_FIELDS.FILL_BUY_QTY:
|
|
252
|
-
[result.fillBuyQty, offset] = readVarint(
|
|
260
|
+
[result.fillBuyQty, offset] = readVarint(data, offset);
|
|
253
261
|
break;
|
|
254
262
|
case INSTRUMENT_PNL_FIELDS.FILL_SELL_QTY:
|
|
255
|
-
[result.fillSellQty, offset] = readVarint(
|
|
263
|
+
[result.fillSellQty, offset] = readVarint(data, offset);
|
|
256
264
|
break;
|
|
257
265
|
case INSTRUMENT_PNL_FIELDS.NET_QUANTITY:
|
|
258
|
-
[result.netQuantity, offset] = readVarint(
|
|
266
|
+
[result.netQuantity, offset] = readVarint(data, offset);
|
|
259
267
|
break;
|
|
260
268
|
case INSTRUMENT_PNL_FIELDS.OPEN_POSITION_QUANTITY:
|
|
261
|
-
[result.openPositionQuantity, offset] = readVarint(
|
|
269
|
+
[result.openPositionQuantity, offset] = readVarint(data, offset);
|
|
262
270
|
break;
|
|
263
271
|
case INSTRUMENT_PNL_FIELDS.AVG_OPEN_FILL_PRICE:
|
|
264
272
|
// Double is 64-bit fixed
|
|
265
273
|
if (wireType === 1) {
|
|
266
|
-
result.avgOpenFillPrice =
|
|
274
|
+
result.avgOpenFillPrice = data.readDoubleLE(offset);
|
|
267
275
|
offset += 8;
|
|
268
276
|
} else {
|
|
269
|
-
offset = skipField(
|
|
277
|
+
offset = skipField(data, offset, wireType);
|
|
270
278
|
}
|
|
271
279
|
break;
|
|
272
280
|
case INSTRUMENT_PNL_FIELDS.OPEN_POSITION_PNL:
|
|
273
|
-
[result.openPositionPnl, offset] = readLengthDelimited(
|
|
281
|
+
[result.openPositionPnl, offset] = readLengthDelimited(data, offset);
|
|
274
282
|
break;
|
|
275
283
|
case INSTRUMENT_PNL_FIELDS.CLOSED_POSITION_PNL:
|
|
276
|
-
[result.closedPositionPnl, offset] = readLengthDelimited(
|
|
284
|
+
[result.closedPositionPnl, offset] = readLengthDelimited(data, offset);
|
|
277
285
|
break;
|
|
278
286
|
case INSTRUMENT_PNL_FIELDS.DAY_PNL:
|
|
279
|
-
[result.dayPnl, offset] = readLengthDelimited(
|
|
287
|
+
[result.dayPnl, offset] = readLengthDelimited(data, offset);
|
|
280
288
|
break;
|
|
281
289
|
case INSTRUMENT_PNL_FIELDS.DAY_OPEN_PNL:
|
|
282
|
-
[result.dayOpenPnl, offset] = readLengthDelimited(
|
|
290
|
+
[result.dayOpenPnl, offset] = readLengthDelimited(data, offset);
|
|
283
291
|
break;
|
|
284
292
|
case INSTRUMENT_PNL_FIELDS.DAY_CLOSED_PNL:
|
|
285
|
-
[result.dayClosedPnl, offset] = readLengthDelimited(
|
|
293
|
+
[result.dayClosedPnl, offset] = readLengthDelimited(data, offset);
|
|
286
294
|
break;
|
|
287
295
|
case INSTRUMENT_PNL_FIELDS.SSBOE:
|
|
288
|
-
[result.ssboe, offset] = readVarint(
|
|
296
|
+
[result.ssboe, offset] = readVarint(data, offset);
|
|
289
297
|
break;
|
|
290
298
|
case INSTRUMENT_PNL_FIELDS.USECS:
|
|
291
|
-
[result.usecs, offset] = readVarint(
|
|
299
|
+
[result.usecs, offset] = readVarint(data, offset);
|
|
292
300
|
break;
|
|
293
301
|
default:
|
|
294
|
-
offset = skipField(
|
|
302
|
+
offset = skipField(data, offset, wireType);
|
|
295
303
|
}
|
|
296
304
|
} catch (error) {
|
|
297
305
|
break;
|