@fullstackcraftllc/floe 0.0.9 → 0.0.11

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.
@@ -89,6 +89,8 @@ export declare class TastyTradeClient extends BaseBrokerClient {
89
89
  private occToStreamerMap;
90
90
  /** Keepalive interval handle */
91
91
  private keepaliveInterval;
92
+ /** Whether the first UNAUTHORIZED message has been handled yet - prevents incorrect handling of 'true' UNAUTHORIZED messages */
93
+ private firstUnauthorizedMessageHandled;
92
94
  /** Keepalive timeout in seconds */
93
95
  private readonly keepaliveTimeoutSeconds;
94
96
  /** TastyTrade API base URL */
@@ -74,6 +74,8 @@ class TastyTradeClient extends BaseBrokerClient_1.BaseBrokerClient {
74
74
  this.occToStreamerMap = new Map();
75
75
  /** Keepalive interval handle */
76
76
  this.keepaliveInterval = null;
77
+ /** Whether the first UNAUTHORIZED message has been handled yet - prevents incorrect handling of 'true' UNAUTHORIZED messages */
78
+ this.firstUnauthorizedMessageHandled = false;
77
79
  /** Keepalive timeout in seconds */
78
80
  this.keepaliveTimeoutSeconds = 60;
79
81
  this.sessionToken = options.sessionToken;
@@ -564,8 +566,7 @@ class TastyTradeClient extends BaseBrokerClient_1.BaseBrokerClient {
564
566
  const message = JSON.parse(data);
565
567
  switch (message.type) {
566
568
  case 'SETUP':
567
- // Server acknowledged setup, send auth
568
- this.sendAuth();
569
+ // no op; the server will send it's own first AUTH_STATE UNAUTHORIZED message right after
569
570
  break;
570
571
  case 'AUTH_STATE':
571
572
  this.handleAuthState(message, connectResolve);
@@ -600,6 +601,15 @@ class TastyTradeClient extends BaseBrokerClient_1.BaseBrokerClient {
600
601
  * Handles AUTH_STATE message.
601
602
  */
602
603
  handleAuthState(message, connectResolve) {
604
+ // the first message we get back (after SETUP response) is an UNAUTHORIZED state
605
+ // this is an expected part of the flow (though unintuitive)
606
+ // see https://developer.tastytrade.com/streaming-market-data/#dxlink-streamer
607
+ if (!this.firstUnauthorizedMessageHandled && message.state === 'UNAUTHORIZED') {
608
+ // Server acknowledged setup, send auth
609
+ this.sendAuth();
610
+ this.firstUnauthorizedMessageHandled = true;
611
+ }
612
+ // once we are authorized, we can proceed as normal
603
613
  if (message.state === 'AUTHORIZED') {
604
614
  this.authorized = true;
605
615
  this.startKeepalive();
@@ -610,8 +620,16 @@ class TastyTradeClient extends BaseBrokerClient_1.BaseBrokerClient {
610
620
  this.emit('connected', undefined);
611
621
  connectResolve?.();
612
622
  }
623
+ // a true unauthorized message after being authorized indicates a problem
624
+ else if (message.state === 'UNAUTHORIZED' && this.authorized) {
625
+ this.authorized = false;
626
+ this.emit('error', new Error('DxLink authorization lost'));
627
+ this.disconnect();
628
+ this.attemptReconnect();
629
+ }
613
630
  else {
614
- this.emit('error', new Error('DxLink authorization failed'));
631
+ console.log('[TastyTrade:DxLink] Received unknown AUTH_STATE message:', message);
632
+ this.emit('error', new Error('Unknown AUTH_STATE message state'));
615
633
  }
616
634
  }
617
635
  /**
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@fullstackcraftllc/floe",
3
- "version": "0.0.9",
3
+ "version": "0.0.11",
4
4
  "description": "Production-ready options analytics toolkit. Normalize broker data structures and calculate Black-Scholes, Greeks, and exposures with a clean, type-safe API. Built for trading platforms and fintech applications.",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",