@wireio/stake 0.1.0 → 0.1.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 (104) hide show
  1. package/README.md +57 -0
  2. package/lib/stake.browser.js +11836 -4103
  3. package/lib/stake.browser.js.map +1 -1
  4. package/lib/stake.d.ts +374 -556
  5. package/lib/stake.js +12089 -4303
  6. package/lib/stake.js.map +1 -1
  7. package/lib/stake.m.js +11836 -4103
  8. package/lib/stake.m.js.map +1 -1
  9. package/package.json +1 -1
  10. package/src/assets/ethereum/ABI/liqEth/DepositManager.sol/DepositManager.dbg.json +4 -0
  11. package/src/assets/ethereum/ABI/liqEth/DepositManager.sol/DepositManager.json +1153 -0
  12. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/IAccounting.dbg.json +4 -0
  13. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/IAccounting.json +172 -0
  14. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/IDepositContract.dbg.json +4 -0
  15. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/IDepositContract.json +39 -0
  16. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/IDepositManager.dbg.json +4 -0
  17. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/IDepositManager.json +64 -0
  18. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/ILiqEthBurn.dbg.json +4 -0
  19. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/ILiqEthBurn.json +24 -0
  20. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/ILiqEthMint.dbg.json +4 -0
  21. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/ILiqEthMint.json +35 -0
  22. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/IRewardsERC20.dbg.json +4 -0
  23. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/IRewardsERC20.json +213 -0
  24. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/IStakingModule.dbg.json +4 -0
  25. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/IStakingModule.json +138 -0
  26. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/IValidatorBalanceVerifier.dbg.json +4 -0
  27. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/IValidatorBalanceVerifier.json +70 -0
  28. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/IWithdrawalRecord.dbg.json +4 -0
  29. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/IWithdrawalRecord.json +64 -0
  30. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/LiqEthCommon.dbg.json +4 -0
  31. package/src/assets/ethereum/ABI/liqEth/LiqEthCommon.sol/LiqEthCommon.json +10 -0
  32. package/src/assets/ethereum/ABI/liqEth/RewardsERC20.sol/RewardsERC20.dbg.json +4 -0
  33. package/src/assets/ethereum/ABI/liqEth/RewardsERC20.sol/RewardsERC20.json +749 -0
  34. package/src/assets/ethereum/ABI/liqEth/RewardsERC20Pausable.sol/RewardsERC20Pausable.dbg.json +4 -0
  35. package/src/assets/ethereum/ABI/liqEth/RewardsERC20Pausable.sol/RewardsERC20Pausable.json +812 -0
  36. package/src/assets/ethereum/ABI/liqEth/ValidatorBalanceVerifier.sol/BeaconRoots.dbg.json +4 -0
  37. package/src/assets/ethereum/ABI/liqEth/ValidatorBalanceVerifier.sol/BeaconRoots.json +10 -0
  38. package/src/assets/ethereum/ABI/liqEth/ValidatorBalanceVerifier.sol/SSZ.dbg.json +4 -0
  39. package/src/assets/ethereum/ABI/liqEth/ValidatorBalanceVerifier.sol/SSZ.json +10 -0
  40. package/src/assets/ethereum/ABI/liqEth/ValidatorBalanceVerifier.sol/ValidatorBalanceVerifier.dbg.json +4 -0
  41. package/src/assets/ethereum/ABI/liqEth/ValidatorBalanceVerifier.sol/ValidatorBalanceVerifier.json +225 -0
  42. package/src/assets/ethereum/ABI/liqEth/Yield.sol/BeaconRoots.dbg.json +4 -0
  43. package/src/assets/ethereum/ABI/liqEth/Yield.sol/BeaconRoots.json +10 -0
  44. package/src/assets/ethereum/ABI/liqEth/Yield.sol/SSZ.dbg.json +4 -0
  45. package/src/assets/ethereum/ABI/liqEth/Yield.sol/SSZ.json +10 -0
  46. package/src/assets/ethereum/ABI/liqEth/Yield.sol/YieldOracle.dbg.json +4 -0
  47. package/src/assets/ethereum/ABI/liqEth/Yield.sol/YieldOracle.json +813 -0
  48. package/src/assets/ethereum/ABI/liqEth/accounting.sol/Accounting.dbg.json +4 -0
  49. package/src/assets/ethereum/ABI/liqEth/accounting.sol/Accounting.json +651 -0
  50. package/src/assets/ethereum/ABI/liqEth/liqEth.sol/LiqEthToken.dbg.json +4 -0
  51. package/src/assets/ethereum/ABI/liqEth/liqEth.sol/LiqEthToken.json +1110 -0
  52. package/src/assets/ethereum/ABI/liqEth/liqEthBurn.sol/LiqEthBurn.dbg.json +4 -0
  53. package/src/assets/ethereum/ABI/liqEth/liqEthBurn.sol/LiqEthBurn.json +391 -0
  54. package/src/assets/ethereum/ABI/liqEth/liqEthMint.sol/LiqEthMint.dbg.json +4 -0
  55. package/src/assets/ethereum/ABI/liqEth/liqEthMint.sol/LiqEthMint.json +402 -0
  56. package/src/assets/ethereum/ABI/liqEth/stakingModule.sol/StakingModule.dbg.json +4 -0
  57. package/src/assets/ethereum/ABI/liqEth/stakingModule.sol/StakingModule.json +1225 -0
  58. package/src/assets/ethereum/ABI/liqEth/withdrawalQueue.sol/WithdrawalQueue.dbg.json +4 -0
  59. package/src/assets/ethereum/ABI/liqEth/withdrawalQueue.sol/WithdrawalQueue.json +927 -0
  60. package/src/assets/ethereum/ABI/liqEth/withdrawalVault.sol/Uint64BE.dbg.json +4 -0
  61. package/src/assets/ethereum/ABI/liqEth/withdrawalVault.sol/Uint64BE.json +10 -0
  62. package/src/assets/ethereum/ABI/liqEth/withdrawalVault.sol/WithdrawalVault.dbg.json +4 -0
  63. package/src/assets/ethereum/ABI/liqEth/withdrawalVault.sol/WithdrawalVault.json +447 -0
  64. package/src/assets/solana/idl/liqsol_core.json +4239 -0
  65. package/src/assets/solana/idl/liqsol_token.json +183 -0
  66. package/src/assets/solana/idl/validator_leaderboard.json +270 -265
  67. package/src/assets/solana/types/liqsol_core.ts +4245 -0
  68. package/src/assets/solana/types/liqsol_token.ts +189 -0
  69. package/src/assets/solana/types/validator_leaderboard.ts +270 -265
  70. package/src/index.ts +1 -3
  71. package/src/networks/ethereum/contract.ts +101 -36
  72. package/src/networks/ethereum/ethereum.ts +141 -45
  73. package/src/networks/ethereum/types.ts +30 -2
  74. package/src/networks/solana/clients/deposit.client.ts +71 -109
  75. package/src/networks/solana/clients/distribution.client.ts +256 -383
  76. package/src/networks/solana/clients/leaderboard.client.ts +38 -133
  77. package/src/networks/solana/constants.ts +214 -130
  78. package/src/networks/solana/program.ts +25 -38
  79. package/src/networks/solana/solana.ts +120 -105
  80. package/src/networks/solana/types.ts +37 -47
  81. package/src/networks/solana/utils.ts +551 -0
  82. package/src/scripts/tsconfig.json +17 -0
  83. package/src/staker/staker.ts +10 -6
  84. package/src/staker/types.ts +14 -9
  85. package/src/assets/solana/idl/deposit.json +0 -296
  86. package/src/assets/solana/idl/distribution.json +0 -768
  87. package/src/assets/solana/idl/liq_sol_token.json +0 -298
  88. package/src/assets/solana/idl/mint_helper.json +0 -110
  89. package/src/assets/solana/idl/read_tracked_balance.json +0 -140
  90. package/src/assets/solana/idl/stake_controller.json +0 -2149
  91. package/src/assets/solana/idl/treasury.json +0 -110
  92. package/src/assets/solana/idl/validator_registry.json +0 -487
  93. package/src/assets/solana/idl/yield_oracle.json +0 -32
  94. package/src/assets/solana/types/deposit.ts +0 -302
  95. package/src/assets/solana/types/distribution.ts +0 -774
  96. package/src/assets/solana/types/liq_sol_token.ts +0 -304
  97. package/src/assets/solana/types/mint_helper.ts +0 -116
  98. package/src/assets/solana/types/read_tracked_balance.ts +0 -146
  99. package/src/assets/solana/types/stake_controller.ts +0 -2155
  100. package/src/assets/solana/types/stake_registry.ts +0 -441
  101. package/src/assets/solana/types/treasury.ts +0 -116
  102. package/src/assets/solana/types/validator_registry.ts +0 -493
  103. package/src/assets/solana/types/yield_oracle.ts +0 -38
  104. package/src/common/utils.ts +0 -9
@@ -1,30 +1,25 @@
1
1
  /**
2
2
  * @module EthereumContractService
3
- *
3
+ *
4
4
  * Provides a unified service for interacting with Ethereum smart contracts using ethers.js.
5
- *
6
- * This module includes:
7
- * - ABI imports for ERC20, ERC721, and ERC1155 token standards.
8
- * - Address book and contract configuration types.
9
- * - A service class for managing contract instances, interfaces, and utility methods for read/write access.
10
- * - Utility for decoding custom errors and events using a combined interface of all known ABIs.
11
- *
12
- * @remarks
13
- * - Update the `ADDRESSES` and `CONTRACTS` objects to match your deployment.
14
- * - The service supports both read-only and write-enabled contract handles, depending on the presence of a signer.
15
- * - The `omniInterface` property allows decoding of errors and events across all included ABIs.
16
- *
17
- * @example
18
- * ```typescript
19
- * const service = new EthereumContractService({ provider, signer });
20
- * const stakeContract = service.getContract('Stake');
21
- * const address = service.getAddress('Stake');
22
- * ```
23
5
  */
6
+ import AccountingArtifact from '../../assets/ethereum/ABI/liqEth/accounting.sol/Accounting.json';
7
+ import DepositManagerArtifact from '../../assets/ethereum/ABI/liqEth/DepositManager.sol/DepositManager.json';
8
+ import LiqEthArtifact from '../../assets/ethereum/ABI/liqEth/liqEth.sol/LiqEthToken.json';
9
+ import LiqEthBurnArtifact from '../../assets/ethereum/ABI/liqEth/liqEthBurn.sol/LiqEthBurn.json';
10
+ // import LiqEthCommonArtifact from '../../assets/ethereum/ABI/liqEth/liqEthCommon.sol/liqEthCommon.json';
11
+ import LiqEthMintArtifact from '../../assets/ethereum/ABI/liqEth/liqEthMint.sol/LiqEthMint.json';
12
+ // import RewardsERC20Artifact from '../../assets/ethereum/ABI/liqEth/RewardsERC20.sol/RewardsERC20.json';
13
+ import StakingModuleArtifact from '../../assets/ethereum/ABI/liqEth/stakingModule.sol/StakingModule.json';
14
+ // import ValidatorBalanceArtifact from '../../assets/ethereum/ABI/liqEth/ValidatorBalanceVerifier.sol/ValidatorBalanceVerifier.json';
15
+ import WithdrawalQueueArtifact from '../../assets/ethereum/ABI/liqEth/withdrawalQueue.sol/WithdrawalQueue.json';
16
+ import WithdrawalVaultArtifact from '../../assets/ethereum/ABI/liqEth/withdrawalVault.sol/WithdrawalVault.json';
17
+ // import YieldArtifact from '../../assets/ethereum/ABI/liqEth/Yield.sol/YieldOracle.json';
24
18
 
25
19
  import ERC20Artifact from '../../assets/ethereum/ABI/token/ERC20Token.sol/ERC20Token.json';
26
20
  import ERC721Artifact from '../../assets/ethereum/ABI/token/ERC721Token.sol/ERC721Token.json';
27
21
  import ERC1155Artifact from '../../assets/ethereum/ABI/token/ERC1155Token.sol/ERC1155Token.json';
22
+
28
23
  import { AddressBook, ContractName } from './types';
29
24
  import { Contract, ethers, providers, Signer } from 'ethers';
30
25
  import { JsonFragment } from '@ethersproject/abi';
@@ -34,9 +29,20 @@ export const ERC20Abi = ERC20Artifact.abi;
34
29
  export const ERC721Abi = ERC721Artifact.abi;
35
30
  export const ERC1155Abi = ERC1155Artifact.abi;
36
31
 
37
- // Update this to be your staking contract address book
32
+ // -----------------------------------------------------------------------------
33
+ // Address book
34
+ // -----------------------------------------------------------------------------
35
+
36
+ // Make sure ContractName in ./types includes all of these keys.
38
37
  export const ADDRESSES: AddressBook = {
39
- Stake: '0xEeaCBa95852324eAc63fE2711aFe0283adf3bC93',
38
+ Accounting: "0xd51CC479c25dc7Cd23f568Ef5c1AdE1671a4D15b",
39
+ DepositManager: "0x2249D309f086363ABF5057Ae7f8057279162786B",
40
+ LiqEth: "0xd5bd3DC2fD86e917A46f7571708aBB88CbfCc197",
41
+ LiqEthMint: "0xdBAa1539eB7b80C29d825FCda76c0d7F8F0E6cFB",
42
+ LiqEthBurn: "0x02e0A02fE2311FAd661677B7117FDdc801c1216b",
43
+ StakingModule: "0x87047291c3b0D55A551C97B9194A02E1D84e06A9",
44
+ WithdrawalQueue: "0x7781368720294fE0bB6D97F14fE2E9275fFED071",
45
+ WithdrawalVault: "0x24457626938d4132556005ecA4d9e6F24F85297E",
40
46
  };
41
47
 
42
48
  export type Contracts<T extends string = ContractName> = Record<T, ContractConfig>;
@@ -44,12 +50,58 @@ export type Contracts<T extends string = ContractName> = Record<T, ContractConfi
44
50
  export type ContractConfig = {
45
51
  address: string;
46
52
  abi: JsonFragment[];
47
- }
53
+ };
54
+
55
+ // -----------------------------------------------------------------------------
56
+ // Contract config
57
+ // -----------------------------------------------------------------------------
48
58
 
49
59
  export const CONTRACTS: Contracts<ContractName> = {
50
- Stake: { address: ADDRESSES.Stake, abi: undefined as any }, // Replace with actual ABI artifact when available
51
- // Stake: { address: ADDRESSES.Stake, abi: Stake.abi },
52
- }
60
+ Accounting: {
61
+ address: ADDRESSES.Accounting,
62
+ abi: AccountingArtifact.abi as JsonFragment[],
63
+ },
64
+ LiqEth: {
65
+ address: ADDRESSES.LiqEth,
66
+ abi: LiqEthArtifact.abi as JsonFragment[],
67
+ },
68
+ DepositManager: {
69
+ address: ADDRESSES.DepositManager,
70
+ abi: DepositManagerArtifact.abi as JsonFragment[],
71
+ },
72
+ LiqEthMint: {
73
+ address: ADDRESSES.LiqEthMint,
74
+ abi: LiqEthMintArtifact.abi as JsonFragment[],
75
+ },
76
+ LiqEthBurn: {
77
+ address: ADDRESSES.LiqEthBurn,
78
+ abi: LiqEthBurnArtifact.abi as JsonFragment[],
79
+ },
80
+ // RewardsERC20: {
81
+ // address: ADDRESSES.RewardsERC20,
82
+ // abi: RewardsERC20Artifact.abi as JsonFragment[],
83
+ // },
84
+ StakingModule: {
85
+ address: ADDRESSES.StakingModule,
86
+ abi: StakingModuleArtifact.abi as JsonFragment[],
87
+ },
88
+ // ValidatorBalance: {
89
+ // address: ADDRESSES.ValidatorBalance,
90
+ // abi: ValidatorBalanceArtifact.abi as JsonFragment[],
91
+ // },
92
+ WithdrawalQueue: {
93
+ address: ADDRESSES.WithdrawalQueue,
94
+ abi: WithdrawalQueueArtifact.abi as JsonFragment[],
95
+ },
96
+ WithdrawalVault: {
97
+ address: ADDRESSES.WithdrawalVault,
98
+ abi: WithdrawalVaultArtifact.abi as JsonFragment[],
99
+ },
100
+ // Yield: {
101
+ // address: ADDRESSES.Yield,
102
+ // abi: YieldArtifact.abi as JsonFragment[],
103
+ // },
104
+ };
53
105
 
54
106
  export interface ContractOptions {
55
107
  /** RPC endpoint or injected EIP-1193 provider */
@@ -58,7 +110,6 @@ export interface ContractOptions {
58
110
  signer?: Signer;
59
111
  }
60
112
 
61
-
62
113
  export class EthereumContractService {
63
114
  private provider?: providers.Provider;
64
115
  private signer?: Signer;
@@ -73,7 +124,11 @@ export class EthereumContractService {
73
124
  (Object.keys(CONTRACTS) as ContractName[]).forEach((name) => {
74
125
  const { address, abi } = CONTRACTS[name];
75
126
  this.iface[name] = new ethers.utils.Interface(abi);
76
- this.contract[name] = new ethers.Contract(address, abi, this.signer ?? this.provider);
127
+ this.contract[name] = new ethers.Contract(
128
+ address,
129
+ abi,
130
+ this.signer ?? this.provider
131
+ );
77
132
  });
78
133
  }
79
134
 
@@ -83,13 +138,13 @@ export class EthereumContractService {
83
138
  }
84
139
 
85
140
  /** Utility: get a read-only handle even if signer is present */
86
- getReadOnly(name: ContractName): Contract {
141
+ public getReadOnly(name: ContractName): Contract {
87
142
  const { address, abi } = CONTRACTS[name];
88
143
  return new Contract(address, abi, this.provider);
89
144
  }
90
145
 
91
146
  /** Utility: get a write-enabled handle (throws if no signer) */
92
- getWrite(name: ContractName): Contract {
147
+ public getWrite(name: ContractName): Contract {
93
148
  if (!this.signer) throw new Error('No signer available for write calls');
94
149
  const { address, abi } = CONTRACTS[name];
95
150
  return new Contract(address, abi, this.signer);
@@ -119,27 +174,35 @@ export class EthereumContractService {
119
174
  return ctr;
120
175
  }
121
176
 
122
- /** A unified Interface containing all ABIs (addresses + extra decoding-only)
123
- * to parse custom errors or events. */
177
+ /** A unified Interface containing all ABIs to parse custom errors or events. */
124
178
  public get omniInterface(): ethers.utils.Interface {
125
179
  const all: any[] = [];
126
180
 
127
- // Add all artifacts to the interface
128
181
  const allArtifacts = [
129
182
  ERC20Artifact,
130
183
  ERC721Artifact,
131
184
  ERC1155Artifact,
132
- // Add more artifacts as needed
185
+
186
+ // liqETH suite
187
+ AccountingArtifact,
188
+ DepositManagerArtifact,
189
+ LiqEthArtifact,
190
+ LiqEthBurnArtifact,
191
+ LiqEthMintArtifact,
192
+ // RewardsERC20Artifact,
193
+ StakingModuleArtifact,
194
+ // ValidatorBalanceArtifact,
195
+ WithdrawalQueueArtifact,
196
+ WithdrawalVaultArtifact,
197
+ // YieldArtifact,
133
198
  ];
134
199
 
135
- // Add all ABIs to the omnibus interface
136
200
  allArtifacts.forEach(artifact => {
137
201
  if (artifact && artifact.abi) {
138
202
  all.push(...artifact.abi);
139
203
  }
140
204
  });
141
205
 
142
- // dedupe
143
206
  const seen = new Set<string>();
144
207
  const dedup: any[] = [];
145
208
  for (const item of all) {
@@ -150,7 +213,9 @@ export class EthereumContractService {
150
213
  seen.add(key);
151
214
  dedup.push(item);
152
215
  }
153
- } catch { }
216
+ } catch {
217
+ // ignore bad fragments
218
+ }
154
219
  }
155
220
 
156
221
  return new ethers.utils.Interface(dedup);
@@ -1,64 +1,160 @@
1
1
  // src/networks/ethereum/ethereum.ts
2
2
 
3
- import { ethers } from 'ethers';
4
- import { IStakingClient, StakerConfig } from '../../staker/types';
3
+ import { BigNumber, BigNumberish, ethers } from 'ethers';
4
+ import { IStakingClient, Portfolio, StakerConfig } from '../../staker/types';
5
5
  import { PublicKey as WirePubKey } from '@wireio/core';
6
- import { ERC20Abi } from './contract'; // TODO replace with staking contract ABI
7
-
8
- // — replace with your actual staking contract ABI & address —
9
- const STAKING_CONTRACT_ADDRESS = '0xYourStakingContractAddress';
6
+ import { ERC20Abi, EthereumContractService } from './contract'; // TODO replace with staking contract ABI
7
+ import { DepositEvent, DepositResult } from './types';
10
8
 
11
9
  // TODO extend to implement ISTAKINGCLIENT
12
- export class EthereumStakingClient {
10
+ export class EthereumStakingClient implements IStakingClient {
13
11
  public readonly pubKey: WirePubKey;
14
12
  private readonly provider: ethers.providers.Web3Provider;
15
13
  private readonly signer: ethers.Signer;
16
- private readonly contract: ethers.Contract;
14
+ private readonly contractService: EthereumContractService;
15
+
16
+ get contract() { return this.contractService.contract; }
17
+ get network() { return this.config.network; }
17
18
 
18
19
  constructor(private config: StakerConfig) {
19
- // 1) unwrap & validate Ethers provider
20
- if (!ethers.providers.Web3Provider.isProvider(config.provider as any)) {
21
- throw new Error('Expected a Web3Provider for Ethereum');
22
- }
23
- this.provider = config.provider as ethers.providers.Web3Provider;
24
-
25
- // 2) signer
26
- this.signer = this.provider.getSigner();
27
- this.pubKey = config.pubKey as WirePubKey;
28
-
29
- // 4) instantiate your contract wrapper
30
- this.contract = new ethers.Contract(
31
- STAKING_CONTRACT_ADDRESS,
32
- ERC20Abi,
33
- this.signer
34
- );
20
+ try {
21
+ this.provider = config.provider as ethers.providers.Web3Provider;
22
+ this.signer = this.provider.getSigner();
23
+ this.pubKey = config.pubKey as WirePubKey;
24
+
25
+ this.contractService = new EthereumContractService({
26
+ provider: this.provider,
27
+ signer: this.signer,
28
+ });
29
+ }
30
+ catch (error) {
31
+ // console.error('Error initializing EthereumStakingClient:', error);
32
+ throw error;
33
+ }
35
34
  }
36
35
 
37
- /** Submit a deposit; returns the transaction hash */
38
- async deposit(amount: number): Promise<string> {
39
- // build & send in one go
40
- const txResponse = await this.contract.deposit(
41
- ethers.BigNumber.from(amount),
42
- {
43
- // if your contract needs ETH value:
44
- // value: ethers.BigNumber.from(amount),
45
- }
46
- );
47
-
48
- // wait for on-chain confirmation (optional)
49
- await txResponse.wait();
50
- return txResponse.hash;
36
+ // ---------------------------------------------------------------------
37
+ // Public IStakingClient.deposit
38
+ // ---------------------------------------------------------------------
39
+
40
+ /**
41
+ * Deposit native ETH into the liqETH protocol via DepositManager.
42
+ * @param amount Amount in wei (or something convertible to BigNumber).
43
+ * Keep this as a bigint / string in the caller; avoid JS floats.
44
+ * @returns transaction hash
45
+ */
46
+ async deposit(amount: number | string | bigint | BigNumber): Promise<string> {
47
+ const amountWei = BigNumber.isBigNumber(amount)
48
+ ? amount
49
+ : BigNumber.from(amount);
50
+
51
+ const result = await this.performDeposit(amountWei);
52
+ // For now, IStakingClient contract is: just return tx hash.
53
+ // If/when you extend the interface, you can surface more here.
54
+ return result.txHash;
51
55
  }
56
+ /**
57
+ * Simulate a deposit via callStatic.
58
+ *
59
+ * Useful for pre-flight checks; will throw with the same revert
60
+ * reason as a real tx if it would fail.
61
+ */
62
+ async simulateDeposit(amount: number | string | bigint | BigNumber): Promise<void> {
63
+ const amountWei = BigNumber.isBigNumber(amount)
64
+ ? amount
65
+ : BigNumber.from(amount);
52
66
 
53
- /** (Optional) dry-run via eth_call */
54
- async simulateDeposit(amount: number): Promise<any> {
55
- return this.provider.call({
56
- to: STAKING_CONTRACT_ADDRESS,
57
- data: this.contract.interface.encodeFunctionData('deposit', [
58
- ethers.BigNumber.from(amount)
59
- ]),
67
+ // callStatic executes the function locally without sending a tx.
68
+ // deposit() doesn't return anything, so we only care if it reverts.
69
+ await this.contract.DepositManager.callStatic.deposit({
70
+ value: amountWei,
60
71
  });
61
72
  }
62
73
 
74
+ private async performDeposit(amountWei: BigNumber): Promise<DepositResult> {
75
+ // Pre-check minDeposit
76
+ const minDeposit: BigNumber = await this.contract.DepositManager.minDeposit();
77
+ if (amountWei.lt(minDeposit)) {
78
+ throw new Error(
79
+ `Deposit amount below minDeposit: ` +
80
+ `amount=${ethers.utils.formatEther(amountWei)} ETH, ` +
81
+ `min=${ethers.utils.formatEther(minDeposit)} ETH`
82
+ );
83
+ }
84
+
85
+ // Send the payable tx
86
+ const tx = await this.contract.DepositManager.deposit({
87
+ value: amountWei,
88
+ });
89
+
90
+ // Wait for 1 confirmation
91
+ const receipt = await tx.wait(1);
92
+
93
+ // Parse Deposited event if present
94
+ let deposited: DepositEvent | undefined;
95
+ const ev = receipt.events?.find((e) => e.event === 'Deposited');
96
+
97
+ if (ev && ev.args) {
98
+ const { user, netEth, fee, shares } = ev.args;
99
+ deposited = {
100
+ user,
101
+ netEth: BigNumber.from(netEth),
102
+ fee: BigNumber.from(fee),
103
+ shares: BigNumber.from(shares),
104
+ };
105
+ }
106
+
107
+ return {
108
+ txHash: tx.hash,
109
+ receipt,
110
+ deposited,
111
+ };
112
+ }
113
+
114
+ /**
115
+ * Resolve the user's ETH + liqETH balances.
116
+ *
117
+ * native = ETH in wallet
118
+ * actual = liqETH token balance (ERC-20)
119
+ * tracked = liqETH tracked balance (protocol/accounting view)
120
+ */
121
+ async getPortfolio(): Promise<Portfolio> {
122
+ const walletAddress = await this.signer.getAddress();
123
+
124
+ // 1) Native ETH balance
125
+ const nativeBalance = await this.provider.getBalance(walletAddress);
126
+ // console.log('nativeBalance', nativeBalance);
127
+ const nativeDecimals = this.network?.nativeCurrency?.decimals ?? 18;
128
+ const nativeSymbol = this.network?.nativeCurrency?.symbol ?? 'ETH';
129
+
130
+ // 2) liqETH ERC-20 balance (actual)
131
+ const liqBalance: ethers.BigNumber = await this.contract.LiqEth.balanceOf(walletAddress);
132
+ // console.log('liqBalance', liqBalance);
133
+
134
+ const liqDecimals = this.network?.nativeCurrency?.decimals ?? 18;
135
+ const liqSymbol = 'Liq' + (this.network?.nativeCurrency?.symbol ?? 'ETH');
136
+
137
+ const portfolio: Portfolio = {
138
+ native: {
139
+ amount: nativeBalance,
140
+ decimals: nativeDecimals,
141
+ symbol: nativeSymbol,
142
+ },
143
+ liq: {
144
+ amount: liqBalance,
145
+ decimals: liqDecimals,
146
+ symbol: liqSymbol,
147
+ },
148
+ staked: { // TODO fetch staked balance from outpost
149
+ amount: BigNumber.from(0),
150
+ decimals: liqDecimals,
151
+ symbol: liqSymbol,
152
+ },
153
+ chainID: this.network.chainId
154
+ }
155
+ // console.log('ETH PORTFOLIO', portfolio);
156
+ return portfolio;
157
+ }
158
+
63
159
  // TODO: implement withdraw, claimRewards, etc.
64
160
  }
@@ -1,6 +1,34 @@
1
+ import { BigNumber, ethers } from 'ethers';
2
+
1
3
  export const CONTRACT_NAMES = [
2
- 'Stake',
4
+ 'Accounting',
5
+ 'DepositManager',
6
+ 'LiqEth',
7
+ 'LiqEthBurn',
8
+ 'LiqEthMint',
9
+ // 'RewardsERC20',
10
+ 'StakingModule',
11
+ // 'ValidatorBalance',
12
+ 'WithdrawalQueue',
13
+ 'WithdrawalVault',
14
+ // 'Yield',
3
15
  ] as const;
4
16
 
5
17
  export type ContractName = typeof CONTRACT_NAMES[number];
6
- export type AddressBook = Record<ContractName, string>;
18
+ export type AddressBook = Record<ContractName, string>;
19
+
20
+ export interface DepositEvent {
21
+ user: string;
22
+ netEth: BigNumber;
23
+ fee: BigNumber;
24
+ shares: BigNumber;
25
+ }
26
+
27
+ export interface DepositResult {
28
+ /** EVM transaction hash */
29
+ txHash: string;
30
+ /** Full receipt, if you want it */
31
+ receipt: ethers.providers.TransactionReceipt;
32
+ /** Parsed Deposited event, if present */
33
+ deposited?: DepositEvent;
34
+ }