@1delta/data-sdk 0.0.47 → 0.0.48

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -95,6 +95,8 @@ var LENDER_DATA_DEFAULTS = () => ({
95
95
  llamaLendMarkets: {},
96
96
  resupplyConfig: {},
97
97
  curvanceConfig: {},
98
+ twyneConfig: {},
99
+ twyneMarkets: {},
98
100
  fraxlendConfig: {},
99
101
  eulerConfigs: {},
100
102
  eulerVaults: {},
@@ -745,6 +747,60 @@ var curvancePositionManager = (lender, chainId, marketManager, kind) => {
745
747
  return pms.simplePositionManager ?? pms.vaultPositionManager ?? pms.nativeVaultPositionManager ?? pms.pendlePtPositionManager;
746
748
  };
747
749
 
750
+ // src/lending/twyne.ts
751
+ var twyneConfig = () => getGlobalData2()?.twyneConfig;
752
+ var twyneConfigFor = (lender, chainId) => getGlobalData2()?.twyneConfig?.[twyneBaseKey(lender)]?.[String(chainId)];
753
+ var twyneMarkets = () => getGlobalData2()?.twyneMarkets;
754
+ var twyneChainData = (lender, chainId) => getGlobalData2()?.twyneMarkets?.[twyneBaseKey(lender)]?.[String(chainId)];
755
+ var twyneBaseKey = (lender) => lender?.startsWith("TWYNE") ? "TWYNE" : lender;
756
+ var twyneMarketKey = (chainId, intermediateVault, targetAsset) => `TWYNE_${chainId}_${intermediateVault.replace(/^0x/i, "").toUpperCase()}_${targetAsset.replace(/^0x/i, "").toUpperCase()}`;
757
+ var assertTwyneKeysUnique = (markets, chainId) => {
758
+ const byKey = /* @__PURE__ */ new Map();
759
+ for (const m of markets) {
760
+ const key = twyneMarketKey(chainId, m.intermediateVault, m.targetAsset);
761
+ const triple = `${m.intermediateVault}|${m.targetVault}|${m.targetAsset}`.toLowerCase();
762
+ const seen = byKey.get(key);
763
+ if (seen && seen !== triple) {
764
+ throw new Error(
765
+ `assertTwyneKeysUnique: key ${key} maps to two triples (${seen} and ${triple}). The target vault must be added back into the key.`
766
+ );
767
+ }
768
+ byKey.set(key, triple);
769
+ }
770
+ };
771
+ var twyneMarketByKey = (lender, chainId) => {
772
+ const upper = lender?.toUpperCase();
773
+ return twyneChainData(lender, chainId)?.markets?.find((m) => m.key.toUpperCase() === upper);
774
+ };
775
+ var twyneMarketFor = (lender, chainId, intermediateVault, targetAsset) => {
776
+ const iv = intermediateVault?.toLowerCase();
777
+ const asset = targetAsset?.toLowerCase();
778
+ return twyneChainData(lender, chainId)?.markets?.find(
779
+ (m) => m.intermediateVault.toLowerCase() === iv && m.targetAsset.toLowerCase() === asset
780
+ );
781
+ };
782
+ var twyneMarketsForIntermediateVault = (lender, chainId, intermediateVault) => {
783
+ const iv = intermediateVault?.toLowerCase();
784
+ return (twyneChainData(lender, chainId)?.markets ?? []).filter((m) => m.intermediateVault.toLowerCase() === iv);
785
+ };
786
+ var twyneLendersByChain = (chainId) => {
787
+ const cfg = getGlobalData2()?.twyneConfig ?? {};
788
+ const chain = String(chainId);
789
+ return Object.keys(cfg).filter((lender) => !!cfg[lender]?.[chain]?.collateralVaultFactory);
790
+ };
791
+ var twyneOperator = (lender, chainId, vaultType, kind) => twyneConfigFor(lender, chainId)?.operators?.[vaultType]?.[kind];
792
+ var twyneBeaconFor = (lender, chainId, targetVault) => {
793
+ const map = twyneConfigFor(lender, chainId)?.beacons;
794
+ if (!map || !targetVault) return void 0;
795
+ const direct = map[targetVault];
796
+ if (direct) return direct;
797
+ const target = targetVault.toLowerCase();
798
+ for (const key of Object.keys(map)) {
799
+ if (key.toLowerCase() === target) return map[key];
800
+ }
801
+ return void 0;
802
+ };
803
+
748
804
  // src/lending/fraxlend.ts
749
805
  var FRAXLEND_ETHEREUM_CONFIG = {
750
806
  deployer: "0xD6E9D27C75Afd88ad24Cd5EdccdC76fd2fc3A751",
@@ -1040,6 +1096,7 @@ exports.aaveV4Peripherals = aaveV4Peripherals;
1040
1096
  exports.aaveV4SpokeLenderKey = aaveV4SpokeLenderKey;
1041
1097
  exports.aaveV4Spokes = aaveV4Spokes;
1042
1098
  exports.aaveWethGateway = aaveWethGateway;
1099
+ exports.assertTwyneKeysUnique = assertTwyneKeysUnique;
1043
1100
  exports.chainLogoURI = chainLogoURI;
1044
1101
  exports.chains = chains;
1045
1102
  exports.clearRemoteCache = clearRemoteCache;
@@ -1207,6 +1264,18 @@ exports.termMaxChainIds = termMaxChainIds;
1207
1264
  exports.termMaxConfig = termMaxConfig;
1208
1265
  exports.termMaxConfigByChain = termMaxConfigByChain;
1209
1266
  exports.termMaxLenderKey = termMaxLenderKey;
1267
+ exports.twyneBaseKey = twyneBaseKey;
1268
+ exports.twyneBeaconFor = twyneBeaconFor;
1269
+ exports.twyneChainData = twyneChainData;
1270
+ exports.twyneConfig = twyneConfig;
1271
+ exports.twyneConfigFor = twyneConfigFor;
1272
+ exports.twyneLendersByChain = twyneLendersByChain;
1273
+ exports.twyneMarketByKey = twyneMarketByKey;
1274
+ exports.twyneMarketFor = twyneMarketFor;
1275
+ exports.twyneMarketKey = twyneMarketKey;
1276
+ exports.twyneMarkets = twyneMarkets;
1277
+ exports.twyneMarketsForIntermediateVault = twyneMarketsForIntermediateVault;
1278
+ exports.twyneOperator = twyneOperator;
1210
1279
  exports.usddChainData = usddChainData;
1211
1280
  exports.usddConfig = usddConfig;
1212
1281
  exports.usddConfigFor = usddConfigFor;
package/dist/index.mjs CHANGED
@@ -93,6 +93,8 @@ var LENDER_DATA_DEFAULTS = () => ({
93
93
  llamaLendMarkets: {},
94
94
  resupplyConfig: {},
95
95
  curvanceConfig: {},
96
+ twyneConfig: {},
97
+ twyneMarkets: {},
96
98
  fraxlendConfig: {},
97
99
  eulerConfigs: {},
98
100
  eulerVaults: {},
@@ -743,6 +745,60 @@ var curvancePositionManager = (lender, chainId, marketManager, kind) => {
743
745
  return pms.simplePositionManager ?? pms.vaultPositionManager ?? pms.nativeVaultPositionManager ?? pms.pendlePtPositionManager;
744
746
  };
745
747
 
748
+ // src/lending/twyne.ts
749
+ var twyneConfig = () => getGlobalData2()?.twyneConfig;
750
+ var twyneConfigFor = (lender, chainId) => getGlobalData2()?.twyneConfig?.[twyneBaseKey(lender)]?.[String(chainId)];
751
+ var twyneMarkets = () => getGlobalData2()?.twyneMarkets;
752
+ var twyneChainData = (lender, chainId) => getGlobalData2()?.twyneMarkets?.[twyneBaseKey(lender)]?.[String(chainId)];
753
+ var twyneBaseKey = (lender) => lender?.startsWith("TWYNE") ? "TWYNE" : lender;
754
+ var twyneMarketKey = (chainId, intermediateVault, targetAsset) => `TWYNE_${chainId}_${intermediateVault.replace(/^0x/i, "").toUpperCase()}_${targetAsset.replace(/^0x/i, "").toUpperCase()}`;
755
+ var assertTwyneKeysUnique = (markets, chainId) => {
756
+ const byKey = /* @__PURE__ */ new Map();
757
+ for (const m of markets) {
758
+ const key = twyneMarketKey(chainId, m.intermediateVault, m.targetAsset);
759
+ const triple = `${m.intermediateVault}|${m.targetVault}|${m.targetAsset}`.toLowerCase();
760
+ const seen = byKey.get(key);
761
+ if (seen && seen !== triple) {
762
+ throw new Error(
763
+ `assertTwyneKeysUnique: key ${key} maps to two triples (${seen} and ${triple}). The target vault must be added back into the key.`
764
+ );
765
+ }
766
+ byKey.set(key, triple);
767
+ }
768
+ };
769
+ var twyneMarketByKey = (lender, chainId) => {
770
+ const upper = lender?.toUpperCase();
771
+ return twyneChainData(lender, chainId)?.markets?.find((m) => m.key.toUpperCase() === upper);
772
+ };
773
+ var twyneMarketFor = (lender, chainId, intermediateVault, targetAsset) => {
774
+ const iv = intermediateVault?.toLowerCase();
775
+ const asset = targetAsset?.toLowerCase();
776
+ return twyneChainData(lender, chainId)?.markets?.find(
777
+ (m) => m.intermediateVault.toLowerCase() === iv && m.targetAsset.toLowerCase() === asset
778
+ );
779
+ };
780
+ var twyneMarketsForIntermediateVault = (lender, chainId, intermediateVault) => {
781
+ const iv = intermediateVault?.toLowerCase();
782
+ return (twyneChainData(lender, chainId)?.markets ?? []).filter((m) => m.intermediateVault.toLowerCase() === iv);
783
+ };
784
+ var twyneLendersByChain = (chainId) => {
785
+ const cfg = getGlobalData2()?.twyneConfig ?? {};
786
+ const chain = String(chainId);
787
+ return Object.keys(cfg).filter((lender) => !!cfg[lender]?.[chain]?.collateralVaultFactory);
788
+ };
789
+ var twyneOperator = (lender, chainId, vaultType, kind) => twyneConfigFor(lender, chainId)?.operators?.[vaultType]?.[kind];
790
+ var twyneBeaconFor = (lender, chainId, targetVault) => {
791
+ const map = twyneConfigFor(lender, chainId)?.beacons;
792
+ if (!map || !targetVault) return void 0;
793
+ const direct = map[targetVault];
794
+ if (direct) return direct;
795
+ const target = targetVault.toLowerCase();
796
+ for (const key of Object.keys(map)) {
797
+ if (key.toLowerCase() === target) return map[key];
798
+ }
799
+ return void 0;
800
+ };
801
+
746
802
  // src/lending/fraxlend.ts
747
803
  var FRAXLEND_ETHEREUM_CONFIG = {
748
804
  deployer: "0xD6E9D27C75Afd88ad24Cd5EdccdC76fd2fc3A751",
@@ -1022,4 +1078,4 @@ async function fetchMainTokensMap() {
1022
1078
  }
1023
1079
  }
1024
1080
 
1025
- export { CURVANCE_MONAD_CONFIG, FRAXLEND_ETHEREUM_CONFIG, GEARBOX_ACCOUNT_COMPRESSOR_V310, REMOTE_CACHE_STORE_TTL_S, RESUPPLY_ETHEREUM_CONFIG, RemoteFetchError, aaveOracles, aaveOraclesConfig, aavePools, aaveReserves, aaveTokens, aaveV4Oracles, aaveV4Peripherals, aaveV4SpokeLenderKey, aaveV4Spokes, aaveWethGateway, chainLogoURI, chains, clearRemoteCache, compoundV2Oracles, compoundV2OraclesConfig, compoundV2Pools, compoundV2Reserves, compoundV2TokenArray, compoundV2Tokens, compoundV3BaseData, compoundV3Bulker, compoundV3OraclesData, compoundV3Pools, compoundV3Reserves, curvanceConfig, curvanceConfigFor, curvanceLendersByChain, curvancePositionManager, curvancePositionManagersFor, dolomiteChains, dolomiteConfigs, dolomiteEmode, dolomiteMarketIdByToken, dssChainData, dssConfigFor, dssDebtJoin, dssDebtToken, dssMarketByIlk, eulerConfigs, eulerVaults, exactlyConfig, exactlyMarketByAddress, exactlyMarketByAsset, exactlyMarkets, exactlyMarketsByChain, fetchMainTokensMap, fetchRemoteJson, fetchTokenList, fetchTokenListFile, fetchTokenLists, findAaveV4PositionManager, fluidChains, fluidResolvers, fluidVaultEntries, fluidVaults, frankencoinChainData, frankencoinConfig, frankencoinConfigFor, frankencoinLendersByChain, frankencoinMarketByPosition, frankencoinMarkets, fraxlendConfig, fraxlendConfigFor, fraxlendLendersByChain, fraxlendPairKey, fraxlendPairsFor, gearboxAccountCompressor, gearboxAddressProviderV310, gearboxBotListV3, gearboxChains, gearboxMarketCompressor, gearboxMarketConfigurators, gearboxResolvers, gearboxV3LenderKey, getAaveV4GatewayAddresses, getAaveV4PositionManagers, getAaveV4SpokeAccess, getAaveV4SpokeEntry, getAaveV4SpokePeripherals, getChainEntries, getSiloV2MarketEntry, getSiloV3MarketEntry, initConfig, initializeChainData, initializeLenderData, inverseChainData, inverseConfig, inverseConfigFor, inverseLendersByChain, inverseMarketByAddress, inverseMarkets, isAaveV4OperationRestricted, isListaSmartLpAsset, liquityBranchByIndex, liquityBranchByTroveManager, liquityBranchesByChain, liquityConfig, liquityConfigFor, liquityLendersByChain, liquityMarkets, listaCollateralProvider, listaCollateralProviders, listaNativeProvider, listaSmartLpByCollateral, llamaLendApiBaseUrl, llamaLendChainData, llamaLendConfig, llamaLendConfigFor, llamaLendLenderKey, llamaLendLendersByChain, llamaLendLeverageZap, llamaLendMarketByController, llamaLendMarketByVault, llamaLendMarkets, llamaLendSupportsDelegation, llamaLendSupportsLeverage, loadCached, loadCachedJson, midnightApiBaseOverride, midnightConfig, midnightMarketById, midnightMarkets, midnightMarketsByChain, morphoBundler3, morphoOracles, morphoPools, morphoTypeMarkets, morphoTypeOracles, morphoTypeVaults, parseAaveV4SpokeLenderKey, parseFraxlendPairKey, parseGearboxV3LenderKey, parseLlamaLendLenderKey, parseSiloV2LenderKey, parseSiloV3LenderKey, parseTermMaxLenderKey, resolveMidnightApiBase, resolveTermApiBase, resupplyConfig, resupplyConfigFor, resupplyLendersByChain, riverChainData, riverConfig, riverConfigFor, riverLendersByChain, riverMarketByIndex, riverMarkets, setMidnightApiBase, setRemoteCacheGithubToken, setRemoteCacheStore, setTermApiBase, siloMarkets, siloMarketsV3, siloPeripherals, siloPeripheralsV3, siloV2LenderKey, siloV3LenderKey, skyChainData, skyConfig, skyConfigFor, skyLendersByChain, skyMarkets, tellerConfig, tellerConfigByChain, tellerPoolByAddress, tellerPools, tellerPoolsByChain, termApiBaseOverride, termConfig, termMarketById, termMarkets, termMarketsByChain, termMaxApiBaseUrl, termMaxChainIds, termMaxConfig, termMaxConfigByChain, termMaxLenderKey, usddChainData, usddConfig, usddConfigFor, usddLendersByChain, usddMarketByIlk, usddMarkets };
1081
+ export { CURVANCE_MONAD_CONFIG, FRAXLEND_ETHEREUM_CONFIG, GEARBOX_ACCOUNT_COMPRESSOR_V310, REMOTE_CACHE_STORE_TTL_S, RESUPPLY_ETHEREUM_CONFIG, RemoteFetchError, aaveOracles, aaveOraclesConfig, aavePools, aaveReserves, aaveTokens, aaveV4Oracles, aaveV4Peripherals, aaveV4SpokeLenderKey, aaveV4Spokes, aaveWethGateway, assertTwyneKeysUnique, chainLogoURI, chains, clearRemoteCache, compoundV2Oracles, compoundV2OraclesConfig, compoundV2Pools, compoundV2Reserves, compoundV2TokenArray, compoundV2Tokens, compoundV3BaseData, compoundV3Bulker, compoundV3OraclesData, compoundV3Pools, compoundV3Reserves, curvanceConfig, curvanceConfigFor, curvanceLendersByChain, curvancePositionManager, curvancePositionManagersFor, dolomiteChains, dolomiteConfigs, dolomiteEmode, dolomiteMarketIdByToken, dssChainData, dssConfigFor, dssDebtJoin, dssDebtToken, dssMarketByIlk, eulerConfigs, eulerVaults, exactlyConfig, exactlyMarketByAddress, exactlyMarketByAsset, exactlyMarkets, exactlyMarketsByChain, fetchMainTokensMap, fetchRemoteJson, fetchTokenList, fetchTokenListFile, fetchTokenLists, findAaveV4PositionManager, fluidChains, fluidResolvers, fluidVaultEntries, fluidVaults, frankencoinChainData, frankencoinConfig, frankencoinConfigFor, frankencoinLendersByChain, frankencoinMarketByPosition, frankencoinMarkets, fraxlendConfig, fraxlendConfigFor, fraxlendLendersByChain, fraxlendPairKey, fraxlendPairsFor, gearboxAccountCompressor, gearboxAddressProviderV310, gearboxBotListV3, gearboxChains, gearboxMarketCompressor, gearboxMarketConfigurators, gearboxResolvers, gearboxV3LenderKey, getAaveV4GatewayAddresses, getAaveV4PositionManagers, getAaveV4SpokeAccess, getAaveV4SpokeEntry, getAaveV4SpokePeripherals, getChainEntries, getSiloV2MarketEntry, getSiloV3MarketEntry, initConfig, initializeChainData, initializeLenderData, inverseChainData, inverseConfig, inverseConfigFor, inverseLendersByChain, inverseMarketByAddress, inverseMarkets, isAaveV4OperationRestricted, isListaSmartLpAsset, liquityBranchByIndex, liquityBranchByTroveManager, liquityBranchesByChain, liquityConfig, liquityConfigFor, liquityLendersByChain, liquityMarkets, listaCollateralProvider, listaCollateralProviders, listaNativeProvider, listaSmartLpByCollateral, llamaLendApiBaseUrl, llamaLendChainData, llamaLendConfig, llamaLendConfigFor, llamaLendLenderKey, llamaLendLendersByChain, llamaLendLeverageZap, llamaLendMarketByController, llamaLendMarketByVault, llamaLendMarkets, llamaLendSupportsDelegation, llamaLendSupportsLeverage, loadCached, loadCachedJson, midnightApiBaseOverride, midnightConfig, midnightMarketById, midnightMarkets, midnightMarketsByChain, morphoBundler3, morphoOracles, morphoPools, morphoTypeMarkets, morphoTypeOracles, morphoTypeVaults, parseAaveV4SpokeLenderKey, parseFraxlendPairKey, parseGearboxV3LenderKey, parseLlamaLendLenderKey, parseSiloV2LenderKey, parseSiloV3LenderKey, parseTermMaxLenderKey, resolveMidnightApiBase, resolveTermApiBase, resupplyConfig, resupplyConfigFor, resupplyLendersByChain, riverChainData, riverConfig, riverConfigFor, riverLendersByChain, riverMarketByIndex, riverMarkets, setMidnightApiBase, setRemoteCacheGithubToken, setRemoteCacheStore, setTermApiBase, siloMarkets, siloMarketsV3, siloPeripherals, siloPeripheralsV3, siloV2LenderKey, siloV3LenderKey, skyChainData, skyConfig, skyConfigFor, skyLendersByChain, skyMarkets, tellerConfig, tellerConfigByChain, tellerPoolByAddress, tellerPools, tellerPoolsByChain, termApiBaseOverride, termConfig, termMarketById, termMarkets, termMarketsByChain, termMaxApiBaseUrl, termMaxChainIds, termMaxConfig, termMaxConfigByChain, termMaxLenderKey, twyneBaseKey, twyneBeaconFor, twyneChainData, twyneConfig, twyneConfigFor, twyneLendersByChain, twyneMarketByKey, twyneMarketFor, twyneMarketKey, twyneMarkets, twyneMarketsForIntermediateVault, twyneOperator, usddChainData, usddConfig, usddConfigFor, usddLendersByChain, usddMarketByIlk, usddMarkets };
@@ -37,4 +37,5 @@ export * from './dss';
37
37
  export * from './llamalend';
38
38
  export * from './resupply';
39
39
  export * from './curvance';
40
+ export * from './twyne';
40
41
  export * from './fraxlend';
@@ -53,6 +53,13 @@ export type MorphoTypeVaultEntry = {
53
53
  underlying: string;
54
54
  /** Curated display name (e.g. `Lista USD1 Vault`). Optional. */
55
55
  name?: string;
56
+ /** Human curator/brand name (e.g. `Steakhouse Financial`). Filled by
57
+ * lender-metadata's `update:vault-curators` job (Morpho curator roster
58
+ * joined on the on-chain `curator()`/`owner()` address, with a
59
+ * conservative name-derived fallback) — the chains in this registry have
60
+ * no Morpho-API coverage, so the on-chain fetcher cannot learn the
61
+ * curator any other way. */
62
+ curatorName?: string;
56
63
  /** Vault interface version. `v1` = MetaMorpho (withdraw-queue → markets);
57
64
  * `v2` = Vaults V2 (adapter-based). Drives the on-chain fetcher's
58
65
  * allocation walk. Absent ⇒ the fetcher auto-detects on-chain
@@ -24,6 +24,7 @@ import type { GeneralReservesMap, OracleMap } from './common';
24
24
  import type { CompoundV2OraclesConfigType, CompoundV2PoolsType, CompoundV2TokenArrayType, CompoundV2TokensType } from './compoundV2';
25
25
  import type { CompoundV3BaseDataType, CompoundV3BulkerType, CompoundV3OracleDataMap, CompoundV3PoolsType } from './compoundV3';
26
26
  import type { CurvanceConfigType } from './curvance';
27
+ import type { TwyneConfigType, TwyneMarketsType } from './twyne';
27
28
  import type { DolomiteConfigsType, DolomiteEmodeType } from './dolomite';
28
29
  import type { UsddConfigType, UsddMarketsType } from './dss';
29
30
  import type { EulerConfigsType, EulerVaultsType } from './euler';
@@ -105,6 +106,8 @@ export interface GlobalLenderDataRegistry {
105
106
  llamaLendMarkets: LlamaLendMarketsType;
106
107
  resupplyConfig: ResupplyConfigType;
107
108
  curvanceConfig: CurvanceConfigType;
109
+ twyneConfig: TwyneConfigType;
110
+ twyneMarkets: TwyneMarketsType;
108
111
  fraxlendConfig: FraxlendConfigType;
109
112
  eulerConfigs: EulerConfigsType;
110
113
  eulerVaults: EulerVaultsType;
@@ -0,0 +1,210 @@
1
+ /** The two external protocols Twyne integrates. Mirrors the on-chain enum. */
2
+ export type TwyneVaultType = 'EULER_V2' | 'AAVE_V3';
3
+ /**
4
+ * The 1-click operators for one `VaultType`. Each is EVC-authenticated
5
+ * (`_msgSender() == collateralVault.borrower()`) and runs a Morpho Blue flash
6
+ * loan plus, where it swaps, Euler's `Swapper` — whose GENERIC handler executes
7
+ * arbitrary calldata on an arbitrary target, so any aggregator we support works
8
+ * without an allowlist.
9
+ */
10
+ export type TwyneOperators = {
11
+ /** `executeLeverage(collateralVault, underlyingAmt, collateralAmt, flashAmt, minOut, deadline, swapData)` */
12
+ leverage?: string;
13
+ /** `executeDeleverage(collateralVault, flashAmt, maxDebt, withdrawAmt, swapData)` */
14
+ deleverage?: string;
15
+ /**
16
+ * `executeTeleport(collateralVault, aTokenAmount, debtAmount)` — migrate an
17
+ * existing external position IN.
18
+ *
19
+ * AAVE_V3 ONLY, and it carries NO swapper (its constructor takes
20
+ * `evc, morpho, factory, permit2, aavePool` and nothing else), so it handles
21
+ * the IDENTITY CASE ONLY: the user's aToken must be this market's aToken and
22
+ * their VARIABLE debt asset must be this market's `targetAsset`. Anything
23
+ * cross-asset has to fall back to the generic migrate. There is no
24
+ * teleport-OUT.
25
+ */
26
+ teleport?: string;
27
+ };
28
+ /**
29
+ * The BeaconProxy beacon for one target vault, and OPTIONALLY a cached
30
+ * init-code hash for the CREATE2 address predictor.
31
+ *
32
+ * `CollateralVaultFactory.createCollateralVault` deploys
33
+ * `new BeaconProxy{salt: keccak256(abi.encodePacked(borrower, nonce))}(beacon, "")`,
34
+ * so a position's address IS predictable — but the init-code hash is a property
35
+ * of the FACTORY IMPLEMENTATION, not of the protocol. That factory is a UUPS
36
+ * proxy which has already been upgraded four times, and the embedded BeaconProxy
37
+ * creation code is not identical across those implementations.
38
+ *
39
+ * So `evc.batchSimulation` is the source of truth for a new vault's address, and
40
+ * a cached hash here is a FAST PATH ONLY. It is valid exactly while
41
+ * `factoryImplementation` still matches the live ERC-1967 implementation slot
42
+ * (`0x360894…382bbc`) — one `eth_getStorageAt` to check. On a mismatch, fall
43
+ * back; never guess, because a stale hash yields a plausible EMPTY address and
44
+ * the leverage batch would then `skim`/`borrow` on nothing.
45
+ *
46
+ * See TWYNE_BUILD_PLAN.md D3.
47
+ */
48
+ export type TwyneBeacon = {
49
+ beacon: string;
50
+ /** `keccak256(BeaconProxy.creationCode ++ abi.encode(beacon, "0x"))`. */
51
+ initCodeHash?: string;
52
+ /** The factory implementation `initCodeHash` was derived from. A cached hash
53
+ * is only usable while this still matches the live implementation slot. */
54
+ factoryImplementation?: string;
55
+ };
56
+ /** Per-chain, protocol-level (evergreen) Twyne addresses. */
57
+ export type TwyneConfigChain = {
58
+ /**
59
+ * Twyne's OWN EVC — `0xef39D649…` on Ethereum, NOT Euler's canonical
60
+ * `0x0C9a3dd6…`. Every collateral-vault write is authenticated through it
61
+ * (`EVCUtil._msgSender()`), which is also what lets an EVC account operator
62
+ * drive a position. Reusing the Euler address here is a silent failure.
63
+ */
64
+ evc: string;
65
+ /** `CollateralVaultFactory` — `createCollateralVault`, `getCollateralVaults`,
66
+ * `isCollateralVault`, `nonce`, `collateralVaultBeacon`, `paused`. */
67
+ collateralVaultFactory: string;
68
+ /** `VaultManager` — the whitelists and the LTV bounds
69
+ * (`maxTwyneLTVs`, `externalLiqBuffers`, `isAllowedTargetAssets`). */
70
+ vaultManager: string;
71
+ /** Euler-style oracle router used to price collateral vaults. */
72
+ oracleRouter?: string;
73
+ /** Morpho Blue — the (free) flash source every operator uses. */
74
+ morpho?: string;
75
+ /** Euler periphery `Swapper` (GENERIC handler = no target allowlist). */
76
+ swapper?: string;
77
+ /** Euler periphery `SwapVerifier` — used by the Euler leverage operator. */
78
+ swapVerifier?: string;
79
+ /** Permit2, as the operators pull user funds through `SafeERC20Lib`. */
80
+ permit2?: string;
81
+ /** 1-click operators per external protocol. */
82
+ operators?: Partial<Record<TwyneVaultType, TwyneOperators>>;
83
+ /**
84
+ * Collateral-vault beacons keyed by TARGET VAULT (the factory keys its
85
+ * beacon map that way), for the CREATE2 address predictor.
86
+ */
87
+ beacons?: {
88
+ [targetVault: string]: TwyneBeacon;
89
+ };
90
+ };
91
+ export type TwyneConfigType = {
92
+ [lender: string]: {
93
+ [chainId: string]: TwyneConfigChain;
94
+ };
95
+ };
96
+ /**
97
+ * One whitelisted Twyne market.
98
+ *
99
+ * Numeric risk fields are strings/numbers in the protocol's own scale (1e4 for
100
+ * LTVs and the buffer) because they are sourced from JSON metadata; live values
101
+ * are re-read on every refresh, since the external liquidation threshold moves
102
+ * — Aave's PT eMode thresholds ramp down as a PT ages, and Twyne's LOWER bound
103
+ * is derived from it.
104
+ */
105
+ export type TwyneMarketConfig = {
106
+ /** `TWYNE_<chainId>_<INTERMEDIATE_VAULT>_<TARGET_ASSET>`, upper-cased hex. */
107
+ key: string;
108
+ vaultType: TwyneVaultType;
109
+ /** The EVK credit vault. Also the market's identity for LTV bounds. */
110
+ intermediateVault: string;
111
+ /** Euler: the debt eVault. Aave: the Pool. */
112
+ targetVault: string;
113
+ /** The borrowed asset (e.g. USDe, WETH). */
114
+ targetAsset: string;
115
+ /** The intermediate vault's asset — an `eToken` or a Twyne aToken wrapper.
116
+ * This is what the collateral vault actually holds. */
117
+ collateralAsset: string;
118
+ /** What the user thinks they deposited (WETH / wstETH / a Pendle PT).
119
+ * `depositUnderlying` / `redeemUnderlying` take this. */
120
+ underlyingAsset: string;
121
+ /** Aave only: the aToken the wrapper wraps. */
122
+ aToken?: string;
123
+ /** Aave only: the eMode category the collateral vault is initialized with.
124
+ * The external liquidation threshold must be read from THIS category when
125
+ * the reserve is in its collateral bitmap — never the plain reserve LT. */
126
+ categoryId?: number;
127
+ /** Governance ceiling on a position's chosen liq LTV, 1e4. */
128
+ maxTwyneLiqLTV?: number;
129
+ /** Safety margin below the external threshold, 1e4 — the LOWER bound is
130
+ * `extLiqLTV * externalLiqBuffer / 1e4`. */
131
+ externalLiqBuffer?: number;
132
+ /** Maturity of the collateral, unix seconds, when the collateral is a
133
+ * fixed-term asset (every live PT market). Absent for wstETH/WETH. */
134
+ collateralMaturity?: number;
135
+ /** The credit vault's `IRMTwyneCurve` — the join key into the `irm` repo's
136
+ * `twyne.json`, where the fitted `gamma` lives. */
137
+ creditIrm?: string;
138
+ /** The collateral vault BeaconProxy beacon for this market's target vault.
139
+ * Recorded for the CREATE2 predictor's fast path; the init-code hash is
140
+ * deliberately NOT pinned (see TWYNE_BUILD_PLAN.md D3). */
141
+ beacon?: string;
142
+ /** Display only. */
143
+ symbol?: string;
144
+ name?: string;
145
+ };
146
+ export type TwyneChainData = {
147
+ markets: TwyneMarketConfig[];
148
+ };
149
+ export type TwyneMarketsType = {
150
+ [lender: string]: {
151
+ [chainId: string]: TwyneChainData;
152
+ };
153
+ };
154
+ export declare const twyneConfig: () => TwyneConfigType;
155
+ /** Deployment seed for one Twyne lender on a chain (undefined if unloaded). */
156
+ export declare const twyneConfigFor: (lender: string, chainId: string | number) => TwyneConfigChain | undefined;
157
+ export declare const twyneMarkets: () => TwyneMarketsType;
158
+ /** Generated chain data (curated market roster; undefined if unloaded). */
159
+ export declare const twyneChainData: (lender: string, chainId: string | number) => TwyneChainData | undefined;
160
+ /**
161
+ * The bare lender key a per-market key belongs to. Per-market keys are
162
+ * `TWYNE_<chainId>_<iv>_<targetAsset>`, so the base is simply the first
163
+ * segment — kept as a function because callers pass both forms
164
+ * interchangeably.
165
+ */
166
+ export declare const twyneBaseKey: (lender: string) => string;
167
+ /**
168
+ * Build the per-market lender key for a triple.
169
+ *
170
+ * The TARGET VAULT is deliberately NOT in the key: it is redundant on every
171
+ * live market (implied by the asset on Euler, always the Pool on Aave), and
172
+ * every other fan-out lender in this registry uses a one-or-two-identifier key.
173
+ * `assertTwyneKeysUnique` guards the day that assumption breaks.
174
+ */
175
+ export declare const twyneMarketKey: (chainId: string | number, intermediateVault: string, targetAsset: string) => string;
176
+ /**
177
+ * Throw if two distinct `(intermediateVault, targetVault, targetAsset)` triples
178
+ * collapse onto one key.
179
+ *
180
+ * This cannot happen with the eight live markets, but it is exactly the failure
181
+ * that would silently MERGE two markets — the same lender key resolving to two
182
+ * different debt venues — so the roster is validated at load rather than
183
+ * trusted. Called by the generator and by the margin-fetcher on ingest.
184
+ */
185
+ export declare const assertTwyneKeysUnique: (markets: TwyneMarketConfig[], chainId: string | number) => void;
186
+ /** Find one Twyne market by its per-market lender key. */
187
+ export declare const twyneMarketByKey: (lender: string, chainId: string | number) => TwyneMarketConfig | undefined;
188
+ /** Find one Twyne market by its (intermediate vault, target asset) pair. */
189
+ export declare const twyneMarketFor: (lender: string, chainId: string | number, intermediateVault: string, targetAsset: string) => TwyneMarketConfig | undefined;
190
+ /** Every market that reserves credit from one intermediate (credit) vault. */
191
+ export declare const twyneMarketsForIntermediateVault: (lender: string, chainId: string | number, intermediateVault: string) => TwyneMarketConfig[];
192
+ /**
193
+ * All Twyne lender keys with config on a chain (drives getLendersForChain).
194
+ * Gated on the collateral vault FACTORY — the one address every flow needs, and
195
+ * the bootstrap for position discovery.
196
+ */
197
+ export declare const twyneLendersByChain: (chainId: string | number) => string[];
198
+ /**
199
+ * The operator to drive for a market's `VaultType`, or `undefined` when Twyne
200
+ * has not deployed one — a real state, not a gap: there is no Euler-side
201
+ * teleport at all, and the docs' address table omits deployed operators, so
202
+ * absence here must be reported rather than defaulted.
203
+ */
204
+ export declare const twyneOperator: (lender: string, chainId: string | number, vaultType: TwyneVaultType, kind: keyof TwyneOperators) => string | undefined;
205
+ /**
206
+ * Beacon + init-code hash for a target vault, for the CREATE2 predictor.
207
+ * Lookup is case-insensitive because target-vault addresses arrive from config
208
+ * and from chain in mixed checksum forms.
209
+ */
210
+ export declare const twyneBeaconFor: (lender: string, chainId: string | number, targetVault: string) => TwyneBeacon | undefined;
package/package.json CHANGED
@@ -4,7 +4,7 @@
4
4
  "publishConfig": {
5
5
  "access": "public"
6
6
  },
7
- "version": "0.0.47",
7
+ "version": "0.0.48",
8
8
  "description": "Hold and initialize lending protocol data across a stack",
9
9
  "files": [
10
10
  "dist"