@usherlabs/cex-broker 0.2.37 → 0.2.38

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.
@@ -334375,6 +334375,62 @@ function isBinanceBalanceUserDataEvent(event) {
334375
334375
  function isBinanceOrderUserDataEvent(event) {
334376
334376
  return event.e === "executionReport" || event.e === "listStatus";
334377
334377
  }
334378
+
334379
+ // src/helpers/binance-user-data-normalization.ts
334380
+ function requireQuantity(entry, key) {
334381
+ const value = entry[key];
334382
+ if (typeof value === "string" && value.trim().length > 0) {
334383
+ return value;
334384
+ }
334385
+ if (typeof value === "number" && Number.isFinite(value)) {
334386
+ return String(value);
334387
+ }
334388
+ throw new Error(`Invalid Binance balance quantity: ${key}`);
334389
+ }
334390
+ async function normalizeBinanceSpotBalanceEvent(exchange, event) {
334391
+ if (event.e !== "outboundAccountPosition") {
334392
+ return exchange.fetchBalance({ type: "spot" });
334393
+ }
334394
+ if (!Array.isArray(event.B)) {
334395
+ throw new Error("Invalid Binance outboundAccountPosition balances");
334396
+ }
334397
+ const timestamp = typeof event.E === "number" && Number.isFinite(event.E) ? event.E : undefined;
334398
+ const balance = {
334399
+ info: event,
334400
+ ...timestamp !== undefined && {
334401
+ timestamp,
334402
+ datetime: new Date(timestamp).toISOString()
334403
+ }
334404
+ };
334405
+ for (const rawEntry of event.B) {
334406
+ const entry = asRecord(rawEntry);
334407
+ const asset = entry?.a;
334408
+ if (!entry || typeof asset !== "string" || asset.length === 0) {
334409
+ throw new Error("Invalid Binance outboundAccountPosition asset");
334410
+ }
334411
+ balance[asset] = {
334412
+ free: requireQuantity(entry, "f"),
334413
+ used: requireQuantity(entry, "l")
334414
+ };
334415
+ }
334416
+ return exchange.safeBalance(balance);
334417
+ }
334418
+ function getTradeId(value) {
334419
+ if (typeof value === "number" && Number.isFinite(value) || typeof value === "string" && value.length > 0) {
334420
+ const tradeId = String(value);
334421
+ return tradeId === "-1" ? undefined : tradeId;
334422
+ }
334423
+ return;
334424
+ }
334425
+ function normalizeBinanceExecutionReport(exchange, event) {
334426
+ const parsed = asRecord(exchange.parseWsOrder(event));
334427
+ if (!parsed) {
334428
+ throw new Error("Binance executionReport did not parse as an order");
334429
+ }
334430
+ const { fee: _fee, fees: _fees, ...order } = parsed;
334431
+ const tradeId = getTradeId(event.t);
334432
+ return tradeId === undefined ? order : { ...order, tradeId };
334433
+ }
334378
334434
  // src/helpers/market-data-archive/ohlcv-bootstrap.ts
334379
334435
  var DEFAULT_OHLCV_BOOTSTRAP_LIMIT = 100;
334380
334436
  var MAX_OHLCV_BOOTSTRAP_LIMIT = 1000;
@@ -334521,17 +334577,6 @@ async function streamBinanceUserData(call, broker, symbol2, subscriptionType, is
334521
334577
  }
334522
334578
  }
334523
334579
  const receivedTimestamp = Date.now();
334524
- if (!await writeSubscribeFrame(call, isClosed, {
334525
- data: JSON.stringify({
334526
- subscriptionId: message.subscriptionId,
334527
- event
334528
- }),
334529
- timestamp: receivedTimestamp,
334530
- symbol: symbol2,
334531
- type: subscriptionType
334532
- })) {
334533
- break;
334534
- }
334535
334580
  const archiveSubscriptionType = subscriptionType === SubscriptionType.BALANCE ? "BALANCE" : "ORDERS";
334536
334581
  archiveSubscribeStreamInBackground(archiveContext?.archiver, {
334537
334582
  exchange: archiveContext?.exchange ?? "binance",
@@ -334552,6 +334597,18 @@ async function streamBinanceUserData(call, broker, symbol2, subscriptionType, is
334552
334597
  receivedTimestamp
334553
334598
  });
334554
334599
  }
334600
+ if (subscriptionType === SubscriptionType.ORDERS && event.e === "listStatus") {
334601
+ continue;
334602
+ }
334603
+ const data = subscriptionType === SubscriptionType.BALANCE ? await normalizeBinanceSpotBalanceEvent(broker, event) : normalizeBinanceExecutionReport(broker, event);
334604
+ if (!await writeSubscribeFrame(call, isClosed, {
334605
+ data: JSON.stringify(data),
334606
+ timestamp: receivedTimestamp,
334607
+ symbol: symbol2,
334608
+ type: subscriptionType
334609
+ })) {
334610
+ break;
334611
+ }
334555
334612
  }
334556
334613
  } finally {
334557
334614
  userDataStream.close();
@@ -0,0 +1,3 @@
1
+ import type { Exchange } from "@usherlabs/ccxt";
2
+ export declare function normalizeBinanceSpotBalanceEvent(exchange: Exchange, event: Record<string, unknown>): Promise<unknown>;
3
+ export declare function normalizeBinanceExecutionReport(exchange: Exchange, event: Record<string, unknown>): Record<string, unknown>;
package/dist/index.js CHANGED
@@ -309889,6 +309889,62 @@ function isBinanceBalanceUserDataEvent(event) {
309889
309889
  function isBinanceOrderUserDataEvent(event) {
309890
309890
  return event.e === "executionReport" || event.e === "listStatus";
309891
309891
  }
309892
+
309893
+ // src/helpers/binance-user-data-normalization.ts
309894
+ function requireQuantity(entry, key) {
309895
+ const value = entry[key];
309896
+ if (typeof value === "string" && value.trim().length > 0) {
309897
+ return value;
309898
+ }
309899
+ if (typeof value === "number" && Number.isFinite(value)) {
309900
+ return String(value);
309901
+ }
309902
+ throw new Error(`Invalid Binance balance quantity: ${key}`);
309903
+ }
309904
+ async function normalizeBinanceSpotBalanceEvent(exchange, event) {
309905
+ if (event.e !== "outboundAccountPosition") {
309906
+ return exchange.fetchBalance({ type: "spot" });
309907
+ }
309908
+ if (!Array.isArray(event.B)) {
309909
+ throw new Error("Invalid Binance outboundAccountPosition balances");
309910
+ }
309911
+ const timestamp = typeof event.E === "number" && Number.isFinite(event.E) ? event.E : undefined;
309912
+ const balance = {
309913
+ info: event,
309914
+ ...timestamp !== undefined && {
309915
+ timestamp,
309916
+ datetime: new Date(timestamp).toISOString()
309917
+ }
309918
+ };
309919
+ for (const rawEntry of event.B) {
309920
+ const entry = asRecord(rawEntry);
309921
+ const asset = entry?.a;
309922
+ if (!entry || typeof asset !== "string" || asset.length === 0) {
309923
+ throw new Error("Invalid Binance outboundAccountPosition asset");
309924
+ }
309925
+ balance[asset] = {
309926
+ free: requireQuantity(entry, "f"),
309927
+ used: requireQuantity(entry, "l")
309928
+ };
309929
+ }
309930
+ return exchange.safeBalance(balance);
309931
+ }
309932
+ function getTradeId(value) {
309933
+ if (typeof value === "number" && Number.isFinite(value) || typeof value === "string" && value.length > 0) {
309934
+ const tradeId = String(value);
309935
+ return tradeId === "-1" ? undefined : tradeId;
309936
+ }
309937
+ return;
309938
+ }
309939
+ function normalizeBinanceExecutionReport(exchange, event) {
309940
+ const parsed = asRecord(exchange.parseWsOrder(event));
309941
+ if (!parsed) {
309942
+ throw new Error("Binance executionReport did not parse as an order");
309943
+ }
309944
+ const { fee: _fee, fees: _fees, ...order } = parsed;
309945
+ const tradeId = getTradeId(event.t);
309946
+ return tradeId === undefined ? order : { ...order, tradeId };
309947
+ }
309892
309948
  // src/helpers/market-data-archive/ohlcv-bootstrap.ts
309893
309949
  var DEFAULT_OHLCV_BOOTSTRAP_LIMIT = 100;
309894
309950
  var MAX_OHLCV_BOOTSTRAP_LIMIT = 1000;
@@ -310035,17 +310091,6 @@ async function streamBinanceUserData(call, broker, symbol2, subscriptionType, is
310035
310091
  }
310036
310092
  }
310037
310093
  const receivedTimestamp = Date.now();
310038
- if (!await writeSubscribeFrame(call, isClosed, {
310039
- data: JSON.stringify({
310040
- subscriptionId: message.subscriptionId,
310041
- event
310042
- }),
310043
- timestamp: receivedTimestamp,
310044
- symbol: symbol2,
310045
- type: subscriptionType
310046
- })) {
310047
- break;
310048
- }
310049
310094
  const archiveSubscriptionType = subscriptionType === SubscriptionType.BALANCE ? "BALANCE" : "ORDERS";
310050
310095
  archiveSubscribeStreamInBackground(archiveContext?.archiver, {
310051
310096
  exchange: archiveContext?.exchange ?? "binance",
@@ -310066,6 +310111,18 @@ async function streamBinanceUserData(call, broker, symbol2, subscriptionType, is
310066
310111
  receivedTimestamp
310067
310112
  });
310068
310113
  }
310114
+ if (subscriptionType === SubscriptionType.ORDERS && event.e === "listStatus") {
310115
+ continue;
310116
+ }
310117
+ const data = subscriptionType === SubscriptionType.BALANCE ? await normalizeBinanceSpotBalanceEvent(broker, event) : normalizeBinanceExecutionReport(broker, event);
310118
+ if (!await writeSubscribeFrame(call, isClosed, {
310119
+ data: JSON.stringify(data),
310120
+ timestamp: receivedTimestamp,
310121
+ symbol: symbol2,
310122
+ type: subscriptionType
310123
+ })) {
310124
+ break;
310125
+ }
310069
310126
  }
310070
310127
  } finally {
310071
310128
  userDataStream.close();
@@ -311031,4 +311088,4 @@ export {
311031
311088
  CEXBroker as default
311032
311089
  };
311033
311090
 
311034
- //# debugId=89161A06846CFA7064756E2164756E21
311091
+ //# debugId=4F503765D539243C64756E2164756E21