@metamask-previews/perps-controller 6.2.0-preview-e43dfcb → 6.2.0-preview-c7c3c44

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.
Files changed (128) hide show
  1. package/CHANGELOG.md +12 -0
  2. package/dist/PerpsController-method-action-types.cjs.map +1 -1
  3. package/dist/PerpsController-method-action-types.d.cts +19 -1
  4. package/dist/PerpsController-method-action-types.d.cts.map +1 -1
  5. package/dist/PerpsController-method-action-types.d.mts +19 -1
  6. package/dist/PerpsController-method-action-types.d.mts.map +1 -1
  7. package/dist/PerpsController-method-action-types.mjs.map +1 -1
  8. package/dist/PerpsController.cjs +43 -5
  9. package/dist/PerpsController.cjs.map +1 -1
  10. package/dist/PerpsController.d.cts +13 -0
  11. package/dist/PerpsController.d.cts.map +1 -1
  12. package/dist/PerpsController.d.mts +13 -0
  13. package/dist/PerpsController.d.mts.map +1 -1
  14. package/dist/PerpsController.mjs +45 -7
  15. package/dist/PerpsController.mjs.map +1 -1
  16. package/dist/constants/eventNames.cjs +22 -0
  17. package/dist/constants/eventNames.cjs.map +1 -1
  18. package/dist/constants/eventNames.d.cts +15 -0
  19. package/dist/constants/eventNames.d.cts.map +1 -1
  20. package/dist/constants/eventNames.d.mts +15 -0
  21. package/dist/constants/eventNames.d.mts.map +1 -1
  22. package/dist/constants/eventNames.mjs +22 -0
  23. package/dist/constants/eventNames.mjs.map +1 -1
  24. package/dist/constants/perpsConfig.cjs +22 -1
  25. package/dist/constants/perpsConfig.cjs.map +1 -1
  26. package/dist/constants/perpsConfig.d.cts +11 -0
  27. package/dist/constants/perpsConfig.d.cts.map +1 -1
  28. package/dist/constants/perpsConfig.d.mts +11 -0
  29. package/dist/constants/perpsConfig.d.mts.map +1 -1
  30. package/dist/constants/perpsConfig.mjs +21 -0
  31. package/dist/constants/perpsConfig.mjs.map +1 -1
  32. package/dist/index.cjs +4 -3
  33. package/dist/index.cjs.map +1 -1
  34. package/dist/index.d.cts +1 -1
  35. package/dist/index.d.cts.map +1 -1
  36. package/dist/index.d.mts +1 -1
  37. package/dist/index.d.mts.map +1 -1
  38. package/dist/index.mjs +1 -1
  39. package/dist/index.mjs.map +1 -1
  40. package/dist/providers/HyperLiquidProvider.cjs +178 -40
  41. package/dist/providers/HyperLiquidProvider.cjs.map +1 -1
  42. package/dist/providers/HyperLiquidProvider.d.cts.map +1 -1
  43. package/dist/providers/HyperLiquidProvider.d.mts.map +1 -1
  44. package/dist/providers/HyperLiquidProvider.mjs +179 -41
  45. package/dist/providers/HyperLiquidProvider.mjs.map +1 -1
  46. package/dist/services/AccountService.cjs +1 -1
  47. package/dist/services/AccountService.cjs.map +1 -1
  48. package/dist/services/AccountService.d.cts.map +1 -1
  49. package/dist/services/AccountService.d.mts.map +1 -1
  50. package/dist/services/AccountService.mjs +2 -2
  51. package/dist/services/AccountService.mjs.map +1 -1
  52. package/dist/services/DataLakeService.cjs +1 -1
  53. package/dist/services/DataLakeService.cjs.map +1 -1
  54. package/dist/services/DataLakeService.d.cts.map +1 -1
  55. package/dist/services/DataLakeService.d.mts.map +1 -1
  56. package/dist/services/DataLakeService.mjs +2 -2
  57. package/dist/services/DataLakeService.mjs.map +1 -1
  58. package/dist/services/DepositService.cjs +2 -2
  59. package/dist/services/DepositService.cjs.map +1 -1
  60. package/dist/services/DepositService.d.cts.map +1 -1
  61. package/dist/services/DepositService.d.mts.map +1 -1
  62. package/dist/services/DepositService.mjs +3 -3
  63. package/dist/services/DepositService.mjs.map +1 -1
  64. package/dist/services/HyperLiquidWalletService.cjs +5 -5
  65. package/dist/services/HyperLiquidWalletService.cjs.map +1 -1
  66. package/dist/services/HyperLiquidWalletService.d.cts.map +1 -1
  67. package/dist/services/HyperLiquidWalletService.d.mts.map +1 -1
  68. package/dist/services/HyperLiquidWalletService.mjs +6 -6
  69. package/dist/services/HyperLiquidWalletService.mjs.map +1 -1
  70. package/dist/services/RewardsIntegrationService.cjs +1 -1
  71. package/dist/services/RewardsIntegrationService.cjs.map +1 -1
  72. package/dist/services/RewardsIntegrationService.d.cts.map +1 -1
  73. package/dist/services/RewardsIntegrationService.d.mts.map +1 -1
  74. package/dist/services/RewardsIntegrationService.mjs +2 -2
  75. package/dist/services/RewardsIntegrationService.mjs.map +1 -1
  76. package/dist/services/TradingReadinessCache.cjs +42 -2
  77. package/dist/services/TradingReadinessCache.cjs.map +1 -1
  78. package/dist/services/TradingReadinessCache.d.cts +29 -0
  79. package/dist/services/TradingReadinessCache.d.cts.map +1 -1
  80. package/dist/services/TradingReadinessCache.d.mts +29 -0
  81. package/dist/services/TradingReadinessCache.d.mts.map +1 -1
  82. package/dist/services/TradingReadinessCache.mjs +42 -2
  83. package/dist/services/TradingReadinessCache.mjs.map +1 -1
  84. package/dist/services/TradingService.cjs +27 -1
  85. package/dist/services/TradingService.cjs.map +1 -1
  86. package/dist/services/TradingService.d.cts +3 -1
  87. package/dist/services/TradingService.d.cts.map +1 -1
  88. package/dist/services/TradingService.d.mts +3 -1
  89. package/dist/services/TradingService.d.mts.map +1 -1
  90. package/dist/services/TradingService.mjs +27 -1
  91. package/dist/services/TradingService.mjs.map +1 -1
  92. package/dist/types/index.cjs.map +1 -1
  93. package/dist/types/index.d.cts +10 -1
  94. package/dist/types/index.d.cts.map +1 -1
  95. package/dist/types/index.d.mts +10 -1
  96. package/dist/types/index.d.mts.map +1 -1
  97. package/dist/types/index.mjs.map +1 -1
  98. package/dist/types/messenger.cjs.map +1 -1
  99. package/dist/types/messenger.d.cts +3 -2
  100. package/dist/types/messenger.d.cts.map +1 -1
  101. package/dist/types/messenger.d.mts +3 -2
  102. package/dist/types/messenger.d.mts.map +1 -1
  103. package/dist/types/messenger.mjs.map +1 -1
  104. package/dist/utils/accountUtils.cjs +38 -1
  105. package/dist/utils/accountUtils.cjs.map +1 -1
  106. package/dist/utils/accountUtils.d.cts +8 -0
  107. package/dist/utils/accountUtils.d.cts.map +1 -1
  108. package/dist/utils/accountUtils.d.mts +8 -0
  109. package/dist/utils/accountUtils.d.mts.map +1 -1
  110. package/dist/utils/accountUtils.mjs +35 -0
  111. package/dist/utils/accountUtils.mjs.map +1 -1
  112. package/dist/utils/errorUtils.cjs +15 -1
  113. package/dist/utils/errorUtils.cjs.map +1 -1
  114. package/dist/utils/errorUtils.d.cts +10 -0
  115. package/dist/utils/errorUtils.d.cts.map +1 -1
  116. package/dist/utils/errorUtils.d.mts +10 -0
  117. package/dist/utils/errorUtils.d.mts.map +1 -1
  118. package/dist/utils/errorUtils.mjs +13 -0
  119. package/dist/utils/errorUtils.mjs.map +1 -1
  120. package/dist/utils/orderCalculations.cjs +7 -3
  121. package/dist/utils/orderCalculations.cjs.map +1 -1
  122. package/dist/utils/orderCalculations.d.cts +1 -1
  123. package/dist/utils/orderCalculations.d.cts.map +1 -1
  124. package/dist/utils/orderCalculations.d.mts +1 -1
  125. package/dist/utils/orderCalculations.d.mts.map +1 -1
  126. package/dist/utils/orderCalculations.mjs +7 -3
  127. package/dist/utils/orderCalculations.mjs.map +1 -1
  128. package/package.json +1 -1
@@ -25,16 +25,23 @@
25
25
  type SigningOperationState = {
26
26
  attempted: boolean;
27
27
  success: boolean;
28
+ reason?: 'no_hl_account' | 'user_rejected' | 'transient';
29
+ };
30
+ type WalletRegistrationState = {
31
+ known: boolean;
32
+ registered: boolean;
28
33
  };
29
34
  type PerpsSigningCacheEntry = {
30
35
  unifiedAccount: SigningOperationState;
31
36
  builderFee: SigningOperationState;
32
37
  referral: SigningOperationState;
38
+ walletRegistered: WalletRegistrationState;
33
39
  timestamp: number;
34
40
  };
35
41
  type TradingReadinessCacheEntry = {
36
42
  attempted: boolean;
37
43
  enabled: boolean;
44
+ reason?: 'no_hl_account' | 'user_rejected' | 'transient';
38
45
  timestamp: number;
39
46
  };
40
47
  declare class PerpsSigningCacheManager {
@@ -76,10 +83,12 @@ declare class PerpsSigningCacheManager {
76
83
  * @param data - The transaction data payload.
77
84
  * @param data.attempted - Whether the operation was attempted.
78
85
  * @param data.enabled - Whether the feature is enabled.
86
+ * @param data.reason - Optional discriminator explaining a non-success outcome.
79
87
  */
80
88
  set(network: 'mainnet' | 'testnet', userAddress: string, data: {
81
89
  attempted: boolean;
82
90
  enabled: boolean;
91
+ reason?: 'no_hl_account' | 'user_rejected' | 'transient';
83
92
  }): void;
84
93
  /**
85
94
  * Check if builder fee approval was attempted
@@ -121,6 +130,26 @@ declare class PerpsSigningCacheManager {
121
130
  * @param userAddress - The user's wallet address.
122
131
  */
123
132
  clearUnifiedAccount(network: 'mainnet' | 'testnet', userAddress: string): void;
133
+ /**
134
+ * Read the wallet's Hyperliquid registration signal.
135
+ *
136
+ * @param network - The network environment.
137
+ * @param userAddress - The user's wallet address.
138
+ * @returns The current signal, or undefined if no entry exists.
139
+ */
140
+ getWalletRegistered(network: 'mainnet' | 'testnet', userAddress: string): WalletRegistrationState | undefined;
141
+ /**
142
+ * Record whether the wallet has been observed on Hyperliquid. Once
143
+ * `registered=true` is set, it stays true for the session — the goal
144
+ * is to skip doomed exchange writes for unfunded wallets, not to
145
+ * gate them after they fund.
146
+ *
147
+ * @param network - The network environment.
148
+ * @param userAddress - The user's wallet address.
149
+ * @param registered - True once any evidence (clearinghouseState balance,
150
+ * userFills, successful deposit, ...) confirms the wallet exists on HL.
151
+ */
152
+ setWalletRegistered(network: 'mainnet' | 'testnet', userAddress: string, registered: boolean): void;
124
153
  /**
125
154
  * Clear only builder fee state for a specific network and user address
126
155
  * This preserves unified account and referral states
@@ -1 +1 @@
1
- {"version":3,"file":"TradingReadinessCache.d.cts","sourceRoot":"","sources":["../../src/services/TradingReadinessCache.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AAEH,KAAK,qBAAqB,GAAG;IAC3B,SAAS,EAAE,OAAO,CAAC;IACnB,OAAO,EAAE,OAAO,CAAC;CAClB,CAAC;AAEF,KAAK,sBAAsB,GAAG;IAC5B,cAAc,EAAE,qBAAqB,CAAC;IACtC,UAAU,EAAE,qBAAqB,CAAC;IAClC,QAAQ,EAAE,qBAAqB,CAAC;IAChC,SAAS,EAAE,MAAM,CAAC;CACnB,CAAC;AAGF,KAAK,0BAA0B,GAAG;IAChC,SAAS,EAAE,OAAO,CAAC;IACnB,OAAO,EAAE,OAAO,CAAC;IACjB,SAAS,EAAE,MAAM,CAAC;CACnB,CAAC;AAEF,cAAM,wBAAwB;;IAU5B,SAAS;WAIK,WAAW,IAAI,wBAAwB;IAOrD;;;;;;;OAOG;IACI,UAAU,CACf,aAAa,EAAE,gBAAgB,GAAG,YAAY,GAAG,UAAU,EAC3D,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,OAAO,CAAC,IAAI,CAAC,GAAG,SAAS;IAK5B;;;;;;;;OAQG;IACI,WAAW,CAChB,aAAa,EAAE,gBAAgB,GAAG,YAAY,GAAG,UAAU,EAC3D,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,MAAM,IAAI;IAqCb;;;;;;OAMG;IACI,GAAG,CACR,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,0BAA0B,GAAG,SAAS;IAazC;;;;;;;;OAQG;IACI,GAAG,CACR,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,EACnB,IAAI,EAAE;QAAE,SAAS,EAAE,OAAO,CAAC;QAAC,OAAO,EAAE,OAAO,CAAA;KAAE,GAC7C,IAAI;IAQP;;;;;;OAMG;IACI,aAAa,CAClB,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,qBAAqB,GAAG,SAAS;IAMpC;;;;;;OAMG;IACI,aAAa,CAClB,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,EACnB,KAAK,EAAE,qBAAqB,GAC3B,IAAI;IAQP;;;;;;OAMG;IACI,WAAW,CAChB,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,qBAAqB,GAAG,SAAS;IAMpC;;;;;;OAMG;IACI,WAAW,CAChB,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,EACnB,KAAK,EAAE,qBAAqB,GAC3B,IAAI;IAQP;;;;;;OAMG;IACI,mBAAmB,CACxB,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,IAAI;IASP;;;;;;OAMG;IACI,eAAe,CACpB,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,IAAI;IASP;;;;;;OAMG;IACI,aAAa,CAClB,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,IAAI;IASP;;;;;;OAMG;IACI,KAAK,CAAC,OAAO,EAAE,SAAS,GAAG,SAAS,EAAE,WAAW,EAAE,MAAM,GAAG,IAAI;IAKvE;;;OAGG;IACI,QAAQ,IAAI,IAAI;IAIvB;;;;OAIG;IACI,MAAM,IAAI,GAAG,CAAC,MAAM,EAAE,sBAAsB,CAAC;IAIpD;;;;OAIG;IACI,IAAI,IAAI,MAAM;IAIrB;;;;OAIG;IACI,UAAU,IAAI,MAAM;CAW5B;AAGD,eAAO,MAAM,qBAAqB,0BAAyC,CAAC;AAG5E,eAAO,MAAM,iBAAiB,0BAAyC,CAAC"}
1
+ {"version":3,"file":"TradingReadinessCache.d.cts","sourceRoot":"","sources":["../../src/services/TradingReadinessCache.ts"],"names":[],"mappings":"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"}
@@ -25,16 +25,23 @@
25
25
  type SigningOperationState = {
26
26
  attempted: boolean;
27
27
  success: boolean;
28
+ reason?: 'no_hl_account' | 'user_rejected' | 'transient';
29
+ };
30
+ type WalletRegistrationState = {
31
+ known: boolean;
32
+ registered: boolean;
28
33
  };
29
34
  type PerpsSigningCacheEntry = {
30
35
  unifiedAccount: SigningOperationState;
31
36
  builderFee: SigningOperationState;
32
37
  referral: SigningOperationState;
38
+ walletRegistered: WalletRegistrationState;
33
39
  timestamp: number;
34
40
  };
35
41
  type TradingReadinessCacheEntry = {
36
42
  attempted: boolean;
37
43
  enabled: boolean;
44
+ reason?: 'no_hl_account' | 'user_rejected' | 'transient';
38
45
  timestamp: number;
39
46
  };
40
47
  declare class PerpsSigningCacheManager {
@@ -76,10 +83,12 @@ declare class PerpsSigningCacheManager {
76
83
  * @param data - The transaction data payload.
77
84
  * @param data.attempted - Whether the operation was attempted.
78
85
  * @param data.enabled - Whether the feature is enabled.
86
+ * @param data.reason - Optional discriminator explaining a non-success outcome.
79
87
  */
80
88
  set(network: 'mainnet' | 'testnet', userAddress: string, data: {
81
89
  attempted: boolean;
82
90
  enabled: boolean;
91
+ reason?: 'no_hl_account' | 'user_rejected' | 'transient';
83
92
  }): void;
84
93
  /**
85
94
  * Check if builder fee approval was attempted
@@ -121,6 +130,26 @@ declare class PerpsSigningCacheManager {
121
130
  * @param userAddress - The user's wallet address.
122
131
  */
123
132
  clearUnifiedAccount(network: 'mainnet' | 'testnet', userAddress: string): void;
133
+ /**
134
+ * Read the wallet's Hyperliquid registration signal.
135
+ *
136
+ * @param network - The network environment.
137
+ * @param userAddress - The user's wallet address.
138
+ * @returns The current signal, or undefined if no entry exists.
139
+ */
140
+ getWalletRegistered(network: 'mainnet' | 'testnet', userAddress: string): WalletRegistrationState | undefined;
141
+ /**
142
+ * Record whether the wallet has been observed on Hyperliquid. Once
143
+ * `registered=true` is set, it stays true for the session — the goal
144
+ * is to skip doomed exchange writes for unfunded wallets, not to
145
+ * gate them after they fund.
146
+ *
147
+ * @param network - The network environment.
148
+ * @param userAddress - The user's wallet address.
149
+ * @param registered - True once any evidence (clearinghouseState balance,
150
+ * userFills, successful deposit, ...) confirms the wallet exists on HL.
151
+ */
152
+ setWalletRegistered(network: 'mainnet' | 'testnet', userAddress: string, registered: boolean): void;
124
153
  /**
125
154
  * Clear only builder fee state for a specific network and user address
126
155
  * This preserves unified account and referral states
@@ -1 +1 @@
1
- {"version":3,"file":"TradingReadinessCache.d.mts","sourceRoot":"","sources":["../../src/services/TradingReadinessCache.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AAEH,KAAK,qBAAqB,GAAG;IAC3B,SAAS,EAAE,OAAO,CAAC;IACnB,OAAO,EAAE,OAAO,CAAC;CAClB,CAAC;AAEF,KAAK,sBAAsB,GAAG;IAC5B,cAAc,EAAE,qBAAqB,CAAC;IACtC,UAAU,EAAE,qBAAqB,CAAC;IAClC,QAAQ,EAAE,qBAAqB,CAAC;IAChC,SAAS,EAAE,MAAM,CAAC;CACnB,CAAC;AAGF,KAAK,0BAA0B,GAAG;IAChC,SAAS,EAAE,OAAO,CAAC;IACnB,OAAO,EAAE,OAAO,CAAC;IACjB,SAAS,EAAE,MAAM,CAAC;CACnB,CAAC;AAEF,cAAM,wBAAwB;;IAU5B,SAAS;WAIK,WAAW,IAAI,wBAAwB;IAOrD;;;;;;;OAOG;IACI,UAAU,CACf,aAAa,EAAE,gBAAgB,GAAG,YAAY,GAAG,UAAU,EAC3D,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,OAAO,CAAC,IAAI,CAAC,GAAG,SAAS;IAK5B;;;;;;;;OAQG;IACI,WAAW,CAChB,aAAa,EAAE,gBAAgB,GAAG,YAAY,GAAG,UAAU,EAC3D,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,MAAM,IAAI;IAqCb;;;;;;OAMG;IACI,GAAG,CACR,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,0BAA0B,GAAG,SAAS;IAazC;;;;;;;;OAQG;IACI,GAAG,CACR,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,EACnB,IAAI,EAAE;QAAE,SAAS,EAAE,OAAO,CAAC;QAAC,OAAO,EAAE,OAAO,CAAA;KAAE,GAC7C,IAAI;IAQP;;;;;;OAMG;IACI,aAAa,CAClB,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,qBAAqB,GAAG,SAAS;IAMpC;;;;;;OAMG;IACI,aAAa,CAClB,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,EACnB,KAAK,EAAE,qBAAqB,GAC3B,IAAI;IAQP;;;;;;OAMG;IACI,WAAW,CAChB,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,qBAAqB,GAAG,SAAS;IAMpC;;;;;;OAMG;IACI,WAAW,CAChB,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,EACnB,KAAK,EAAE,qBAAqB,GAC3B,IAAI;IAQP;;;;;;OAMG;IACI,mBAAmB,CACxB,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,IAAI;IASP;;;;;;OAMG;IACI,eAAe,CACpB,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,IAAI;IASP;;;;;;OAMG;IACI,aAAa,CAClB,OAAO,EAAE,SAAS,GAAG,SAAS,EAC9B,WAAW,EAAE,MAAM,GAClB,IAAI;IASP;;;;;;OAMG;IACI,KAAK,CAAC,OAAO,EAAE,SAAS,GAAG,SAAS,EAAE,WAAW,EAAE,MAAM,GAAG,IAAI;IAKvE;;;OAGG;IACI,QAAQ,IAAI,IAAI;IAIvB;;;;OAIG;IACI,MAAM,IAAI,GAAG,CAAC,MAAM,EAAE,sBAAsB,CAAC;IAIpD;;;;OAIG;IACI,IAAI,IAAI,MAAM;IAIrB;;;;OAIG;IACI,UAAU,IAAI,MAAM;CAW5B;AAGD,eAAO,MAAM,qBAAqB,0BAAyC,CAAC;AAG5E,eAAO,MAAM,iBAAiB,0BAAyC,CAAC"}
1
+ {"version":3,"file":"TradingReadinessCache.d.mts","sourceRoot":"","sources":["../../src/services/TradingReadinessCache.ts"],"names":[],"mappings":"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"}
@@ -100,6 +100,7 @@ class PerpsSigningCacheManager {
100
100
  return {
101
101
  attempted: entry.unifiedAccount.attempted,
102
102
  enabled: entry.unifiedAccount.success,
103
+ reason: entry.unifiedAccount.reason,
103
104
  timestamp: entry.timestamp,
104
105
  };
105
106
  }
@@ -111,10 +112,15 @@ class PerpsSigningCacheManager {
111
112
  * @param data - The transaction data payload.
112
113
  * @param data.attempted - Whether the operation was attempted.
113
114
  * @param data.enabled - Whether the feature is enabled.
115
+ * @param data.reason - Optional discriminator explaining a non-success outcome.
114
116
  */
115
117
  set(network, userAddress, data) {
116
118
  const entry = __classPrivateFieldGet(this, _PerpsSigningCacheManager_instances, "m", _PerpsSigningCacheManager_getOrCreateEntry).call(this, network, userAddress);
117
- entry.unifiedAccount = { attempted: data.attempted, success: data.enabled };
119
+ entry.unifiedAccount = {
120
+ attempted: data.attempted,
121
+ success: data.enabled,
122
+ reason: data.reason,
123
+ };
118
124
  entry.timestamp = Date.now();
119
125
  }
120
126
  // ===== Builder Fee Methods =====
@@ -183,6 +189,38 @@ class PerpsSigningCacheManager {
183
189
  entry.timestamp = Date.now();
184
190
  }
185
191
  }
192
+ // ===== Wallet Registration Methods =====
193
+ /**
194
+ * Read the wallet's Hyperliquid registration signal.
195
+ *
196
+ * @param network - The network environment.
197
+ * @param userAddress - The user's wallet address.
198
+ * @returns The current signal, or undefined if no entry exists.
199
+ */
200
+ getWalletRegistered(network, userAddress) {
201
+ const key = __classPrivateFieldGet(this, _PerpsSigningCacheManager_instances, "m", _PerpsSigningCacheManager_getCacheKey).call(this, network, userAddress);
202
+ return __classPrivateFieldGet(this, _PerpsSigningCacheManager_cache, "f").get(key)?.walletRegistered;
203
+ }
204
+ /**
205
+ * Record whether the wallet has been observed on Hyperliquid. Once
206
+ * `registered=true` is set, it stays true for the session — the goal
207
+ * is to skip doomed exchange writes for unfunded wallets, not to
208
+ * gate them after they fund.
209
+ *
210
+ * @param network - The network environment.
211
+ * @param userAddress - The user's wallet address.
212
+ * @param registered - True once any evidence (clearinghouseState balance,
213
+ * userFills, successful deposit, ...) confirms the wallet exists on HL.
214
+ */
215
+ setWalletRegistered(network, userAddress, registered) {
216
+ const entry = __classPrivateFieldGet(this, _PerpsSigningCacheManager_instances, "m", _PerpsSigningCacheManager_getOrCreateEntry).call(this, network, userAddress);
217
+ if (entry.walletRegistered.registered && !registered) {
218
+ // Monotonic: once registered, never demote.
219
+ return;
220
+ }
221
+ entry.walletRegistered = { known: true, registered };
222
+ entry.timestamp = Date.now();
223
+ }
186
224
  /**
187
225
  * Clear only builder fee state for a specific network and user address
188
226
  * This preserves unified account and referral states
@@ -257,7 +295,8 @@ class PerpsSigningCacheManager {
257
295
  __classPrivateFieldGet(this, _PerpsSigningCacheManager_cache, "f").forEach((entry, key) => {
258
296
  entries.push(`${key}: unified=${entry.unifiedAccount.attempted}/${entry.unifiedAccount.success}, ` +
259
297
  `builder=${entry.builderFee.attempted}/${entry.builderFee.success}, ` +
260
- `referral=${entry.referral.attempted}/${entry.referral.success}`);
298
+ `referral=${entry.referral.attempted}/${entry.referral.success}, ` +
299
+ `walletRegistered=${entry.walletRegistered.known}/${entry.walletRegistered.registered}`);
261
300
  });
262
301
  return entries.join('\n') || '(empty)';
263
302
  }
@@ -272,6 +311,7 @@ _a = PerpsSigningCacheManager, _PerpsSigningCacheManager_cache = new WeakMap(),
272
311
  unifiedAccount: { attempted: false, success: false },
273
312
  builderFee: { attempted: false, success: false },
274
313
  referral: { attempted: false, success: false },
314
+ walletRegistered: { known: false, registered: false },
275
315
  timestamp: Date.now(),
276
316
  };
277
317
  __classPrivateFieldGet(this, _PerpsSigningCacheManager_cache, "f").set(key, entry);
@@ -1 +1 @@
1
- {"version":3,"file":"TradingReadinessCache.mjs","sourceRoot":"","sources":["../../src/services/TradingReadinessCache.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * Global singleton cache for Perps signing operations\n *\n * This cache persists across provider reconnections to prevent repeated\n * signing requests for hardware wallets. Critical for preventing repeated\n * hardware wallet signing prompts.\n *\n * Cache is intentionally kept separate from provider instances because providers\n * are recreated on account/network changes, which would reset instance-level caches.\n *\n * Tracks three signing operations:\n * 1. Unified Account enablement (one-time, replaces deprecated DEX abstraction)\n * 2. Builder Fee approval (required for trading)\n * 3. Referral code setup (one-time per account)\n *\n * Cache Structure:\n * - Key: `network:userAddress` (e.g., \"mainnet:0x123...\")\n * - Value: { unifiedAccount, builderFee, referral, timestamp }\n *\n * Lifecycle:\n * - Cache persists throughout app session\n * - Individual entries can be cleared per user/network\n * - Full cache can be cleared on app restart or explicit user action\n */\n\ntype SigningOperationState = {\n attempted: boolean; // Whether we've attempted this operation\n success: boolean; // Whether it succeeded (only valid if attempted=true)\n};\n\ntype PerpsSigningCacheEntry = {\n unifiedAccount: SigningOperationState;\n builderFee: SigningOperationState;\n referral: SigningOperationState;\n timestamp: number; // When this entry was last updated\n};\n\n// Legacy interface for backward compatibility\ntype TradingReadinessCacheEntry = {\n attempted: boolean;\n enabled: boolean;\n timestamp: number;\n};\n\nclass PerpsSigningCacheManager {\n static #instance: PerpsSigningCacheManager;\n\n readonly #cache: Map<string, PerpsSigningCacheEntry> = new Map();\n\n // Global in-flight locks to prevent concurrent signing attempts across providers\n // Key: operationType:network:userAddress, Value: Promise that resolves when operation completes\n readonly #inFlightOperations: Map<string, Promise<void>> = new Map();\n\n // Singleton: use getInstance() instead of new\n protected constructor() {\n // Protected constructor for singleton\n }\n\n public static getInstance(): PerpsSigningCacheManager {\n PerpsSigningCacheManager.#instance ??= new PerpsSigningCacheManager();\n return PerpsSigningCacheManager.#instance;\n }\n\n // ===== In-Flight Lock Methods =====\n\n /**\n * Check if an operation is currently in-flight for this user/network\n *\n * @param operationType - The type of operation being performed.\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @returns The resulting string value.\n */\n public isInFlight(\n operationType: 'unifiedAccount' | 'builderFee' | 'referral',\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): Promise<void> | undefined {\n const key = `${operationType}:${network}:${userAddress.toLowerCase()}`;\n return this.#inFlightOperations.get(key);\n }\n\n /**\n * Set an operation as in-flight\n * Returns a function to call when operation completes\n *\n * @param operationType - The type of operation being performed.\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @returns The resulting string value.\n */\n public setInFlight(\n operationType: 'unifiedAccount' | 'builderFee' | 'referral',\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): () => void {\n const key = `${operationType}:${network}:${userAddress.toLowerCase()}`;\n let resolvePromise: () => void;\n const promise = new Promise<void>((resolve) => {\n resolvePromise = resolve;\n });\n this.#inFlightOperations.set(key, promise);\n return () => {\n this.#inFlightOperations.delete(key);\n resolvePromise();\n };\n }\n\n #getCacheKey(network: 'mainnet' | 'testnet', userAddress: string): string {\n return `${network}:${userAddress.toLowerCase()}`;\n }\n\n #getOrCreateEntry(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): PerpsSigningCacheEntry {\n const key = this.#getCacheKey(network, userAddress);\n let entry = this.#cache.get(key);\n if (!entry) {\n entry = {\n unifiedAccount: { attempted: false, success: false },\n builderFee: { attempted: false, success: false },\n referral: { attempted: false, success: false },\n timestamp: Date.now(),\n };\n this.#cache.set(key, entry);\n }\n return entry;\n }\n\n // ===== Unified Account Methods =====\n\n /**\n * Get unified account cache entry (legacy compatibility)\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @returns The resulting string value.\n */\n public get(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): TradingReadinessCacheEntry | undefined {\n const key = this.#getCacheKey(network, userAddress);\n const entry = this.#cache.get(key);\n if (!entry) {\n return undefined;\n }\n return {\n attempted: entry.unifiedAccount.attempted,\n enabled: entry.unifiedAccount.success,\n timestamp: entry.timestamp,\n };\n }\n\n /**\n * Set unified account cache entry (legacy compatibility)\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @param data - The transaction data payload.\n * @param data.attempted - Whether the operation was attempted.\n * @param data.enabled - Whether the feature is enabled.\n */\n public set(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n data: { attempted: boolean; enabled: boolean },\n ): void {\n const entry = this.#getOrCreateEntry(network, userAddress);\n entry.unifiedAccount = { attempted: data.attempted, success: data.enabled };\n entry.timestamp = Date.now();\n }\n\n // ===== Builder Fee Methods =====\n\n /**\n * Check if builder fee approval was attempted\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @returns The resulting string value.\n */\n public getBuilderFee(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): SigningOperationState | undefined {\n const key = this.#getCacheKey(network, userAddress);\n const entry = this.#cache.get(key);\n return entry?.builderFee;\n }\n\n /**\n * Set builder fee approval state\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @param state - The current state.\n */\n public setBuilderFee(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n state: SigningOperationState,\n ): void {\n const entry = this.#getOrCreateEntry(network, userAddress);\n entry.builderFee = state;\n entry.timestamp = Date.now();\n }\n\n // ===== Referral Methods =====\n\n /**\n * Check if referral setup was attempted\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @returns The resulting string value.\n */\n public getReferral(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): SigningOperationState | undefined {\n const key = this.#getCacheKey(network, userAddress);\n const entry = this.#cache.get(key);\n return entry?.referral;\n }\n\n /**\n * Set referral setup state\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @param state - The current state.\n */\n public setReferral(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n state: SigningOperationState,\n ): void {\n const entry = this.#getOrCreateEntry(network, userAddress);\n entry.referral = state;\n entry.timestamp = Date.now();\n }\n\n // ===== General Methods =====\n\n /**\n * Clear only unified account state for a specific network and user address\n * This preserves builder fee and referral states\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n */\n public clearUnifiedAccount(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): void {\n const key = this.#getCacheKey(network, userAddress);\n const entry = this.#cache.get(key);\n if (entry) {\n entry.unifiedAccount = { attempted: false, success: false };\n entry.timestamp = Date.now();\n }\n }\n\n /**\n * Clear only builder fee state for a specific network and user address\n * This preserves unified account and referral states\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n */\n public clearBuilderFee(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): void {\n const key = this.#getCacheKey(network, userAddress);\n const entry = this.#cache.get(key);\n if (entry) {\n entry.builderFee = { attempted: false, success: false };\n entry.timestamp = Date.now();\n }\n }\n\n /**\n * Clear only referral state for a specific network and user address\n * This preserves unified account and builder fee states\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n */\n public clearReferral(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): void {\n const key = this.#getCacheKey(network, userAddress);\n const entry = this.#cache.get(key);\n if (entry) {\n entry.referral = { attempted: false, success: false };\n entry.timestamp = Date.now();\n }\n }\n\n /**\n * Clear entire cache entry for a specific network and user address\n * WARNING: This clears ALL signing operation states (unifiedAccount, builderFee, referral)\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n */\n public clear(network: 'mainnet' | 'testnet', userAddress: string): void {\n const key = this.#getCacheKey(network, userAddress);\n this.#cache.delete(key);\n }\n\n /**\n * Clear all cache entries\n * WARNING: This clears ALL signing operation states for ALL users\n */\n public clearAll(): void {\n this.#cache.clear();\n }\n\n /**\n * Get all cache entries (for debugging)\n *\n * @returns The result of the operation.\n */\n public getAll(): Map<string, PerpsSigningCacheEntry> {\n return new Map(this.#cache);\n }\n\n /**\n * Get cache size (for debugging)\n *\n * @returns The resulting numeric value.\n */\n public size(): number {\n return this.#cache.size;\n }\n\n /**\n * Get full cache state for debugging\n *\n * @returns The resulting string value.\n */\n public debugState(): string {\n const entries: string[] = [];\n this.#cache.forEach((entry, key) => {\n entries.push(\n `${key}: unified=${entry.unifiedAccount.attempted}/${entry.unifiedAccount.success}, ` +\n `builder=${entry.builderFee.attempted}/${entry.builderFee.success}, ` +\n `referral=${entry.referral.attempted}/${entry.referral.success}`,\n );\n });\n return entries.join('\\n') || '(empty)';\n }\n}\n\n// Export singleton instance with backward-compatible name\nexport const TradingReadinessCache = PerpsSigningCacheManager.getInstance();\n\n// Export with new name for clarity\nexport const PerpsSigningCache = PerpsSigningCacheManager.getInstance();\n"]}
1
+ {"version":3,"file":"TradingReadinessCache.mjs","sourceRoot":"","sources":["../../src/services/TradingReadinessCache.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * Global singleton cache for Perps signing operations\n *\n * This cache persists across provider reconnections to prevent repeated\n * signing requests for hardware wallets. Critical for preventing repeated\n * hardware wallet signing prompts.\n *\n * Cache is intentionally kept separate from provider instances because providers\n * are recreated on account/network changes, which would reset instance-level caches.\n *\n * Tracks three signing operations:\n * 1. Unified Account enablement (one-time, replaces deprecated DEX abstraction)\n * 2. Builder Fee approval (required for trading)\n * 3. Referral code setup (one-time per account)\n *\n * Cache Structure:\n * - Key: `network:userAddress` (e.g., \"mainnet:0x123...\")\n * - Value: { unifiedAccount, builderFee, referral, timestamp }\n *\n * Lifecycle:\n * - Cache persists throughout app session\n * - Individual entries can be cleared per user/network\n * - Full cache can be cleared on app restart or explicit user action\n */\n\ntype SigningOperationState = {\n attempted: boolean; // Whether we've attempted this operation\n success: boolean; // Whether it succeeded (only valid if attempted=true)\n reason?: 'no_hl_account' | 'user_rejected' | 'transient'; // optional discriminator\n};\n\n// Tracks whether the wallet has ever been observed on Hyperliquid.\n// Hyperliquid accounts only come into existence on first USDC deposit.\n// Before then, user-scoped exchange writes (agentSetAbstraction,\n// userSetAbstraction, setReferrer, ...) reject with\n// \"User or API Wallet 0x... does not exist.\"\n// Used to skip those writes proactively rather than catching the rejection.\ntype WalletRegistrationState = {\n known: boolean; // Whether we have signal at all\n registered: boolean; // True once observed on Hyperliquid (monotonic)\n};\n\ntype PerpsSigningCacheEntry = {\n unifiedAccount: SigningOperationState;\n builderFee: SigningOperationState;\n referral: SigningOperationState;\n walletRegistered: WalletRegistrationState;\n timestamp: number; // When this entry was last updated\n};\n\n// Legacy interface for backward compatibility\ntype TradingReadinessCacheEntry = {\n attempted: boolean;\n enabled: boolean;\n reason?: 'no_hl_account' | 'user_rejected' | 'transient';\n timestamp: number;\n};\n\nclass PerpsSigningCacheManager {\n static #instance: PerpsSigningCacheManager;\n\n readonly #cache: Map<string, PerpsSigningCacheEntry> = new Map();\n\n // Global in-flight locks to prevent concurrent signing attempts across providers\n // Key: operationType:network:userAddress, Value: Promise that resolves when operation completes\n readonly #inFlightOperations: Map<string, Promise<void>> = new Map();\n\n // Singleton: use getInstance() instead of new\n protected constructor() {\n // Protected constructor for singleton\n }\n\n public static getInstance(): PerpsSigningCacheManager {\n PerpsSigningCacheManager.#instance ??= new PerpsSigningCacheManager();\n return PerpsSigningCacheManager.#instance;\n }\n\n // ===== In-Flight Lock Methods =====\n\n /**\n * Check if an operation is currently in-flight for this user/network\n *\n * @param operationType - The type of operation being performed.\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @returns The resulting string value.\n */\n public isInFlight(\n operationType: 'unifiedAccount' | 'builderFee' | 'referral',\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): Promise<void> | undefined {\n const key = `${operationType}:${network}:${userAddress.toLowerCase()}`;\n return this.#inFlightOperations.get(key);\n }\n\n /**\n * Set an operation as in-flight\n * Returns a function to call when operation completes\n *\n * @param operationType - The type of operation being performed.\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @returns The resulting string value.\n */\n public setInFlight(\n operationType: 'unifiedAccount' | 'builderFee' | 'referral',\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): () => void {\n const key = `${operationType}:${network}:${userAddress.toLowerCase()}`;\n let resolvePromise: () => void;\n const promise = new Promise<void>((resolve) => {\n resolvePromise = resolve;\n });\n this.#inFlightOperations.set(key, promise);\n return () => {\n this.#inFlightOperations.delete(key);\n resolvePromise();\n };\n }\n\n #getCacheKey(network: 'mainnet' | 'testnet', userAddress: string): string {\n return `${network}:${userAddress.toLowerCase()}`;\n }\n\n #getOrCreateEntry(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): PerpsSigningCacheEntry {\n const key = this.#getCacheKey(network, userAddress);\n let entry = this.#cache.get(key);\n if (!entry) {\n entry = {\n unifiedAccount: { attempted: false, success: false },\n builderFee: { attempted: false, success: false },\n referral: { attempted: false, success: false },\n walletRegistered: { known: false, registered: false },\n timestamp: Date.now(),\n };\n this.#cache.set(key, entry);\n }\n return entry;\n }\n\n // ===== Unified Account Methods =====\n\n /**\n * Get unified account cache entry (legacy compatibility)\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @returns The resulting string value.\n */\n public get(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): TradingReadinessCacheEntry | undefined {\n const key = this.#getCacheKey(network, userAddress);\n const entry = this.#cache.get(key);\n if (!entry) {\n return undefined;\n }\n return {\n attempted: entry.unifiedAccount.attempted,\n enabled: entry.unifiedAccount.success,\n reason: entry.unifiedAccount.reason,\n timestamp: entry.timestamp,\n };\n }\n\n /**\n * Set unified account cache entry (legacy compatibility)\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @param data - The transaction data payload.\n * @param data.attempted - Whether the operation was attempted.\n * @param data.enabled - Whether the feature is enabled.\n * @param data.reason - Optional discriminator explaining a non-success outcome.\n */\n public set(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n data: {\n attempted: boolean;\n enabled: boolean;\n reason?: 'no_hl_account' | 'user_rejected' | 'transient';\n },\n ): void {\n const entry = this.#getOrCreateEntry(network, userAddress);\n entry.unifiedAccount = {\n attempted: data.attempted,\n success: data.enabled,\n reason: data.reason,\n };\n entry.timestamp = Date.now();\n }\n\n // ===== Builder Fee Methods =====\n\n /**\n * Check if builder fee approval was attempted\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @returns The resulting string value.\n */\n public getBuilderFee(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): SigningOperationState | undefined {\n const key = this.#getCacheKey(network, userAddress);\n const entry = this.#cache.get(key);\n return entry?.builderFee;\n }\n\n /**\n * Set builder fee approval state\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @param state - The current state.\n */\n public setBuilderFee(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n state: SigningOperationState,\n ): void {\n const entry = this.#getOrCreateEntry(network, userAddress);\n entry.builderFee = state;\n entry.timestamp = Date.now();\n }\n\n // ===== Referral Methods =====\n\n /**\n * Check if referral setup was attempted\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @returns The resulting string value.\n */\n public getReferral(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): SigningOperationState | undefined {\n const key = this.#getCacheKey(network, userAddress);\n const entry = this.#cache.get(key);\n return entry?.referral;\n }\n\n /**\n * Set referral setup state\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @param state - The current state.\n */\n public setReferral(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n state: SigningOperationState,\n ): void {\n const entry = this.#getOrCreateEntry(network, userAddress);\n entry.referral = state;\n entry.timestamp = Date.now();\n }\n\n // ===== General Methods =====\n\n /**\n * Clear only unified account state for a specific network and user address\n * This preserves builder fee and referral states\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n */\n public clearUnifiedAccount(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): void {\n const key = this.#getCacheKey(network, userAddress);\n const entry = this.#cache.get(key);\n if (entry) {\n entry.unifiedAccount = { attempted: false, success: false };\n entry.timestamp = Date.now();\n }\n }\n\n // ===== Wallet Registration Methods =====\n\n /**\n * Read the wallet's Hyperliquid registration signal.\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @returns The current signal, or undefined if no entry exists.\n */\n public getWalletRegistered(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): WalletRegistrationState | undefined {\n const key = this.#getCacheKey(network, userAddress);\n return this.#cache.get(key)?.walletRegistered;\n }\n\n /**\n * Record whether the wallet has been observed on Hyperliquid. Once\n * `registered=true` is set, it stays true for the session — the goal\n * is to skip doomed exchange writes for unfunded wallets, not to\n * gate them after they fund.\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n * @param registered - True once any evidence (clearinghouseState balance,\n * userFills, successful deposit, ...) confirms the wallet exists on HL.\n */\n public setWalletRegistered(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n registered: boolean,\n ): void {\n const entry = this.#getOrCreateEntry(network, userAddress);\n if (entry.walletRegistered.registered && !registered) {\n // Monotonic: once registered, never demote.\n return;\n }\n entry.walletRegistered = { known: true, registered };\n entry.timestamp = Date.now();\n }\n\n /**\n * Clear only builder fee state for a specific network and user address\n * This preserves unified account and referral states\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n */\n public clearBuilderFee(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): void {\n const key = this.#getCacheKey(network, userAddress);\n const entry = this.#cache.get(key);\n if (entry) {\n entry.builderFee = { attempted: false, success: false };\n entry.timestamp = Date.now();\n }\n }\n\n /**\n * Clear only referral state for a specific network and user address\n * This preserves unified account and builder fee states\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n */\n public clearReferral(\n network: 'mainnet' | 'testnet',\n userAddress: string,\n ): void {\n const key = this.#getCacheKey(network, userAddress);\n const entry = this.#cache.get(key);\n if (entry) {\n entry.referral = { attempted: false, success: false };\n entry.timestamp = Date.now();\n }\n }\n\n /**\n * Clear entire cache entry for a specific network and user address\n * WARNING: This clears ALL signing operation states (unifiedAccount, builderFee, referral)\n *\n * @param network - The network environment.\n * @param userAddress - The user's wallet address.\n */\n public clear(network: 'mainnet' | 'testnet', userAddress: string): void {\n const key = this.#getCacheKey(network, userAddress);\n this.#cache.delete(key);\n }\n\n /**\n * Clear all cache entries\n * WARNING: This clears ALL signing operation states for ALL users\n */\n public clearAll(): void {\n this.#cache.clear();\n }\n\n /**\n * Get all cache entries (for debugging)\n *\n * @returns The result of the operation.\n */\n public getAll(): Map<string, PerpsSigningCacheEntry> {\n return new Map(this.#cache);\n }\n\n /**\n * Get cache size (for debugging)\n *\n * @returns The resulting numeric value.\n */\n public size(): number {\n return this.#cache.size;\n }\n\n /**\n * Get full cache state for debugging\n *\n * @returns The resulting string value.\n */\n public debugState(): string {\n const entries: string[] = [];\n this.#cache.forEach((entry, key) => {\n entries.push(\n `${key}: unified=${entry.unifiedAccount.attempted}/${entry.unifiedAccount.success}, ` +\n `builder=${entry.builderFee.attempted}/${entry.builderFee.success}, ` +\n `referral=${entry.referral.attempted}/${entry.referral.success}, ` +\n `walletRegistered=${entry.walletRegistered.known}/${entry.walletRegistered.registered}`,\n );\n });\n return entries.join('\\n') || '(empty)';\n }\n}\n\n// Export singleton instance with backward-compatible name\nexport const TradingReadinessCache = PerpsSigningCacheManager.getInstance();\n\n// Export with new name for clarity\nexport const PerpsSigningCache = PerpsSigningCacheManager.getInstance();\n"]}
@@ -1052,11 +1052,12 @@ class TradingService {
1052
1052
  * @param options - The configuration options.
1053
1053
  * @param options.provider - The perps provider instance.
1054
1054
  * @param options.position - The position data.
1055
+ * @param options.trackingData - Optional tracking data for analytics events.
1055
1056
  * @param options.context - The service context for dependencies.
1056
1057
  * @returns The result of the operation.
1057
1058
  */
1058
1059
  async flipPosition(options) {
1059
- const { provider, position, context } = options;
1060
+ const { provider, position, trackingData, context } = options;
1060
1061
  const traceId = (0, uuid_1.v4)();
1061
1062
  const startTime = __classPrivateFieldGet(this, _TradingService_deps, "f").performance.now();
1062
1063
  try {
@@ -1113,6 +1114,12 @@ class TradingService {
1113
1114
  [eventNames_1.PERPS_EVENT_PROPERTY.COMPLETION_DURATION]: completionDuration,
1114
1115
  [eventNames_1.PERPS_EVENT_PROPERTY.ACTION]: flipAction,
1115
1116
  [eventNames_1.PERPS_EVENT_PROPERTY.ORDER_VALUE]: positionSize * executedPrice,
1117
+ ...(trackingData?.vipTier !== undefined && {
1118
+ [eventNames_1.PERPS_EVENT_PROPERTY.VIP_TIER]: trackingData.vipTier,
1119
+ }),
1120
+ ...(trackingData?.vipDiscount !== undefined && {
1121
+ [eventNames_1.PERPS_EVENT_PROPERTY.VIP_DISCOUNT]: trackingData.vipDiscount,
1122
+ }),
1116
1123
  });
1117
1124
  // Invalidate standalone caches so external hooks refresh
1118
1125
  __classPrivateFieldGet(this, _TradingService_deps, "f").cacheInvalidator.invalidate({ cacheType: 'positions' });
@@ -1140,6 +1147,12 @@ class TradingService {
1140
1147
  [eventNames_1.PERPS_EVENT_PROPERTY.ACTION]: failFlipAction,
1141
1148
  [eventNames_1.PERPS_EVENT_PROPERTY.COMPLETION_DURATION]: completionDuration,
1142
1149
  [eventNames_1.PERPS_EVENT_PROPERTY.ERROR_MESSAGE]: errorMessage,
1150
+ ...(trackingData?.vipTier !== undefined && {
1151
+ [eventNames_1.PERPS_EVENT_PROPERTY.VIP_TIER]: trackingData.vipTier,
1152
+ }),
1153
+ ...(trackingData?.vipDiscount !== undefined && {
1154
+ [eventNames_1.PERPS_EVENT_PROPERTY.VIP_DISCOUNT]: trackingData.vipDiscount,
1155
+ }),
1143
1156
  });
1144
1157
  __classPrivateFieldGet(this, _TradingService_deps, "f").tracer.endTrace({
1145
1158
  name: types_1.PerpsTraceNames.FlipPosition,
@@ -1251,6 +1264,13 @@ _TradingService_deps = new WeakMap(), _TradingService_controllerDeps = new WeakM
1251
1264
  properties[eventNames_1.PERPS_EVENT_PROPERTY.ERROR_MESSAGE] =
1252
1265
  error?.message ?? result?.error ?? 'Unknown error';
1253
1266
  }
1267
+ if (params.trackingData?.vipTier !== undefined) {
1268
+ properties[eventNames_1.PERPS_EVENT_PROPERTY.VIP_TIER] = params.trackingData.vipTier;
1269
+ }
1270
+ if (params.trackingData?.vipDiscount !== undefined) {
1271
+ properties[eventNames_1.PERPS_EVENT_PROPERTY.VIP_DISCOUNT] =
1272
+ params.trackingData.vipDiscount;
1273
+ }
1254
1274
  if (params.trackingData?.abTests &&
1255
1275
  Object.keys(params.trackingData.abTests).length > 0) {
1256
1276
  properties[eventNames_1.PERPS_EVENT_PROPERTY.AB_TESTS] = params.trackingData.abTests;
@@ -1429,6 +1449,12 @@ async function _TradingService_loadPositionData(options) {
1429
1449
  ...(params.trackingData?.source && {
1430
1450
  [eventNames_1.PERPS_EVENT_PROPERTY.SOURCE]: params.trackingData.source,
1431
1451
  }),
1452
+ ...(params.trackingData?.vipTier !== undefined && {
1453
+ [eventNames_1.PERPS_EVENT_PROPERTY.VIP_TIER]: params.trackingData.vipTier,
1454
+ }),
1455
+ ...(params.trackingData?.vipDiscount !== undefined && {
1456
+ [eventNames_1.PERPS_EVENT_PROPERTY.VIP_DISCOUNT]: params.trackingData.vipDiscount,
1457
+ }),
1432
1458
  };
1433
1459
  // Calculate and add order value in USD (size * price)
1434
1460
  const closeAssetPrice = result?.averagePrice