-
Notifications
You must be signed in to change notification settings - Fork 1
Expand file tree
/
Copy pathtestFile.js
More file actions
357 lines (299 loc) · 13 KB
/
testFile.js
File metadata and controls
357 lines (299 loc) · 13 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
const { ethers } = require("hardhat");
const { set } = require("mongoose");
const { parseUnits, formatUnits } = ethers;
async function main() {
console.log("Starting deployment and test script...");
// Get deployer account
const [deployer, lender1, lender2, borrower] = await ethers.getSigners();
console.log(`Deploying with account: ${deployer.address}`);
// Deploy MockDeployer
console.log("Deploying MockDeployer...");
const MockDeployer = await ethers.getContractFactory("MockDeployer");
const mockDeployer = await MockDeployer.deploy();
await mockDeployer.waitForDeployment();
console.log(`MockDeployer deployed to: ${await mockDeployer.getAddress()}`);
// Deploy mock contracts
console.log("Deploying mock contracts...");
await mockDeployer.deploy();
console.log("All mock contracts deployed!");
// Initialize mock contracts with liquidity and settings
console.log("Initializing mock contracts...");
await mockDeployer.initialize();
console.log("Mock contracts initialized with liquidity and settings!");
// Get mock contract addresses
const addresses = await mockDeployer.getAddresses();
console.log("Deployed Contract Addresses:");
console.log("----------------------------");
console.log(`USDC: ${addresses[0]}`);
console.log(`cbBTC: ${addresses[1]}`);
console.log(`AavePool: ${addresses[2]}`);
console.log(`SwapRouter: ${addresses[3]}`);
console.log(`Price Oracle: ${addresses[4]}`);
// Get instances of ERC20 tokens first (before minting)
const MockUSDC = await ethers.getContractFactory("MockUSDC");
const MockCbBTC = await ethers.getContractFactory("MockCbBTC");
const usdc = MockUSDC.attach(addresses[0]);
const cbBtc = MockCbBTC.attach(addresses[1]);
// Mint test tokens for the deployer - with enough for later liquidity operations
console.log("Minting test tokens for deployer...");
await mockDeployer.mintTestTokens(
deployer.address,
parseUnits("100000000", 6), // 100M USDC (6 decimals)
parseUnits("1000", 8), // 1000 BTC (8 decimals)
);
console.log(
`Minted 100,000,000 USDC and 1,000 cbBTC for ${deployer.address}`,
);
// Check deployer's balance before proceeding
const deployerUsdcBalance = await usdc.balanceOf(deployer.address);
const deployerBtcBalance = await cbBtc.balanceOf(deployer.address);
console.log(
`Deployer USDC balance: ${formatUnits(deployerUsdcBalance, 6)} USDC`,
);
console.log(
`Deployer cbBTC balance: ${formatUnits(deployerBtcBalance, 8)} cbBTC`,
);
// Deploy the LendingPool contract
console.log("Deploying LendingPool contract...");
const LendingPool = await ethers.getContractFactory("LendingPool");
const lendingPool = await LendingPool.deploy(
addresses[0], // USDC
addresses[1], // cbBTC
addresses[4], // Oracle
addresses[2], // Aave Pool
addresses[3], // Swap Router
);
await lendingPool.waitForDeployment();
console.log(`LendingPool deployed to: ${await lendingPool.getAddress()}`);
console.log("Deployment complete! 🎉");
// Set up the SwapRouter with higher liquidity
const MockSwapRouter = await ethers.getContractFactory("MockSwapRouter");
const swapRouter = MockSwapRouter.attach(addresses[3]);
console.log("-------------- STARTING INTERACTION TESTS --------------");
// Check if the swap router has enough liquidity
const routerUsdcBalance = await usdc.balanceOf(addresses[3]);
const routerBtcBalance = await cbBtc.balanceOf(addresses[3]);
console.log(
`Swap Router USDC balance: ${formatUnits(routerUsdcBalance, 6)} USDC`,
);
console.log(
`Swap Router cbBTC balance: ${formatUnits(routerBtcBalance, 8)} cbBTC`,
);
// Mint additional test tokens for the test accounts
console.log("Minting tokens for test accounts...");
// Mint for lenders
await mockDeployer.mintTestTokens(
lender1.address,
parseUnits("100000", 6),
0,
);
await mockDeployer.mintTestTokens(
lender2.address,
parseUnits("100000", 6),
0,
);
// Mint for borrower
await mockDeployer.mintTestTokens(
borrower.address,
parseUnits("50000", 6),
0,
);
console.log("Minted 100,000 USDC for each lender");
console.log("Minted 50,000 USDC and 1 BTC for borrower");
// Check balances
const lender1Balance = await usdc.balanceOf(lender1.address);
const lender2Balance = await usdc.balanceOf(lender2.address);
const borrowerUsdcBalance = await usdc.balanceOf(borrower.address);
const borrowerBtcBalance = await cbBtc.balanceOf(borrower.address);
console.log("Current balances:");
console.log(`Lender1 USDC: ${formatUnits(lender1Balance, 6)}`);
console.log(`Lender2 USDC: ${formatUnits(lender2Balance, 6)}`);
console.log(`Borrower USDC: ${formatUnits(borrowerUsdcBalance, 6)}`);
console.log(`Borrower cbBTC: ${formatUnits(borrowerBtcBalance, 8)}`);
// Set up a test loan
console.log("Setting up a test loan...");
// Calculate the amount of USDC needed for the loan
const loanAmount = parseUnits("105562.649", 6); // 105,562.649 USDC
const lender1Amount = parseUnits("84450.12", 6); // 84,450.12 USDC
// const lender2Amount = parseUnits("20000", 6); // 20,000 USDC
const borrowerDeposit = (loanAmount * 20n) / 100n; // 20% deposit = 21,112.53 USDC
console.log(`Loan amount: ${formatUnits(loanAmount, 6)} USDC`);
console.log(`Borrower deposit: ${formatUnits(borrowerDeposit, 6)} USDC`);
// Transfer more tokens to the swap router to ensure sufficient liquidity
console.log("Adding more liquidity to swap router...");
// Check deployer's balance again before the transfer
const currentDeployerUsdcBalance = await usdc.balanceOf(deployer.address);
const currentDeployerBtcBalance = await cbBtc.balanceOf(deployer.address);
console.log(
`Deployer current USDC balance: ${formatUnits(currentDeployerUsdcBalance, 6)} USDC`,
);
console.log(
`Deployer current cbBTC balance: ${formatUnits(currentDeployerBtcBalance, 8)} cbBTC`,
);
// Add more liquidity to the swap router - using amounts that we're sure the deployer has
const usdcToAdd = parseUnits("10000000", 6); // 10M USDC
const btcToAdd = parseUnits("100", 8); // 100 BTC
await usdc.connect(deployer).transfer(addresses[3], usdcToAdd);
await cbBtc.connect(deployer).transfer(addresses[3], btcToAdd);
console.log(
`Added ${formatUnits(usdcToAdd, 6)} USDC and ${formatUnits(btcToAdd, 8)} cbBTC to the swap router`,
);
// Check new router balances
const newRouterUsdcBalance = await usdc.balanceOf(addresses[3]);
const newRouterBtcBalance = await cbBtc.balanceOf(addresses[3]);
console.log(
`New Swap Router USDC balance: ${formatUnits(newRouterUsdcBalance, 6)} USDC`,
);
console.log(
`New Swap Router cbBTC balance: ${formatUnits(newRouterBtcBalance, 8)} cbBTC`,
);
// Approve tokens for the lending pool
const lendingPoolAddress = await lendingPool.getAddress();
console.log(`Approving lendingPool at address: ${lendingPoolAddress}`);
await usdc.connect(lender1).approve(lendingPoolAddress, lender1Amount);
// await usdc.connect(lender2).approve(lendingPoolAddress, lender2Amount);
await usdc.connect(borrower).approve(lendingPoolAddress, borrowerDeposit);
console.log(
`Lender1 approved LendingPool to spend ${formatUnits(lender1Amount, 6)} USDC`,
);
// console.log(
// `Lender2 approved LendingPool to spend ${formatUnits(lender2Amount, 6)} USDC`,
// );
console.log(
`Borrower approved LendingPool to spend ${formatUnits(borrowerDeposit, 6)} USDC`,
);
// Check allowances to verify approvals
const lender1Allowance = await usdc.allowance(
lender1.address,
lendingPoolAddress,
);
// const lender2Allowance = await usdc.allowance(
// lender2.address,
// lendingPoolAddress,
// );
const borrowerAllowance = await usdc.allowance(
borrower.address,
lendingPoolAddress,
);
console.log("Checking allowances to verify approvals:");
console.log(`Lender1 allowance: ${formatUnits(lender1Allowance, 6)} USDC`);
// console.log(`Lender2 allowance: ${formatUnits(lender2Allowance, 6)} USDC`);
console.log(`Borrower allowance: ${formatUnits(borrowerAllowance, 6)} USDC`);
// Create the loan
console.log("Creating loan...");
const tx = await lendingPool.connect(borrower).loan(
loanAmount, // Total loan amount (40,000 USDC)
18, // 18 months duration
15, // 15% annual interest rate
[lender1.address], // Lender addresses
[lender1Amount], // Lender amounts
);
await tx.wait();
console.log("Loan created successfully!");
// Get loan details
const latestBlock = await ethers.provider.getBlock("latest");
const loanId = ethers.keccak256(
ethers.solidityPacked(
["address", "uint256"],
[borrower.address, latestBlock.timestamp],
),
);
console.log(`Generated loan ID: ${loanId}`);
// Check updated balances
const updatedLender1Balance = await usdc.balanceOf(lender1.address);
// const updatedLender2Balance = await usdc.balanceOf(lender2.address);
const updatedBorrowerUsdcBalance = await usdc.balanceOf(borrower.address);
console.log("Updated balances after loan creation:");
console.log(`Lender1 USDC: ${formatUnits(updatedLender1Balance, 6)}`);
// console.log(`Lender2 USDC: ${formatUnits(updatedLender2Balance, 6)}`);
console.log(`Borrower USDC: ${formatUnits(updatedBorrowerUsdcBalance, 6)}`);
const MockAavePool = await ethers.getContractFactory("MockAavePool");
const aavePool = MockAavePool.attach(addresses[2]);
const staked = await aavePool.getUserSupply(addresses[1], lendingPoolAddress);
console.log(
`Staked cbBTC in Aave by LendingPool: ${ethers.formatUnits(staked, 8)} cbBTC`,
);
console.log("Test completed successfully! 🎉");
// console.log("---------- STARTING REPAYMENT TEST ----------");
// const [principals, interests, paidStatuses] =
// await lendingPool.getAmortizationSchedule(loanId);
// console.log("Amortization schedule:");
// console.log(
// "Principals:",
// principals.map((p) => ethers.formatUnits(p, 6)),
// );
// console.log(
// "Interests:",
// interests.map((i) => ethers.formatUnits(i, 6)),
// );
// console.log(
// "Paid statuses:",
// paidStatuses.map((s) => s.toString()),
// );
// console.log("Loan ID:", loanId);
// const lpBalanceBefore = await usdc.balanceOf(lendingPoolAddress);
// console.log(
// "LendingPool USDC balance before payout:",
// formatUnits(lpBalanceBefore, 6),
// );
// // Approve repayment
// const repaymentAmount = parseUnits("3517", 6); // First repayment
// await usdc.connect(borrower).approve(lendingPoolAddress, repaymentAmount);
// console.log(
// `Borrower approved ${formatUnits(repaymentAmount, 6)} USDC for repayment`,
// );
// const allowance = await usdc.allowance(borrower.address, lendingPoolAddress);
// console.log(`Borrower allowance: ${formatUnits(allowance, 6)} USDC`);
// const borrowerBalance = await usdc.balanceOf(borrower.address);
// console.log(`Borrower balance: ${formatUnits(borrowerBalance, 6)} USDC`);
// const debug = await lendingPool.debugUnstakeCalc(
// loanId,
// parseUnits("3183.3", 6),
// ); // principal repaid in this payout
// console.log(
// `Proportion repaid: ${ethers.formatUnits(debug[0], 18)} (1.0 = fully repaid)`,
// );
// console.log(`cbBTC to unstake: ${ethers.formatUnits(debug[1], 8)} cbBTC`);
// const stakedBefore = await lendingPool.getStakedAmount(loanId);
// console.log(
// `Staked amount before repayment: ${ethers.formatUnits(stakedBefore, 8)} cbBTC`,
// );
// // Call payouts
// const payoutTx = await lendingPool
// .connect(borrower)
// .payouts(loanId, repaymentAmount);
// await payoutTx.wait();
// console.log(
// `Borrower repaid ${formatUnits(repaymentAmount, 6)} USDC for loan ${loanId}`,
// );
// const stakedAfter = await lendingPool.getStakedAmount(loanId);
// console.log(
// `Staked amount after repayment: ${ethers.formatUnits(stakedAfter, 8)} cbBTC`,
// );
// // Check balances after payout
// const lender1Post = await usdc.balanceOf(lender1.address);
// const lender2Post = await usdc.balanceOf(lender2.address);
// const borrowerPost = await usdc.balanceOf(borrower.address);
// const borrowerBtcPost = await cbBtc.balanceOf(borrower.address);
// const lendingPoolPost = await cbBtc.balanceOf(lendingPoolAddress);
// console.log("Balances after repayment:");
// console.log(`Lender1: ${formatUnits(lender1Post, 6)} USDC`);
// console.log(`Lender2: ${formatUnits(lender2Post, 6)} USDC`);
// console.log(`Borrower: ${formatUnits(borrowerPost, 6)} USDC`);
// console.log(`Borrower cbBTC: ${formatUnits(borrowerBtcPost, 8)} cbBTC`);
// console.log(`LendingPool cbBTC: ${formatUnits(lendingPoolPost, 8)} cbBTC`);
// // Check cbBTC still staked
// const remainingStake = await aavePool.getUserSupply(
// addresses[1],
// lendingPoolAddress,
// );
// console.log(
// `Remaining cbBTC in Aave for LendingPool: ${formatUnits(remainingStake, 8)} cbBTC`,
// );
}
main()
.then(() => process.exit(0))
.catch((error) => {
console.error("Deployment or testing failed:", error);
process.exit(1);
});