@humanode-hyperlane/rebalancer 0.0.0-stage → 27.2.2

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 (439) hide show
  1. package/LICENSE.md +193 -0
  2. package/README.md +297 -2
  3. package/dist/bridges/LiFiBridge.d.ts +93 -0
  4. package/dist/bridges/LiFiBridge.d.ts.map +1 -0
  5. package/dist/bridges/LiFiBridge.js +527 -0
  6. package/dist/bridges/LiFiBridge.js.map +1 -0
  7. package/dist/bridges/LiFiBridge.test.d.ts +2 -0
  8. package/dist/bridges/LiFiBridge.test.d.ts.map +1 -0
  9. package/dist/bridges/LiFiBridge.test.js +504 -0
  10. package/dist/bridges/LiFiBridge.test.js.map +1 -0
  11. package/dist/config/RebalancerConfig.d.ts +20 -0
  12. package/dist/config/RebalancerConfig.d.ts.map +1 -0
  13. package/dist/config/RebalancerConfig.js +35 -0
  14. package/dist/config/RebalancerConfig.js.map +1 -0
  15. package/dist/config/RebalancerConfig.test.d.ts +2 -0
  16. package/dist/config/RebalancerConfig.test.d.ts.map +1 -0
  17. package/dist/config/RebalancerConfig.test.js +798 -0
  18. package/dist/config/RebalancerConfig.test.js.map +1 -0
  19. package/dist/config/types.d.ts +3008 -0
  20. package/dist/config/types.d.ts.map +1 -0
  21. package/dist/config/types.js +451 -0
  22. package/dist/config/types.js.map +1 -0
  23. package/dist/core/InventoryRebalancer.d.ts +201 -0
  24. package/dist/core/InventoryRebalancer.d.ts.map +1 -0
  25. package/dist/core/InventoryRebalancer.js +994 -0
  26. package/dist/core/InventoryRebalancer.js.map +1 -0
  27. package/dist/core/InventoryRebalancer.test.d.ts +2 -0
  28. package/dist/core/InventoryRebalancer.test.d.ts.map +1 -0
  29. package/dist/core/InventoryRebalancer.test.js +1511 -0
  30. package/dist/core/InventoryRebalancer.test.js.map +1 -0
  31. package/dist/core/Rebalancer.d.ts +37 -0
  32. package/dist/core/Rebalancer.d.ts.map +1 -0
  33. package/dist/core/Rebalancer.js +433 -0
  34. package/dist/core/Rebalancer.js.map +1 -0
  35. package/dist/core/Rebalancer.test.d.ts +2 -0
  36. package/dist/core/Rebalancer.test.d.ts.map +1 -0
  37. package/dist/core/Rebalancer.test.js +424 -0
  38. package/dist/core/Rebalancer.test.js.map +1 -0
  39. package/dist/core/RebalancerOrchestrator.d.ts +56 -0
  40. package/dist/core/RebalancerOrchestrator.d.ts.map +1 -0
  41. package/dist/core/RebalancerOrchestrator.js +154 -0
  42. package/dist/core/RebalancerOrchestrator.js.map +1 -0
  43. package/dist/core/RebalancerOrchestrator.test.d.ts +2 -0
  44. package/dist/core/RebalancerOrchestrator.test.d.ts.map +1 -0
  45. package/dist/core/RebalancerOrchestrator.test.js +721 -0
  46. package/dist/core/RebalancerOrchestrator.test.js.map +1 -0
  47. package/dist/core/RebalancerService.d.ts +127 -0
  48. package/dist/core/RebalancerService.d.ts.map +1 -0
  49. package/dist/core/RebalancerService.js +270 -0
  50. package/dist/core/RebalancerService.js.map +1 -0
  51. package/dist/core/RebalancerService.test.d.ts +2 -0
  52. package/dist/core/RebalancerService.test.d.ts.map +1 -0
  53. package/dist/core/RebalancerService.test.js +777 -0
  54. package/dist/core/RebalancerService.test.js.map +1 -0
  55. package/dist/e2e/collateral-deficit.e2e-test.d.ts +2 -0
  56. package/dist/e2e/collateral-deficit.e2e-test.d.ts.map +1 -0
  57. package/dist/e2e/collateral-deficit.e2e-test.js +227 -0
  58. package/dist/e2e/collateral-deficit.e2e-test.js.map +1 -0
  59. package/dist/e2e/composite.e2e-test.d.ts +2 -0
  60. package/dist/e2e/composite.e2e-test.d.ts.map +1 -0
  61. package/dist/e2e/composite.e2e-test.js +666 -0
  62. package/dist/e2e/composite.e2e-test.js.map +1 -0
  63. package/dist/e2e/fixtures/routes.d.ts +89 -0
  64. package/dist/e2e/fixtures/routes.d.ts.map +1 -0
  65. package/dist/e2e/fixtures/routes.js +420 -0
  66. package/dist/e2e/fixtures/routes.js.map +1 -0
  67. package/dist/e2e/harness/BaseLocalDeploymentManager.d.ts +38 -0
  68. package/dist/e2e/harness/BaseLocalDeploymentManager.d.ts.map +1 -0
  69. package/dist/e2e/harness/BaseLocalDeploymentManager.js +144 -0
  70. package/dist/e2e/harness/BaseLocalDeploymentManager.js.map +1 -0
  71. package/dist/e2e/harness/BridgeSetup.d.ts +11 -0
  72. package/dist/e2e/harness/BridgeSetup.d.ts.map +1 -0
  73. package/dist/e2e/harness/BridgeSetup.js +50 -0
  74. package/dist/e2e/harness/BridgeSetup.js.map +1 -0
  75. package/dist/e2e/harness/Erc20InventoryLocalDeploymentManager.d.ts +13 -0
  76. package/dist/e2e/harness/Erc20InventoryLocalDeploymentManager.d.ts.map +1 -0
  77. package/dist/e2e/harness/Erc20InventoryLocalDeploymentManager.js +105 -0
  78. package/dist/e2e/harness/Erc20InventoryLocalDeploymentManager.js.map +1 -0
  79. package/dist/e2e/harness/Erc20LocalDeploymentManager.d.ts +11 -0
  80. package/dist/e2e/harness/Erc20LocalDeploymentManager.d.ts.map +1 -0
  81. package/dist/e2e/harness/Erc20LocalDeploymentManager.js +105 -0
  82. package/dist/e2e/harness/Erc20LocalDeploymentManager.js.map +1 -0
  83. package/dist/e2e/harness/ForkIndexer.d.ts +23 -0
  84. package/dist/e2e/harness/ForkIndexer.d.ts.map +1 -0
  85. package/dist/e2e/harness/ForkIndexer.js +127 -0
  86. package/dist/e2e/harness/ForkIndexer.js.map +1 -0
  87. package/dist/e2e/harness/ForkIndexer.test.d.ts +2 -0
  88. package/dist/e2e/harness/ForkIndexer.test.d.ts.map +1 -0
  89. package/dist/e2e/harness/ForkIndexer.test.js +257 -0
  90. package/dist/e2e/harness/ForkIndexer.test.js.map +1 -0
  91. package/dist/e2e/harness/MixedLocalDeploymentManager.d.ts +21 -0
  92. package/dist/e2e/harness/MixedLocalDeploymentManager.d.ts.map +1 -0
  93. package/dist/e2e/harness/MixedLocalDeploymentManager.js +115 -0
  94. package/dist/e2e/harness/MixedLocalDeploymentManager.js.map +1 -0
  95. package/dist/e2e/harness/MockExplorerClient.d.ts +23 -0
  96. package/dist/e2e/harness/MockExplorerClient.d.ts.map +1 -0
  97. package/dist/e2e/harness/MockExplorerClient.js +57 -0
  98. package/dist/e2e/harness/MockExplorerClient.js.map +1 -0
  99. package/dist/e2e/harness/MockExternalBridge.d.ts +32 -0
  100. package/dist/e2e/harness/MockExternalBridge.d.ts.map +1 -0
  101. package/dist/e2e/harness/MockExternalBridge.js +247 -0
  102. package/dist/e2e/harness/MockExternalBridge.js.map +1 -0
  103. package/dist/e2e/harness/NativeLocalDeploymentManager.d.ts +13 -0
  104. package/dist/e2e/harness/NativeLocalDeploymentManager.d.ts.map +1 -0
  105. package/dist/e2e/harness/NativeLocalDeploymentManager.js +91 -0
  106. package/dist/e2e/harness/NativeLocalDeploymentManager.js.map +1 -0
  107. package/dist/e2e/harness/SnapshotHelper.d.ts +13 -0
  108. package/dist/e2e/harness/SnapshotHelper.d.ts.map +1 -0
  109. package/dist/e2e/harness/SnapshotHelper.js +36 -0
  110. package/dist/e2e/harness/SnapshotHelper.js.map +1 -0
  111. package/dist/e2e/harness/TestHelpers.d.ts +25 -0
  112. package/dist/e2e/harness/TestHelpers.d.ts.map +1 -0
  113. package/dist/e2e/harness/TestHelpers.js +103 -0
  114. package/dist/e2e/harness/TestHelpers.js.map +1 -0
  115. package/dist/e2e/harness/TestRebalancer.d.ts +85 -0
  116. package/dist/e2e/harness/TestRebalancer.d.ts.map +1 -0
  117. package/dist/e2e/harness/TestRebalancer.js +427 -0
  118. package/dist/e2e/harness/TestRebalancer.js.map +1 -0
  119. package/dist/e2e/harness/TransferHelper.d.ts +34 -0
  120. package/dist/e2e/harness/TransferHelper.d.ts.map +1 -0
  121. package/dist/e2e/harness/TransferHelper.js +93 -0
  122. package/dist/e2e/harness/TransferHelper.js.map +1 -0
  123. package/dist/e2e/inventory-erc20-minAmount.e2e-test.d.ts +2 -0
  124. package/dist/e2e/inventory-erc20-minAmount.e2e-test.d.ts.map +1 -0
  125. package/dist/e2e/inventory-erc20-minAmount.e2e-test.js +411 -0
  126. package/dist/e2e/inventory-erc20-minAmount.e2e-test.js.map +1 -0
  127. package/dist/e2e/inventory-erc20-weighted.e2e-test.d.ts +2 -0
  128. package/dist/e2e/inventory-erc20-weighted.e2e-test.d.ts.map +1 -0
  129. package/dist/e2e/inventory-erc20-weighted.e2e-test.js +408 -0
  130. package/dist/e2e/inventory-erc20-weighted.e2e-test.js.map +1 -0
  131. package/dist/e2e/inventory-minAmount.e2e-test.d.ts +2 -0
  132. package/dist/e2e/inventory-minAmount.e2e-test.d.ts.map +1 -0
  133. package/dist/e2e/inventory-minAmount.e2e-test.js +411 -0
  134. package/dist/e2e/inventory-minAmount.e2e-test.js.map +1 -0
  135. package/dist/e2e/inventory-weighted.e2e-test.d.ts +2 -0
  136. package/dist/e2e/inventory-weighted.e2e-test.d.ts.map +1 -0
  137. package/dist/e2e/inventory-weighted.e2e-test.js +409 -0
  138. package/dist/e2e/inventory-weighted.e2e-test.js.map +1 -0
  139. package/dist/e2e/minAmount.e2e-test.d.ts +2 -0
  140. package/dist/e2e/minAmount.e2e-test.d.ts.map +1 -0
  141. package/dist/e2e/minAmount.e2e-test.js +203 -0
  142. package/dist/e2e/minAmount.e2e-test.js.map +1 -0
  143. package/dist/e2e/mixed-weighted.e2e-test.d.ts +2 -0
  144. package/dist/e2e/mixed-weighted.e2e-test.d.ts.map +1 -0
  145. package/dist/e2e/mixed-weighted.e2e-test.js +189 -0
  146. package/dist/e2e/mixed-weighted.e2e-test.js.map +1 -0
  147. package/dist/e2e/weighted.e2e-test.d.ts +2 -0
  148. package/dist/e2e/weighted.e2e-test.d.ts.map +1 -0
  149. package/dist/e2e/weighted.e2e-test.js +198 -0
  150. package/dist/e2e/weighted.e2e-test.js.map +1 -0
  151. package/dist/factories/RebalancerContextFactory.d.ts +89 -0
  152. package/dist/factories/RebalancerContextFactory.d.ts.map +1 -0
  153. package/dist/factories/RebalancerContextFactory.js +420 -0
  154. package/dist/factories/RebalancerContextFactory.js.map +1 -0
  155. package/dist/factories/RebalancerContextFactory.test.d.ts +2 -0
  156. package/dist/factories/RebalancerContextFactory.test.d.ts.map +1 -0
  157. package/dist/factories/RebalancerContextFactory.test.js +270 -0
  158. package/dist/factories/RebalancerContextFactory.test.js.map +1 -0
  159. package/dist/index.d.ts +37 -0
  160. package/dist/index.d.ts.map +1 -0
  161. package/dist/index.js +37 -0
  162. package/dist/index.js.map +1 -0
  163. package/dist/interfaces/IExternalBridge.d.ts +103 -0
  164. package/dist/interfaces/IExternalBridge.d.ts.map +1 -0
  165. package/dist/interfaces/IExternalBridge.js +2 -0
  166. package/dist/interfaces/IExternalBridge.js.map +1 -0
  167. package/dist/interfaces/IMetrics.d.ts +5 -0
  168. package/dist/interfaces/IMetrics.d.ts.map +1 -0
  169. package/dist/interfaces/IMetrics.js +2 -0
  170. package/dist/interfaces/IMetrics.js.map +1 -0
  171. package/dist/interfaces/IMonitor.d.ts +50 -0
  172. package/dist/interfaces/IMonitor.d.ts.map +1 -0
  173. package/dist/interfaces/IMonitor.js +14 -0
  174. package/dist/interfaces/IMonitor.js.map +1 -0
  175. package/dist/interfaces/IRebalancer.d.ts +31 -0
  176. package/dist/interfaces/IRebalancer.d.ts.map +1 -0
  177. package/dist/interfaces/IRebalancer.js +2 -0
  178. package/dist/interfaces/IRebalancer.js.map +1 -0
  179. package/dist/interfaces/IStrategy.d.ts +60 -0
  180. package/dist/interfaces/IStrategy.d.ts.map +1 -0
  181. package/dist/interfaces/IStrategy.js +13 -0
  182. package/dist/interfaces/IStrategy.js.map +1 -0
  183. package/dist/metrics/Metrics.d.ts +25 -0
  184. package/dist/metrics/Metrics.d.ts.map +1 -0
  185. package/dist/metrics/Metrics.js +164 -0
  186. package/dist/metrics/Metrics.js.map +1 -0
  187. package/dist/metrics/PriceGetter.d.ts +10 -0
  188. package/dist/metrics/PriceGetter.d.ts.map +1 -0
  189. package/dist/metrics/PriceGetter.js +41 -0
  190. package/dist/metrics/PriceGetter.js.map +1 -0
  191. package/dist/metrics/scripts/metrics.d.ts +28 -0
  192. package/dist/metrics/scripts/metrics.d.ts.map +1 -0
  193. package/dist/metrics/scripts/metrics.js +61 -0
  194. package/dist/metrics/scripts/metrics.js.map +1 -0
  195. package/dist/monitor/Monitor.d.ts +40 -0
  196. package/dist/monitor/Monitor.d.ts.map +1 -0
  197. package/dist/monitor/Monitor.js +211 -0
  198. package/dist/monitor/Monitor.js.map +1 -0
  199. package/dist/service.d.ts +3 -0
  200. package/dist/service.d.ts.map +1 -0
  201. package/dist/service.js +205 -0
  202. package/dist/service.js.map +1 -0
  203. package/dist/strategy/BaseStrategy.d.ts +86 -0
  204. package/dist/strategy/BaseStrategy.d.ts.map +1 -0
  205. package/dist/strategy/BaseStrategy.js +342 -0
  206. package/dist/strategy/BaseStrategy.js.map +1 -0
  207. package/dist/strategy/CollateralDeficitStrategy.d.ts +65 -0
  208. package/dist/strategy/CollateralDeficitStrategy.d.ts.map +1 -0
  209. package/dist/strategy/CollateralDeficitStrategy.js +253 -0
  210. package/dist/strategy/CollateralDeficitStrategy.js.map +1 -0
  211. package/dist/strategy/CollateralDeficitStrategy.test.d.ts +2 -0
  212. package/dist/strategy/CollateralDeficitStrategy.test.d.ts.map +1 -0
  213. package/dist/strategy/CollateralDeficitStrategy.test.js +497 -0
  214. package/dist/strategy/CollateralDeficitStrategy.test.js.map +1 -0
  215. package/dist/strategy/CompositeStrategy.d.ts +18 -0
  216. package/dist/strategy/CompositeStrategy.d.ts.map +1 -0
  217. package/dist/strategy/CompositeStrategy.js +63 -0
  218. package/dist/strategy/CompositeStrategy.js.map +1 -0
  219. package/dist/strategy/CompositeStrategy.test.d.ts +2 -0
  220. package/dist/strategy/CompositeStrategy.test.d.ts.map +1 -0
  221. package/dist/strategy/CompositeStrategy.test.js +278 -0
  222. package/dist/strategy/CompositeStrategy.test.js.map +1 -0
  223. package/dist/strategy/MinAmountStrategy.d.ts +35 -0
  224. package/dist/strategy/MinAmountStrategy.d.ts.map +1 -0
  225. package/dist/strategy/MinAmountStrategy.js +112 -0
  226. package/dist/strategy/MinAmountStrategy.js.map +1 -0
  227. package/dist/strategy/MinAmountStrategy.test.d.ts +2 -0
  228. package/dist/strategy/MinAmountStrategy.test.d.ts.map +1 -0
  229. package/dist/strategy/MinAmountStrategy.test.js +547 -0
  230. package/dist/strategy/MinAmountStrategy.test.js.map +1 -0
  231. package/dist/strategy/StrategyFactory.d.ts +27 -0
  232. package/dist/strategy/StrategyFactory.d.ts.map +1 -0
  233. package/dist/strategy/StrategyFactory.js +79 -0
  234. package/dist/strategy/StrategyFactory.js.map +1 -0
  235. package/dist/strategy/StrategyFactory.test.d.ts +2 -0
  236. package/dist/strategy/StrategyFactory.test.d.ts.map +1 -0
  237. package/dist/strategy/StrategyFactory.test.js +81 -0
  238. package/dist/strategy/StrategyFactory.test.js.map +1 -0
  239. package/dist/strategy/WeightedStrategy.d.ts +32 -0
  240. package/dist/strategy/WeightedStrategy.d.ts.map +1 -0
  241. package/dist/strategy/WeightedStrategy.js +73 -0
  242. package/dist/strategy/WeightedStrategy.js.map +1 -0
  243. package/dist/strategy/WeightedStrategy.test.d.ts +2 -0
  244. package/dist/strategy/WeightedStrategy.test.d.ts.map +1 -0
  245. package/dist/strategy/WeightedStrategy.test.js +403 -0
  246. package/dist/strategy/WeightedStrategy.test.js.map +1 -0
  247. package/dist/strategy/index.d.ts +7 -0
  248. package/dist/strategy/index.d.ts.map +1 -0
  249. package/dist/strategy/index.js +7 -0
  250. package/dist/strategy/index.js.map +1 -0
  251. package/dist/test/helpers.d.ts +99 -0
  252. package/dist/test/helpers.d.ts.map +1 -0
  253. package/dist/test/helpers.js +311 -0
  254. package/dist/test/helpers.js.map +1 -0
  255. package/dist/test/lifiMocks.d.ts +52 -0
  256. package/dist/test/lifiMocks.d.ts.map +1 -0
  257. package/dist/test/lifiMocks.js +160 -0
  258. package/dist/test/lifiMocks.js.map +1 -0
  259. package/dist/tracking/ActionTracker.d.ts +90 -0
  260. package/dist/tracking/ActionTracker.d.ts.map +1 -0
  261. package/dist/tracking/ActionTracker.js +678 -0
  262. package/dist/tracking/ActionTracker.js.map +1 -0
  263. package/dist/tracking/ActionTracker.test.d.ts +2 -0
  264. package/dist/tracking/ActionTracker.test.d.ts.map +1 -0
  265. package/dist/tracking/ActionTracker.test.js +1351 -0
  266. package/dist/tracking/ActionTracker.test.js.map +1 -0
  267. package/dist/tracking/IActionTracker.d.ts +157 -0
  268. package/dist/tracking/IActionTracker.d.ts.map +1 -0
  269. package/dist/tracking/IActionTracker.js +2 -0
  270. package/dist/tracking/IActionTracker.js.map +1 -0
  271. package/dist/tracking/InflightContextAdapter.d.ts +18 -0
  272. package/dist/tracking/InflightContextAdapter.d.ts.map +1 -0
  273. package/dist/tracking/InflightContextAdapter.js +52 -0
  274. package/dist/tracking/InflightContextAdapter.js.map +1 -0
  275. package/dist/tracking/InflightContextAdapter.test.d.ts +2 -0
  276. package/dist/tracking/InflightContextAdapter.test.d.ts.map +1 -0
  277. package/dist/tracking/InflightContextAdapter.test.js +175 -0
  278. package/dist/tracking/InflightContextAdapter.test.js.map +1 -0
  279. package/dist/tracking/store/IStore.d.ts +41 -0
  280. package/dist/tracking/store/IStore.d.ts.map +1 -0
  281. package/dist/tracking/store/IStore.js +2 -0
  282. package/dist/tracking/store/IStore.js.map +1 -0
  283. package/dist/tracking/store/InMemoryStore.d.ts +21 -0
  284. package/dist/tracking/store/InMemoryStore.d.ts.map +1 -0
  285. package/dist/tracking/store/InMemoryStore.js +40 -0
  286. package/dist/tracking/store/InMemoryStore.js.map +1 -0
  287. package/dist/tracking/store/InMemoryStore.test.d.ts +2 -0
  288. package/dist/tracking/store/InMemoryStore.test.d.ts.map +1 -0
  289. package/dist/tracking/store/InMemoryStore.test.js +290 -0
  290. package/dist/tracking/store/InMemoryStore.test.js.map +1 -0
  291. package/dist/tracking/store/index.d.ts +3 -0
  292. package/dist/tracking/store/index.d.ts.map +1 -0
  293. package/dist/tracking/store/index.js +2 -0
  294. package/dist/tracking/store/index.js.map +1 -0
  295. package/dist/tracking/types.d.ts +77 -0
  296. package/dist/tracking/types.d.ts.map +1 -0
  297. package/dist/tracking/types.js +2 -0
  298. package/dist/tracking/types.js.map +1 -0
  299. package/dist/utils/ExplorerClient.d.ts +68 -0
  300. package/dist/utils/ExplorerClient.d.ts.map +1 -0
  301. package/dist/utils/ExplorerClient.js +324 -0
  302. package/dist/utils/ExplorerClient.js.map +1 -0
  303. package/dist/utils/ExplorerClient.test.d.ts +2 -0
  304. package/dist/utils/ExplorerClient.test.d.ts.map +1 -0
  305. package/dist/utils/ExplorerClient.test.js +261 -0
  306. package/dist/utils/ExplorerClient.test.js.map +1 -0
  307. package/dist/utils/balanceUtils.d.ts +12 -0
  308. package/dist/utils/balanceUtils.d.ts.map +1 -0
  309. package/dist/utils/balanceUtils.js +40 -0
  310. package/dist/utils/balanceUtils.js.map +1 -0
  311. package/dist/utils/balanceUtils.test.d.ts +2 -0
  312. package/dist/utils/balanceUtils.test.d.ts.map +1 -0
  313. package/dist/utils/balanceUtils.test.js +55 -0
  314. package/dist/utils/balanceUtils.test.js.map +1 -0
  315. package/dist/utils/blockTag.d.ts +14 -0
  316. package/dist/utils/blockTag.d.ts.map +1 -0
  317. package/dist/utils/blockTag.js +46 -0
  318. package/dist/utils/blockTag.js.map +1 -0
  319. package/dist/utils/bridgeUtils.d.ts +40 -0
  320. package/dist/utils/bridgeUtils.d.ts.map +1 -0
  321. package/dist/utils/bridgeUtils.js +54 -0
  322. package/dist/utils/bridgeUtils.js.map +1 -0
  323. package/dist/utils/bridgeUtils.test.d.ts +2 -0
  324. package/dist/utils/bridgeUtils.test.d.ts.map +1 -0
  325. package/dist/utils/bridgeUtils.test.js +163 -0
  326. package/dist/utils/bridgeUtils.test.js.map +1 -0
  327. package/dist/utils/errors.d.ts +4 -0
  328. package/dist/utils/errors.d.ts.map +1 -0
  329. package/dist/utils/errors.js +6 -0
  330. package/dist/utils/errors.js.map +1 -0
  331. package/dist/utils/gasEstimation.d.ts +65 -0
  332. package/dist/utils/gasEstimation.d.ts.map +1 -0
  333. package/dist/utils/gasEstimation.js +206 -0
  334. package/dist/utils/gasEstimation.js.map +1 -0
  335. package/dist/utils/solanaKeyParser.d.ts +10 -0
  336. package/dist/utils/solanaKeyParser.d.ts.map +1 -0
  337. package/dist/utils/solanaKeyParser.js +87 -0
  338. package/dist/utils/solanaKeyParser.js.map +1 -0
  339. package/dist/utils/solanaKeyParser.test.d.ts +2 -0
  340. package/dist/utils/solanaKeyParser.test.d.ts.map +1 -0
  341. package/dist/utils/solanaKeyParser.test.js +71 -0
  342. package/dist/utils/solanaKeyParser.test.js.map +1 -0
  343. package/dist/utils/tokenUtils.d.ts +38 -0
  344. package/dist/utils/tokenUtils.d.ts.map +1 -0
  345. package/dist/utils/tokenUtils.js +65 -0
  346. package/dist/utils/tokenUtils.js.map +1 -0
  347. package/dist/utils/transactionUtils.d.ts +22 -0
  348. package/dist/utils/transactionUtils.d.ts.map +1 -0
  349. package/dist/utils/transactionUtils.js +26 -0
  350. package/dist/utils/transactionUtils.js.map +1 -0
  351. package/package.json +87 -3
  352. package/src/bridges/LiFiBridge.test.ts +615 -0
  353. package/src/bridges/LiFiBridge.ts +731 -0
  354. package/src/config/RebalancerConfig.test.ts +921 -0
  355. package/src/config/RebalancerConfig.ts +63 -0
  356. package/src/config/types.ts +613 -0
  357. package/src/core/InventoryRebalancer.test.ts +1858 -0
  358. package/src/core/InventoryRebalancer.ts +1455 -0
  359. package/src/core/Rebalancer.test.ts +686 -0
  360. package/src/core/Rebalancer.ts +686 -0
  361. package/src/core/RebalancerOrchestrator.test.ts +871 -0
  362. package/src/core/RebalancerOrchestrator.ts +273 -0
  363. package/src/core/RebalancerService.test.ts +1094 -0
  364. package/src/core/RebalancerService.ts +412 -0
  365. package/src/e2e/E2E_TEST_CONVENTIONS.md +222 -0
  366. package/src/e2e/collateral-deficit.e2e-test.ts +403 -0
  367. package/src/e2e/composite.e2e-test.ts +1008 -0
  368. package/src/e2e/fixtures/routes.ts +532 -0
  369. package/src/e2e/harness/BaseLocalDeploymentManager.ts +246 -0
  370. package/src/e2e/harness/BridgeSetup.ts +95 -0
  371. package/src/e2e/harness/Erc20InventoryLocalDeploymentManager.ts +183 -0
  372. package/src/e2e/harness/Erc20LocalDeploymentManager.ts +190 -0
  373. package/src/e2e/harness/ForkIndexer.test.ts +448 -0
  374. package/src/e2e/harness/ForkIndexer.ts +183 -0
  375. package/src/e2e/harness/MixedLocalDeploymentManager.ts +196 -0
  376. package/src/e2e/harness/MockExplorerClient.ts +94 -0
  377. package/src/e2e/harness/MockExternalBridge.ts +411 -0
  378. package/src/e2e/harness/NativeLocalDeploymentManager.ts +138 -0
  379. package/src/e2e/harness/SnapshotHelper.ts +56 -0
  380. package/src/e2e/harness/TestHelpers.ts +169 -0
  381. package/src/e2e/harness/TestRebalancer.ts +758 -0
  382. package/src/e2e/harness/TransferHelper.ts +188 -0
  383. package/src/e2e/inventory-erc20-minAmount.e2e-test.ts +735 -0
  384. package/src/e2e/inventory-erc20-weighted.e2e-test.ts +733 -0
  385. package/src/e2e/inventory-minAmount.e2e-test.ts +734 -0
  386. package/src/e2e/inventory-weighted.e2e-test.ts +734 -0
  387. package/src/e2e/minAmount.e2e-test.ts +313 -0
  388. package/src/e2e/mixed-weighted.e2e-test.ts +267 -0
  389. package/src/e2e/weighted.e2e-test.ts +304 -0
  390. package/src/factories/RebalancerContextFactory.test.ts +394 -0
  391. package/src/factories/RebalancerContextFactory.ts +771 -0
  392. package/src/index.ts +125 -0
  393. package/src/interfaces/IExternalBridge.ts +117 -0
  394. package/src/interfaces/IMetrics.ts +5 -0
  395. package/src/interfaces/IMonitor.ts +71 -0
  396. package/src/interfaces/IRebalancer.ts +57 -0
  397. package/src/interfaces/IStrategy.ts +81 -0
  398. package/src/metrics/Metrics.ts +335 -0
  399. package/src/metrics/PriceGetter.ts +74 -0
  400. package/src/metrics/scripts/metrics.ts +139 -0
  401. package/src/monitor/Monitor.ts +324 -0
  402. package/src/service.ts +285 -0
  403. package/src/strategy/BaseStrategy.ts +553 -0
  404. package/src/strategy/CollateralDeficitStrategy.test.ts +728 -0
  405. package/src/strategy/CollateralDeficitStrategy.ts +421 -0
  406. package/src/strategy/CompositeStrategy.test.ts +418 -0
  407. package/src/strategy/CompositeStrategy.ts +102 -0
  408. package/src/strategy/MinAmountStrategy.test.ts +732 -0
  409. package/src/strategy/MinAmountStrategy.ts +200 -0
  410. package/src/strategy/StrategyFactory.test.ts +108 -0
  411. package/src/strategy/StrategyFactory.ts +157 -0
  412. package/src/strategy/WeightedStrategy.test.ts +529 -0
  413. package/src/strategy/WeightedStrategy.ts +126 -0
  414. package/src/strategy/index.ts +6 -0
  415. package/src/test/helpers.ts +477 -0
  416. package/src/test/lifiMocks.ts +211 -0
  417. package/src/tracking/ActionTracker.test.ts +1625 -0
  418. package/src/tracking/ActionTracker.ts +1019 -0
  419. package/src/tracking/IActionTracker.ts +213 -0
  420. package/src/tracking/InflightContextAdapter.test.ts +206 -0
  421. package/src/tracking/InflightContextAdapter.ts +75 -0
  422. package/src/tracking/store/IStore.ts +48 -0
  423. package/src/tracking/store/InMemoryStore.test.ts +338 -0
  424. package/src/tracking/store/InMemoryStore.ts +59 -0
  425. package/src/tracking/store/index.ts +2 -0
  426. package/src/tracking/types.ts +118 -0
  427. package/src/utils/ExplorerClient.test.ts +386 -0
  428. package/src/utils/ExplorerClient.ts +439 -0
  429. package/src/utils/balanceUtils.test.ts +79 -0
  430. package/src/utils/balanceUtils.ts +65 -0
  431. package/src/utils/blockTag.ts +68 -0
  432. package/src/utils/bridgeUtils.test.ts +193 -0
  433. package/src/utils/bridgeUtils.ts +101 -0
  434. package/src/utils/errors.ts +5 -0
  435. package/src/utils/gasEstimation.ts +306 -0
  436. package/src/utils/solanaKeyParser.test.ts +103 -0
  437. package/src/utils/solanaKeyParser.ts +117 -0
  438. package/src/utils/tokenUtils.ts +89 -0
  439. package/src/utils/transactionUtils.ts +41 -0
@@ -0,0 +1,313 @@
1
+ import { expect } from 'chai';
2
+ import { BigNumber, providers } from 'ethers';
3
+
4
+ import {
5
+ HyperlaneCore,
6
+ MultiProvider,
7
+ snapshot,
8
+ } from '@humanode-hyperlane/sdk';
9
+
10
+ import {
11
+ RebalancerMinAmountType,
12
+ RebalancerStrategyOptions,
13
+ type StrategyConfig,
14
+ } from '../config/types.js';
15
+
16
+ import {
17
+ DOMAIN_IDS,
18
+ type DeployedAddresses,
19
+ TEST_CHAINS,
20
+ } from './fixtures/routes.js';
21
+ import { getAllCollateralBalances } from './harness/BridgeSetup.js';
22
+ import { type LocalDeploymentContext } from './harness/BaseLocalDeploymentManager.js';
23
+ import { Erc20LocalDeploymentManager } from './harness/Erc20LocalDeploymentManager.js';
24
+ import { resetSnapshotsAndRefreshProviders } from './harness/SnapshotHelper.js';
25
+ import { getFirstMonitorEvent } from './harness/TestHelpers.js';
26
+ import { TestRebalancer } from './harness/TestRebalancer.js';
27
+ import { tryRelayMessage } from './harness/TransferHelper.js';
28
+
29
+ describe('MinAmountStrategy E2E', function () {
30
+ this.timeout(300_000);
31
+
32
+ let deploymentManager: Erc20LocalDeploymentManager;
33
+ let multiProvider: MultiProvider;
34
+ let localProviders: Map<string, providers.JsonRpcProvider>;
35
+ let snapshotIds: Map<string, string>;
36
+ let hyperlaneCore: HyperlaneCore;
37
+ let deployedAddresses: DeployedAddresses;
38
+ let minAmountStrategyConfig: StrategyConfig[];
39
+
40
+ before(async function () {
41
+ deploymentManager = new Erc20LocalDeploymentManager();
42
+ const ctx: LocalDeploymentContext<DeployedAddresses> =
43
+ await deploymentManager.start();
44
+ multiProvider = ctx.multiProvider;
45
+ localProviders = ctx.providers;
46
+ deployedAddresses = ctx.deployedAddresses;
47
+
48
+ const coreAddresses: Record<string, Record<string, string>> = {};
49
+ for (const chain of TEST_CHAINS) {
50
+ coreAddresses[chain] = {
51
+ mailbox: deployedAddresses.chains[chain].mailbox,
52
+ interchainSecurityModule: deployedAddresses.chains[chain].ism,
53
+ };
54
+ }
55
+ hyperlaneCore = HyperlaneCore.fromAddressesMap(
56
+ coreAddresses,
57
+ multiProvider,
58
+ );
59
+
60
+ minAmountStrategyConfig = [
61
+ {
62
+ rebalanceStrategy: RebalancerStrategyOptions.MinAmount,
63
+ chains: {
64
+ anvil1: {
65
+ minAmount: {
66
+ min: '100',
67
+ target: '120',
68
+ type: RebalancerMinAmountType.Absolute,
69
+ },
70
+ bridge: deployedAddresses.bridgeRoute1.anvil1,
71
+ },
72
+ anvil2: {
73
+ minAmount: {
74
+ min: '100',
75
+ target: '120',
76
+ type: RebalancerMinAmountType.Absolute,
77
+ },
78
+ bridge: deployedAddresses.bridgeRoute1.anvil2,
79
+ },
80
+ anvil3: {
81
+ minAmount: {
82
+ min: '100',
83
+ target: '120',
84
+ type: RebalancerMinAmountType.Absolute,
85
+ },
86
+ bridge: deployedAddresses.bridgeRoute1.anvil3,
87
+ },
88
+ },
89
+ },
90
+ ];
91
+
92
+ snapshotIds = new Map();
93
+ for (const [chain, provider] of localProviders) {
94
+ snapshotIds.set(chain, await snapshot(provider));
95
+ }
96
+ });
97
+
98
+ afterEach(async function () {
99
+ await resetSnapshotsAndRefreshProviders({
100
+ localProviders,
101
+ multiProvider,
102
+ snapshotIds,
103
+ });
104
+ });
105
+
106
+ after(async function () {
107
+ if (deploymentManager) {
108
+ await deploymentManager.stop();
109
+ }
110
+ });
111
+
112
+ it('should propose rebalance routes when chain is below minimum', async function () {
113
+ const context = await TestRebalancer.builder(
114
+ deploymentManager,
115
+ multiProvider,
116
+ )
117
+ .withStrategy(minAmountStrategyConfig)
118
+ .withBalances('BELOW_MIN_ARB')
119
+ .withExecutionMode('execute')
120
+ .build();
121
+
122
+ const monitor = context.createMonitor(0);
123
+ const event = await getFirstMonitorEvent(monitor);
124
+
125
+ await context.orchestrator.executeCycle(event);
126
+
127
+ // Assert: ethereum→arbitrum, amount=70 USDC to reach 120 target from 50
128
+ const activeIntents = await context.tracker.getActiveRebalanceIntents();
129
+ expect(activeIntents.length).to.equal(1);
130
+ expect(activeIntents[0].origin).to.equal(DOMAIN_IDS.anvil1);
131
+ expect(activeIntents[0].destination).to.equal(DOMAIN_IDS.anvil2);
132
+ expect(activeIntents[0].amount).to.equal(70000000n);
133
+ });
134
+
135
+ it('should not propose routes when all chains at or above minimum', async function () {
136
+ const context = await TestRebalancer.builder(
137
+ deploymentManager,
138
+ multiProvider,
139
+ )
140
+ .withStrategy(minAmountStrategyConfig)
141
+ .withBalances('BALANCED')
142
+ .withExecutionMode('execute')
143
+ .build();
144
+
145
+ const monitor = context.createMonitor(0);
146
+ const event = await getFirstMonitorEvent(monitor);
147
+
148
+ await context.orchestrator.executeCycle(event);
149
+
150
+ // Assert: No routes - all chains have 5000 USDC, well above 100 min
151
+ const activeIntents = await context.tracker.getActiveRebalanceIntents();
152
+ expect(activeIntents.length).to.equal(0);
153
+ });
154
+
155
+ it('should execute full rebalance cycle with actual transfers', async function () {
156
+ const context = await TestRebalancer.builder(
157
+ deploymentManager,
158
+ multiProvider,
159
+ )
160
+ .withStrategy(minAmountStrategyConfig)
161
+ .withBalances('BELOW_MIN_ARB')
162
+ .withExecutionMode('execute')
163
+ .build();
164
+
165
+ const initialCollateralBalances = await getAllCollateralBalances(
166
+ localProviders,
167
+ TEST_CHAINS,
168
+ deployedAddresses.monitoredRoute,
169
+ deployedAddresses.tokens,
170
+ );
171
+
172
+ const monitor = context.createMonitor(0);
173
+ const event = await getFirstMonitorEvent(monitor);
174
+ await context.orchestrator.executeCycle(event);
175
+
176
+ // Assert: Rebalance intent was created with correct fields
177
+ const activeIntents = await context.tracker.getActiveRebalanceIntents();
178
+ expect(activeIntents.length).to.equal(1);
179
+ expect(activeIntents[0].destination).to.equal(DOMAIN_IDS.anvil2);
180
+ expect(activeIntents[0].amount).to.equal(70000000n);
181
+
182
+ // Assert: Rebalance action was created
183
+ const inProgressActions = await context.tracker.getInProgressActions();
184
+ expect(inProgressActions.length).to.equal(1);
185
+
186
+ const actionToArbitrum = inProgressActions[0];
187
+ expect(actionToArbitrum.destination).to.equal(DOMAIN_IDS.anvil2);
188
+ expect(actionToArbitrum.amount).to.equal(70000000n);
189
+
190
+ // Assert: Monitored route collateral on origin DECREASED (sent to bridge)
191
+ const balancesAfterRebalance = await getAllCollateralBalances(
192
+ localProviders,
193
+ TEST_CHAINS,
194
+ deployedAddresses.monitoredRoute,
195
+ deployedAddresses.tokens,
196
+ );
197
+
198
+ // Assert: ethereum balance decreased by 70 USDC
199
+ const expectedDecrease = BigNumber.from(70000000);
200
+ expect(
201
+ initialCollateralBalances.anvil1.sub(expectedDecrease).toString(),
202
+ ).to.equal(balancesAfterRebalance.anvil1.toString());
203
+
204
+ // Relay the rebalance message to destination
205
+ const ethProvider = localProviders.get('anvil1')!;
206
+ const rebalanceTxReceipt = await ethProvider.getTransactionReceipt(
207
+ actionToArbitrum.txHash!,
208
+ );
209
+ const rebalanceRelayResult = await tryRelayMessage(
210
+ multiProvider,
211
+ hyperlaneCore,
212
+ {
213
+ dispatchTx: rebalanceTxReceipt,
214
+ messageId: actionToArbitrum.messageId!,
215
+ origin: 'anvil1',
216
+ destination: 'anvil2',
217
+ },
218
+ );
219
+ expect(
220
+ rebalanceRelayResult.success,
221
+ `Rebalance relay should succeed: ${rebalanceRelayResult.error}`,
222
+ ).to.be.true;
223
+
224
+ // Sync actions to detect delivery and mark complete
225
+ const blockTags = await context.getConfirmedBlockTags();
226
+ await context.tracker.syncRebalanceActions(blockTags);
227
+
228
+ // Assert: Action is now complete
229
+ const completedAction = await context.tracker.getRebalanceAction(
230
+ actionToArbitrum.id,
231
+ );
232
+ expect(completedAction!.status).to.equal('complete');
233
+
234
+ // Assert: Intent is now complete
235
+ const completedIntent = await context.tracker.getRebalanceIntent(
236
+ activeIntents[0].id,
237
+ );
238
+ expect(completedIntent!.status).to.equal('complete');
239
+ });
240
+
241
+ it('should handle stuck transfer and propose routes to destination', async function () {
242
+ const context = await TestRebalancer.builder(
243
+ deploymentManager,
244
+ multiProvider,
245
+ )
246
+ .withStrategy(minAmountStrategyConfig)
247
+ .withBalances('BELOW_MIN_ARB')
248
+ .withExecutionMode('execute')
249
+ .build();
250
+
251
+ // ===== CYCLE 1: Execute to create inflight eth→arb =====
252
+ // Initial: eth=6000, arb=50 (below 100 min), base=4000
253
+ // MinAmount will trigger: arb needs 100, so propose ~70 USDC from eth
254
+ const monitor1 = context.createMonitor(0);
255
+ const event1 = await getFirstMonitorEvent(monitor1);
256
+ await context.orchestrator.executeCycle(event1);
257
+
258
+ const blockTags1 = await context.getConfirmedBlockTags();
259
+ await context.tracker.syncRebalanceActions(blockTags1);
260
+
261
+ const inProgress = await context.tracker.getInProgressActions();
262
+ expect(
263
+ inProgress.length,
264
+ 'Cycle 1 should create inflight action',
265
+ ).to.be.greaterThan(0);
266
+
267
+ const inflightToArb = inProgress.find(
268
+ (a) =>
269
+ a.destination === DOMAIN_IDS.anvil2 && a.origin === DOMAIN_IDS.anvil1,
270
+ );
271
+ expect(inflightToArb, 'Should have inflight action eth→arb').to.exist;
272
+
273
+ // ===== CYCLE 2: Execute again - should account for inflight =====
274
+ // Strategy sees: arb effective = 50 + inflight ≈ 120 (target)
275
+ // Should propose reduced amount or nothing to arb (within tolerance)
276
+ const monitor2 = context.createMonitor(0);
277
+ const event2 = await getFirstMonitorEvent(monitor2);
278
+ await context.orchestrator.executeCycle(event2);
279
+
280
+ const blockTags = await context.getConfirmedBlockTags();
281
+ await context.tracker.syncRebalanceActions(blockTags);
282
+
283
+ // Check if new routes to arb were proposed
284
+ const inProgressAfterCycle2 = await context.tracker.getInProgressActions();
285
+ const newActionsToArb = inProgressAfterCycle2.filter(
286
+ (a) =>
287
+ a.destination === DOMAIN_IDS.anvil2 &&
288
+ a.id !== inflightToArb!.id &&
289
+ a.status === 'in_progress',
290
+ );
291
+
292
+ if (newActionsToArb.length > 0) {
293
+ // If route was proposed, should be much smaller than original ~70 USDC
294
+ const proposedAmount = BigNumber.from(
295
+ newActionsToArb[0].amount,
296
+ ).toBigInt();
297
+ expect(
298
+ proposedAmount < 50000000n,
299
+ `Amount to arb (${proposedAmount}) should be reduced accounting for inflight`,
300
+ ).to.be.true;
301
+ }
302
+ // If no new route to arb, that's valid (within tolerance after inflight)
303
+
304
+ // Verify inflight still exists and action tracking is working
305
+ const finalInProgress = await context.tracker.getInProgressActions();
306
+ const inflightStillActive = finalInProgress.find(
307
+ (a) => a.id === inflightToArb!.id,
308
+ );
309
+ expect(inflightStillActive, 'Inflight action should still be tracked').to
310
+ .exist;
311
+ expect(inflightStillActive!.status).to.equal('in_progress');
312
+ });
313
+ });
@@ -0,0 +1,267 @@
1
+ import { expect } from 'chai';
2
+ import { BigNumber, Wallet, providers } from 'ethers';
3
+
4
+ import {
5
+ HyperlaneCore,
6
+ MultiProvider,
7
+ revertToSnapshot,
8
+ snapshot,
9
+ } from '@humanode-hyperlane/sdk';
10
+
11
+ import {
12
+ ExecutionType,
13
+ ExternalBridgeType,
14
+ RebalancerConfigSchema,
15
+ RebalancerStrategyOptions,
16
+ type StrategyConfig,
17
+ } from '../config/types.js';
18
+
19
+ import {
20
+ ANVIL_USER_PRIVATE_KEY,
21
+ type Erc20InventoryDeployedAddresses,
22
+ TEST_CHAINS,
23
+ } from './fixtures/routes.js';
24
+ import {
25
+ MIXED_INVENTORY_CHAIN,
26
+ MIXED_INVENTORY_OVERRIDE,
27
+ MIXED_MOVABLE_CHAINS,
28
+ MixedLocalDeploymentManager,
29
+ } from './harness/MixedLocalDeploymentManager.js';
30
+ import { MockExternalBridge } from './harness/MockExternalBridge.js';
31
+ import { getFirstMonitorEvent } from './harness/TestHelpers.js';
32
+ import {
33
+ type TestRebalancerContext,
34
+ TestRebalancerBuilder,
35
+ } from './harness/TestRebalancer.js';
36
+
37
+ function buildMixedWeightedStrategyConfig(
38
+ addresses: Erc20InventoryDeployedAddresses,
39
+ ): StrategyConfig[] {
40
+ return [
41
+ {
42
+ rebalanceStrategy: RebalancerStrategyOptions.Weighted,
43
+ chains: {
44
+ anvil1: {
45
+ weighted: { weight: 60n, tolerance: 5n },
46
+ bridge: addresses.bridgeRoute.anvil1,
47
+ executionType: ExecutionType.MovableCollateral,
48
+ override: {
49
+ [MIXED_INVENTORY_CHAIN]: {
50
+ ...MIXED_INVENTORY_OVERRIDE,
51
+ },
52
+ },
53
+ },
54
+ anvil2: {
55
+ weighted: { weight: 20n, tolerance: 5n },
56
+ bridge: addresses.bridgeRoute.anvil2,
57
+ executionType: ExecutionType.MovableCollateral,
58
+ override: {
59
+ [MIXED_INVENTORY_CHAIN]: {
60
+ ...MIXED_INVENTORY_OVERRIDE,
61
+ },
62
+ },
63
+ },
64
+ anvil3: {
65
+ weighted: { weight: 20n, tolerance: 5n },
66
+ bridge: addresses.bridgeRoute.anvil3,
67
+ executionType: ExecutionType.MovableCollateral,
68
+ },
69
+ },
70
+ },
71
+ ];
72
+ }
73
+
74
+ describe('Mixed WeightedStrategy E2E', function () {
75
+ this.timeout(300_000);
76
+
77
+ let deploymentManager: MixedLocalDeploymentManager;
78
+ let multiProvider: MultiProvider;
79
+ let localProviders: Map<string, providers.JsonRpcProvider>;
80
+ let snapshotIds: Map<string, string>;
81
+ let hyperlaneCore: HyperlaneCore;
82
+ let deployedAddresses: Erc20InventoryDeployedAddresses;
83
+ let mixedStrategyConfig: StrategyConfig[];
84
+ let mockBridge: MockExternalBridge;
85
+
86
+ const inventorySignerAddress = new Wallet(ANVIL_USER_PRIVATE_KEY).address;
87
+
88
+ async function buildContext(
89
+ inventoryBalances: string | Record<string, BigNumber>,
90
+ ): Promise<TestRebalancerContext> {
91
+ return new TestRebalancerBuilder(deploymentManager, multiProvider)
92
+ .withStrategy(mixedStrategyConfig)
93
+ .withExecutionMode('execute')
94
+ .withErc20InventoryConfig({
95
+ inventorySignerKey: ANVIL_USER_PRIVATE_KEY,
96
+ erc20DeployedAddresses: deployedAddresses,
97
+ })
98
+ .withMockExternalBridge(mockBridge)
99
+ .withBalances(inventoryBalances)
100
+ .build();
101
+ }
102
+
103
+ before(async function () {
104
+ deploymentManager = new MixedLocalDeploymentManager(inventorySignerAddress);
105
+ const ctx = await deploymentManager.start();
106
+ multiProvider = ctx.multiProvider;
107
+ localProviders = ctx.providers;
108
+ deployedAddresses = ctx.deployedAddresses;
109
+
110
+ const coreAddresses: Record<string, Record<string, string>> = {};
111
+ for (const chain of TEST_CHAINS) {
112
+ coreAddresses[chain] = {
113
+ mailbox: deployedAddresses.chains[chain].mailbox,
114
+ interchainSecurityModule: deployedAddresses.chains[chain].ism,
115
+ };
116
+ }
117
+ hyperlaneCore = HyperlaneCore.fromAddressesMap(
118
+ coreAddresses,
119
+ multiProvider,
120
+ );
121
+
122
+ mixedStrategyConfig = buildMixedWeightedStrategyConfig(deployedAddresses);
123
+ mockBridge = new MockExternalBridge(
124
+ deployedAddresses,
125
+ multiProvider,
126
+ hyperlaneCore,
127
+ 'erc20',
128
+ );
129
+
130
+ snapshotIds = new Map();
131
+ for (const [chain, provider] of localProviders) {
132
+ snapshotIds.set(chain, await snapshot(provider));
133
+ }
134
+ });
135
+
136
+ afterEach(async function () {
137
+ mockBridge.reset();
138
+ for (const [chain, provider] of localProviders) {
139
+ const id = snapshotIds.get(chain)!;
140
+ await revertToSnapshot(provider, id);
141
+ snapshotIds.set(chain, await snapshot(provider));
142
+ Reflect.set(provider, '_maxInternalBlockNumber', -1);
143
+ Reflect.set(provider, '_internalBlockNumber', null);
144
+ }
145
+ });
146
+
147
+ after(async function () {
148
+ if (deploymentManager) {
149
+ await deploymentManager.stop();
150
+ }
151
+ });
152
+
153
+ it('accepts mixed movable + inventory override config in schema', function () {
154
+ const configResult = RebalancerConfigSchema.safeParse({
155
+ warpRouteId: 'USDC/test-mixed-weighted',
156
+ strategy: [
157
+ {
158
+ rebalanceStrategy: RebalancerStrategyOptions.Weighted,
159
+ chains: {
160
+ anvil1: {
161
+ weighted: { weight: 60, tolerance: 5 },
162
+ bridge: deployedAddresses.bridgeRoute.anvil1,
163
+ executionType: ExecutionType.MovableCollateral,
164
+ override: {
165
+ [MIXED_INVENTORY_CHAIN]: {
166
+ ...MIXED_INVENTORY_OVERRIDE,
167
+ },
168
+ },
169
+ },
170
+ anvil2: {
171
+ weighted: { weight: 20, tolerance: 5 },
172
+ bridge: deployedAddresses.bridgeRoute.anvil2,
173
+ executionType: ExecutionType.MovableCollateral,
174
+ override: {
175
+ [MIXED_INVENTORY_CHAIN]: {
176
+ ...MIXED_INVENTORY_OVERRIDE,
177
+ },
178
+ },
179
+ },
180
+ anvil3: {
181
+ weighted: { weight: 20, tolerance: 5 },
182
+ bridge: deployedAddresses.bridgeRoute.anvil3,
183
+ executionType: ExecutionType.MovableCollateral,
184
+ },
185
+ },
186
+ },
187
+ ],
188
+ inventorySigners: {
189
+ ethereum: inventorySignerAddress,
190
+ },
191
+ externalBridges: {
192
+ lifi: {
193
+ integrator: 'test',
194
+ },
195
+ },
196
+ });
197
+
198
+ expect(configResult.success).to.equal(true);
199
+ });
200
+
201
+ it('includes override-only inventory chain and creates both rebalancers', async function () {
202
+ const context = await buildContext('ERC20_INVENTORY_BALANCED');
203
+
204
+ const { rebalancers, inventoryConfig } =
205
+ await context.contextFactory.createRebalancers(
206
+ context.tracker,
207
+ undefined,
208
+ {
209
+ [ExternalBridgeType.LiFi]: mockBridge,
210
+ },
211
+ );
212
+
213
+ expect(inventoryConfig).to.exist;
214
+ expect(inventoryConfig!.chains).to.have.members([
215
+ MIXED_INVENTORY_CHAIN,
216
+ ...MIXED_MOVABLE_CHAINS,
217
+ ]);
218
+ expect(rebalancers.map((r) => r.rebalancerType).sort()).to.deep.equal([
219
+ 'inventory',
220
+ 'movableCollateral',
221
+ ]);
222
+ });
223
+
224
+ it('routes inventory destination through inventory and movable destination through movable collateral', async function () {
225
+ const context = await buildContext({
226
+ anvil1: BigNumber.from('10000000000'),
227
+ anvil2: BigNumber.from('0'),
228
+ anvil3: BigNumber.from('0'),
229
+ });
230
+
231
+ const monitor = context.createMonitor(0);
232
+ const event = await getFirstMonitorEvent(monitor);
233
+ const cycleResult = await context.orchestrator.executeCycle(event);
234
+
235
+ const routeToInventory = cycleResult.proposedRoutes.find(
236
+ (route) => route.destination === MIXED_INVENTORY_CHAIN,
237
+ );
238
+ expect(routeToInventory).to.exist;
239
+ expect(routeToInventory!.executionType).to.equal(ExecutionType.Inventory);
240
+
241
+ const movableDestination = MIXED_MOVABLE_CHAINS.find(
242
+ (chain) => chain !== 'anvil1',
243
+ )!;
244
+ const routeToMovable = cycleResult.proposedRoutes.find(
245
+ (route) => route.destination === movableDestination,
246
+ );
247
+ expect(routeToMovable).to.exist;
248
+ expect(routeToMovable!.executionType).to.equal(
249
+ ExecutionType.MovableCollateral,
250
+ );
251
+
252
+ const inProgressActions = await context.tracker.getInProgressActions();
253
+ const hasInventoryExecution = inProgressActions.some(
254
+ (action) =>
255
+ action.type === 'inventory_deposit' &&
256
+ multiProvider.getChainName(action.origin) === MIXED_INVENTORY_CHAIN,
257
+ );
258
+ const hasMovableExecution = inProgressActions.some(
259
+ (action) =>
260
+ action.type === 'rebalance_message' &&
261
+ multiProvider.getChainName(action.destination) === movableDestination,
262
+ );
263
+
264
+ expect(hasInventoryExecution).to.equal(true);
265
+ expect(hasMovableExecution).to.equal(true);
266
+ });
267
+ });