From 27365697ac4eda6ac1f97c79d6226146719fad60 Mon Sep 17 00:00:00 2001 From: David Racero Date: Mon, 16 Nov 2020 19:22:22 +0100 Subject: [PATCH] Added mainnet check list. Remove deployed contracts. Update README.md --- README.md | 25 + contracts/misc/AaveProtocolDataProvider.sol | 16 +- .../misc/interfaces/IUniswapV2Router01.sol | 160 ++ .../misc/interfaces/IUniswapV2Router02.sol | 50 + deployed-contracts.json | 1336 ----------------- helpers/configuration.ts | 2 +- helpers/contracts-helpers.ts | 4 +- package.json | 14 +- tasks/full/1_address_provider.ts | 9 +- tasks/full/2_lending_pool.ts | 3 - tasks/full/3_oracles.ts | 7 - tasks/migrations/aave.full.ts | 5 +- tasks/migrations/aave.mainnet.ts | 8 +- test/__setup.spec.ts | 11 +- test/helpers/make-suite.ts | 6 +- test/mainnet/check-list.spec.ts | 362 +++++ 16 files changed, 645 insertions(+), 1373 deletions(-) create mode 100644 contracts/misc/interfaces/IUniswapV2Router01.sol create mode 100644 contracts/misc/interfaces/IUniswapV2Router02.sol delete mode 100644 deployed-contracts.json create mode 100644 test/mainnet/check-list.spec.ts diff --git a/README.md b/README.md index 12395316..4ebfdb3c 100644 --- a/README.md +++ b/README.md @@ -83,6 +83,8 @@ npm run aave:kovan:full:migration ### Mainnet fork deployment +You can deploy Aave Protocol v2 in a forked Mainnet chain using Hardhat built-in feature: + ``` # In one terminal, run a hardhat note with mainnet fork enabled MAINNET_FORK=true npx hardhat node @@ -95,4 +97,27 @@ docker-compose exec contracts-env bash # A new Bash terminal is prompted, connected to the container npm run aave:fork:main + +# Contracts are now deployed at Hardhat node with Mainnet fork. + +# You can interact with them via Hardhat console +MAINNET_FORK=true npx hardhat console +# Or your custom Hardhat task +MAINNET_FORK=true npx hardhat your-custom-task + +``` + +### Mainnet fork - Run the check list + +For testing the deployment scripts for Mainnet release, you can run the check-list tests in a Mainnet fork using Hardhat built-in feature: + +``` +# In another terminal, run docker-compose +docker-compose up + +# Open another tab or terminal +docker-compose exec contracts-env bash + +# A new Bash terminal is prompted, connected to the container +npm run test:main:check-list ``` diff --git a/contracts/misc/AaveProtocolDataProvider.sol b/contracts/misc/AaveProtocolDataProvider.sol index cc35f17d..ca8e8d85 100644 --- a/contracts/misc/AaveProtocolDataProvider.sol +++ b/contracts/misc/AaveProtocolDataProvider.sol @@ -10,11 +10,15 @@ import {ReserveConfiguration} from '../libraries/configuration/ReserveConfigurat import {UserConfiguration} from '../libraries/configuration/UserConfiguration.sol'; import {IStableDebtToken} from '../tokenization/interfaces/IStableDebtToken.sol'; import {IVariableDebtToken} from '../tokenization/interfaces/IVariableDebtToken.sol'; +import 'hardhat/console.sol'; contract AaveProtocolDataProvider { using ReserveConfiguration for ReserveConfiguration.Map; using UserConfiguration for UserConfiguration.Map; + address constant MKR = 0x9f8F72aA9304c8B593d555F12eF6589cC3A579A2; + address constant ETH = 0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE; + struct TokenData { string symbol; address tokenAddress; @@ -31,10 +35,16 @@ contract AaveProtocolDataProvider { address[] memory reserves = pool.getReservesList(); TokenData[] memory reservesTokens = new TokenData[](reserves.length); for (uint256 i = 0; i < reserves.length; i++) { + if (reserves[i] == MKR) { + reservesTokens[i] = TokenData({symbol: 'MKR', tokenAddress: reserves[i]}); + continue; + } + if (reserves[i] == ETH) { + reservesTokens[i] = TokenData({symbol: 'ETH', tokenAddress: reserves[i]}); + continue; + } reservesTokens[i] = TokenData({ - symbol: (reserves[i] == 0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE) - ? 'ETH' - : IERC20Detailed(reserves[i]).symbol(), + symbol: IERC20Detailed(reserves[i]).symbol(), tokenAddress: reserves[i] }); } diff --git a/contracts/misc/interfaces/IUniswapV2Router01.sol b/contracts/misc/interfaces/IUniswapV2Router01.sol new file mode 100644 index 00000000..6acc52be --- /dev/null +++ b/contracts/misc/interfaces/IUniswapV2Router01.sol @@ -0,0 +1,160 @@ +pragma solidity >=0.6.2; + +interface IUniswapV2Router01 { + function factory() external pure returns (address); + + function WETH() external pure returns (address); + + function addLiquidity( + address tokenA, + address tokenB, + uint256 amountADesired, + uint256 amountBDesired, + uint256 amountAMin, + uint256 amountBMin, + address to, + uint256 deadline + ) + external + returns ( + uint256 amountA, + uint256 amountB, + uint256 liquidity + ); + + function addLiquidityETH( + address token, + uint256 amountTokenDesired, + uint256 amountTokenMin, + uint256 amountETHMin, + address to, + uint256 deadline + ) + external + payable + returns ( + uint256 amountToken, + uint256 amountETH, + uint256 liquidity + ); + + function removeLiquidity( + address tokenA, + address tokenB, + uint256 liquidity, + uint256 amountAMin, + uint256 amountBMin, + address to, + uint256 deadline + ) external returns (uint256 amountA, uint256 amountB); + + function removeLiquidityETH( + address token, + uint256 liquidity, + uint256 amountTokenMin, + uint256 amountETHMin, + address to, + uint256 deadline + ) external returns (uint256 amountToken, uint256 amountETH); + + function removeLiquidityWithPermit( + address tokenA, + address tokenB, + uint256 liquidity, + uint256 amountAMin, + uint256 amountBMin, + address to, + uint256 deadline, + bool approveMax, + uint8 v, + bytes32 r, + bytes32 s + ) external returns (uint256 amountA, uint256 amountB); + + function removeLiquidityETHWithPermit( + address token, + uint256 liquidity, + uint256 amountTokenMin, + uint256 amountETHMin, + address to, + uint256 deadline, + bool approveMax, + uint8 v, + bytes32 r, + bytes32 s + ) external returns (uint256 amountToken, uint256 amountETH); + + function swapExactTokensForTokens( + uint256 amountIn, + uint256 amountOutMin, + address[] calldata path, + address to, + uint256 deadline + ) external returns (uint256[] memory amounts); + + function swapTokensForExactTokens( + uint256 amountOut, + uint256 amountInMax, + address[] calldata path, + address to, + uint256 deadline + ) external returns (uint256[] memory amounts); + + function swapExactETHForTokens( + uint256 amountOutMin, + address[] calldata path, + address to, + uint256 deadline + ) external payable returns (uint256[] memory amounts); + + function swapTokensForExactETH( + uint256 amountOut, + uint256 amountInMax, + address[] calldata path, + address to, + uint256 deadline + ) external returns (uint256[] memory amounts); + + function swapExactTokensForETH( + uint256 amountIn, + uint256 amountOutMin, + address[] calldata path, + address to, + uint256 deadline + ) external returns (uint256[] memory amounts); + + function swapETHForExactTokens( + uint256 amountOut, + address[] calldata path, + address to, + uint256 deadline + ) external payable returns (uint256[] memory amounts); + + function quote( + uint256 amountA, + uint256 reserveA, + uint256 reserveB + ) external pure returns (uint256 amountB); + + function getAmountOut( + uint256 amountIn, + uint256 reserveIn, + uint256 reserveOut + ) external pure returns (uint256 amountOut); + + function getAmountIn( + uint256 amountOut, + uint256 reserveIn, + uint256 reserveOut + ) external pure returns (uint256 amountIn); + + function getAmountsOut(uint256 amountIn, address[] calldata path) + external + view + returns (uint256[] memory amounts); + + function getAmountsIn(uint256 amountOut, address[] calldata path) + external + view + returns (uint256[] memory amounts); +} diff --git a/contracts/misc/interfaces/IUniswapV2Router02.sol b/contracts/misc/interfaces/IUniswapV2Router02.sol new file mode 100644 index 00000000..53fa9eb3 --- /dev/null +++ b/contracts/misc/interfaces/IUniswapV2Router02.sol @@ -0,0 +1,50 @@ +pragma solidity >=0.6.2; + +import './IUniswapV2Router01.sol'; + +interface IUniswapV2Router02 is IUniswapV2Router01 { + function removeLiquidityETHSupportingFeeOnTransferTokens( + address token, + uint256 liquidity, + uint256 amountTokenMin, + uint256 amountETHMin, + address to, + uint256 deadline + ) external returns (uint256 amountETH); + + function removeLiquidityETHWithPermitSupportingFeeOnTransferTokens( + address token, + uint256 liquidity, + uint256 amountTokenMin, + uint256 amountETHMin, + address to, + uint256 deadline, + bool approveMax, + uint8 v, + bytes32 r, + bytes32 s + ) external returns (uint256 amountETH); + + function swapExactTokensForTokensSupportingFeeOnTransferTokens( + uint256 amountIn, + uint256 amountOutMin, + address[] calldata path, + address to, + uint256 deadline + ) external; + + function swapExactETHForTokensSupportingFeeOnTransferTokens( + uint256 amountOutMin, + address[] calldata path, + address to, + uint256 deadline + ) external payable; + + function swapExactTokensForETHSupportingFeeOnTransferTokens( + uint256 amountIn, + uint256 amountOutMin, + address[] calldata path, + address to, + uint256 deadline + ) external; +} diff --git a/deployed-contracts.json b/deployed-contracts.json deleted file mode 100644 index 55e206aa..00000000 --- a/deployed-contracts.json +++ /dev/null @@ -1,1336 +0,0 @@ -{ - "MintableERC20": { - "buidlerevm": { - "address": "0x18b9306737eaf6E8FC8e737F488a1AE077b18053", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x18b9306737eaf6E8FC8e737F488a1AE077b18053", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "DAI": { - "buidlerevm": { - "address": "0x7c2C195CD6D34B8F845992d380aADB2730bB9C6F", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x7c2C195CD6D34B8F845992d380aADB2730bB9C6F", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "LEND": { - "buidlerevm": { - "address": "0x8858eeB3DfffA017D4BCE9801D340D36Cf895CCf", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "TUSD": { - "buidlerevm": { - "address": "0x0078371BDeDE8aAc7DeBfFf451B74c5EDB385Af7", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x0078371BDeDE8aAc7DeBfFf451B74c5EDB385Af7", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "BAT": { - "buidlerevm": { - "address": "0xf4e77E5Da47AC3125140c470c71cBca77B5c638c", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0xf4e77E5Da47AC3125140c470c71cBca77B5c638c", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "WETH": { - "buidlerevm": { - "address": "0xf784709d2317D872237C4bC22f867d1BAe2913AB", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0xf784709d2317D872237C4bC22f867d1BAe2913AB", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "USDC": { - "buidlerevm": { - "address": "0x3619DbE27d7c1e7E91aA738697Ae7Bc5FC3eACA5", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x3619DbE27d7c1e7E91aA738697Ae7Bc5FC3eACA5", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "USDT": { - "buidlerevm": { - "address": "0x038B86d9d8FAFdd0a02ebd1A476432877b0107C8", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x038B86d9d8FAFdd0a02ebd1A476432877b0107C8", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "SUSD": { - "buidlerevm": { - "address": "0x1A1FEe7EeD918BD762173e4dc5EfDB8a78C924A8", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x1A1FEe7EeD918BD762173e4dc5EfDB8a78C924A8", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "ZRX": { - "buidlerevm": { - "address": "0x500D1d6A4c7D8Ae28240b47c8FCde034D827fD5e", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x500D1d6A4c7D8Ae28240b47c8FCde034D827fD5e", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "MKR": { - "buidlerevm": { - "address": "0xc4905364b78a742ccce7B890A89514061E47068D", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0xc4905364b78a742ccce7B890A89514061E47068D", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "WBTC": { - "buidlerevm": { - "address": "0xD6C850aeBFDC46D7F4c207e445cC0d6B0919BDBe", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0xD6C850aeBFDC46D7F4c207e445cC0d6B0919BDBe", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "LINK": { - "buidlerevm": { - "address": "0x8B5B7a6055E54a36fF574bbE40cf2eA68d5554b3", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x8B5B7a6055E54a36fF574bbE40cf2eA68d5554b3", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "KNC": { - "buidlerevm": { - "address": "0xEcc0a6dbC0bb4D51E4F84A315a9e5B0438cAD4f0", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0xEcc0a6dbC0bb4D51E4F84A315a9e5B0438cAD4f0", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "MANA": { - "buidlerevm": { - "address": "0x20Ce94F404343aD2752A2D01b43fa407db9E0D00", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x20Ce94F404343aD2752A2D01b43fa407db9E0D00", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "REP": { - "buidlerevm": { - "address": "0x1d80315fac6aBd3EfeEbE97dEc44461ba7556160", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x1d80315fac6aBd3EfeEbE97dEc44461ba7556160", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "SNX": { - "buidlerevm": { - "address": "0x52d3b94181f8654db2530b0fEe1B19173f519C52", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x52d3b94181f8654db2530b0fEe1B19173f519C52", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "BUSD": { - "buidlerevm": { - "address": "0xd15468525c35BDBC1eD8F2e09A00F8a173437f2f", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0xd15468525c35BDBC1eD8F2e09A00F8a173437f2f", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "USD": { - "buidlerevm": { - "address": "0x7e35Eaf7e8FBd7887ad538D4A38Df5BbD073814a", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x7e35Eaf7e8FBd7887ad538D4A38Df5BbD073814a", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "UNI_DAI_ETH": { - "buidlerevm": { - "address": "0xB00cC45B4a7d3e1FEE684cFc4417998A1c183e6d", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0xB00cC45B4a7d3e1FEE684cFc4417998A1c183e6d", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "UNI_USDC_ETH": { - "buidlerevm": { - "address": "0x58F132FBB86E21545A4Bace3C19f1C05d86d7A22", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x58F132FBB86E21545A4Bace3C19f1C05d86d7A22", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "UNI_SETH_ETH": { - "buidlerevm": { - "address": "0xa4bcDF64Cdd5451b6ac3743B414124A6299B65FF", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0xa4bcDF64Cdd5451b6ac3743B414124A6299B65FF", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "UNI_LINK_ETH": { - "buidlerevm": { - "address": "0x22474D350EC2dA53D717E30b96e9a2B7628Ede5b", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x22474D350EC2dA53D717E30b96e9a2B7628Ede5b", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "UNI_MKR_ETH": { - "buidlerevm": { - "address": "0x5A0773Ff307Bf7C71a832dBB5312237fD3437f9F", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x5A0773Ff307Bf7C71a832dBB5312237fD3437f9F", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "UNI_LEND_ETH": { - "buidlerevm": { - "address": "0x18b9306737eaf6E8FC8e737F488a1AE077b18053", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x18b9306737eaf6E8FC8e737F488a1AE077b18053", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "LendingPoolAddressesProvider": { - "buidlerevm": { - "address": "0xFAe0fd738dAbc8a0426F47437322b6d026A9FD95", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "kovan": { - "address": "0x2ed9F124cF9b079DDBbFb68D352FB83bdeFc39Ee", - "deployer": "0x85e4A467343c0dc4aDAB74Af84448D9c45D8ae6F" - }, - "hardhat": { - "address": "0x7c2C195CD6D34B8F845992d380aADB2730bB9C6F", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "tenderlyMain": { - "address": "0x4Be9d82643799cA95D3a77d1618afC5011268382", - "deployer": "0xddAF59aB7A3f2215965d8bF74Eb975073a5fa126" - } - }, - "LendingPoolAddressesProviderRegistry": { - "buidlerevm": { - "address": "0x18b9306737eaf6E8FC8e737F488a1AE077b18053", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "kovan": { - "address": "0xAA14619F08ADe8109F47905CAda9EDDee0c876c3", - "deployer": "0x85e4A467343c0dc4aDAB74Af84448D9c45D8ae6F" - }, - "hardhat": { - "address": "0xf4e77E5Da47AC3125140c470c71cBca77B5c638c", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "tenderlyMain": { - "address": "0x70DA60D03b61e32F6d11eD4056D15a6202C673c5", - "deployer": "0xc10Cd14F2B546e6e4603e002AD2f9CC4f3c1d3c8" - } - }, - "ReserveLogic": { - "buidlerevm": { - "address": "0x920d847fE49E54C19047ba8bc236C45A8068Bca7", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "kovan": { - "address": "0x89b33E0CB2294f5c09ACB6281B37DED90Cd8025F", - "deployer": "0x85e4A467343c0dc4aDAB74Af84448D9c45D8ae6F" - }, - "hardhat": { - "address": "0x3619DbE27d7c1e7E91aA738697Ae7Bc5FC3eACA5", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "tenderlyMain": { - "address": "0xbC4BbB5d0642EB4841Fe97fE7B29035a8539a078", - "deployer": "0x3054fFbdD1506e38FDA08B1e19be37a3081F74bf" - } - }, - "GenericLogic": { - "buidlerevm": { - "address": "0xA4765Ff72A9F3CfE73089bb2c3a41B838DF71574", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "kovan": { - "address": "0x86EB6F23b497320742eb1dDab598fD04c3E11682", - "deployer": "0x85e4A467343c0dc4aDAB74Af84448D9c45D8ae6F" - }, - "hardhat": { - "address": "0x038B86d9d8FAFdd0a02ebd1A476432877b0107C8", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "tenderlyMain": { - "address": "0x7962d48c83a8B7a511Ae3986145E497E55b43d02", - "deployer": "0xEB445d7d663ff60fFdE5aed8bFa8B4aa678E9Af3" - } - }, - "ValidationLogic": { - "buidlerevm": { - "address": "0x35c1419Da7cf0Ff885B8Ef8EA9242FEF6800c99b", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "kovan": { - "address": "0xe0bd0Adcca9de46aE8fe8E50276A13b4c1dfE931", - "deployer": "0x85e4A467343c0dc4aDAB74Af84448D9c45D8ae6F" - }, - "hardhat": { - "address": "0x1A1FEe7EeD918BD762173e4dc5EfDB8a78C924A8", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "tenderlyMain": { - "address": "0x303eE85cB0e2B1fea6dF1A67F7D3868A602780D0", - "deployer": "0x2269cA0fD6e027160E3e0176DF25a32c039C7c16" - } - }, - "LendingPool": { - "buidlerevm": { - "address": "0xe2607EabC87fd0A4856840bF23da8458cDF0434F", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "kovan": { - "address": "0x212B0b733BFbc58D3B62b79Da1B38E915057039f" - }, - "hardhat": { - "address": "0xdA71454D2a71D63116cd67099e4a0fdd3a8Dfb47" - }, - "tenderlyMain": { - "address": "0xd2c20bDA613DD9E268559a08CdDb49A90a0b9dA9" - } - }, - "LendingPoolConfigurator": { - "buidlerevm": { - "address": "0xdbaA15927b1463EdD14Cf51D082BD7703Fd1C238" - }, - "kovan": { - "address": "0xD57c7ad0F079EbA38B0c1972d68d13f78719FC00" - }, - "hardhat": { - "address": "0x1b88b3E43526cB076931AD76cB2eC0CC93382FAc" - }, - "tenderlyMain": { - "address": "0x291c74E889865751557776Df1FD23476981DDcB2" - } - }, - "StableAndVariableTokensHelper": { - "buidlerevm": { - "address": "0x06bA8d8af0dF898D0712DffFb0f862cC51AF45c2", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "kovan": { - "address": "0xF67bbFB9265b7eA7c450F405673690A11a20748D", - "deployer": "0x85e4A467343c0dc4aDAB74Af84448D9c45D8ae6F" - }, - "hardhat": { - "address": "0xEcc0a6dbC0bb4D51E4F84A315a9e5B0438cAD4f0", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "tenderlyMain": { - "address": "0xbBE7278FdF24860F05D9a10316F3c5E425cBD4ec", - "deployer": "0x0Fc326f9b8155b674733bCc8FcDcdE36606ba7C5" - } - }, - "ATokensAndRatesHelper": { - "buidlerevm": { - "address": "0xA4765Ff72A9F3CfE73089bb2c3a41B838DF71574", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "kovan": { - "address": "0x8177E36Fc8Cb12c31F0e463F39394fC417345B56", - "deployer": "0x85e4A467343c0dc4aDAB74Af84448D9c45D8ae6F" - }, - "hardhat": { - "address": "0x20Ce94F404343aD2752A2D01b43fa407db9E0D00", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "tenderlyMain": { - "address": "0x39dE816FaEA0CBC12C2066bB379d7425c128A7Ee", - "deployer": "0x0c90eCAE8f9f8E5CafAfFcBBa46Eeb41A46Bb2a8" - } - }, - "PriceOracle": { - "buidlerevm": { - "address": "0x1750499D05Ed1674d822430FB960d5F6731fDf64", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0xe1B3b8F6b298b52bCd15357ED29e65e66a4045fF", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "MockAggregator": { - "buidlerevm": { - "address": "0xEC1C93A9f6a9e18E97784c76aC52053587FcDB89", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0xfA9dbd706c674801F50169f4B5862cCe045408E6", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "ChainlinkProxyPriceProvider": { - "buidlerevm": { - "address": "0x7B6C3e5486D9e6959441ab554A889099eed76290", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x1d80315fac6aBd3EfeEbE97dEc44461ba7556160", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "tenderlyMain": { - "address": "0x5D7a3a9317f0F232828Cca6F3752b7e2820075B0", - "deployer": "0xFaA2D857Ff599923415523f8b0B54dFdc5c6E7c3" - } - }, - "LendingRateOracle": { - "buidlerevm": { - "address": "0xD83D2773a7873ae2b5f8Fb92097e20a8C64F691E", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x2D8553F9ddA85A9B3259F6Bf26911364B85556F5", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "tenderlyMain": { - "address": "0xABF6Cf29dD10232E5168F085F2a9ebA690F9623b", - "deployer": "0x50DBD6EC6c6666c3aE018E5d0f62104a598F9571" - } - }, - "AaveProtocolDataProvider": { - "buidlerevm": { - "address": "0x93472C0e03215F9c33DA240Eb16703C8244eAa8c" - }, - "kovan": { - "address": "0x2457cE7EFe23B8887B08006004C3Fdb4E3252094", - "deployer": "0x85e4A467343c0dc4aDAB74Af84448D9c45D8ae6F" - }, - "hardhat": { - "address": "0x53369fd4680FfE3DfF39Fc6DDa9CfbfD43daeA2E", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "LendingPoolCollateralManager": { - "buidlerevm": { - "address": "0x3c5408De7435Dfa3eB2aF2Edf5E39385f68F69b2", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "kovan": { - "address": "0x15fF71A8F0B1E43AF2A0D3554c9F8E41601bCE6b", - "deployer": "0x85e4A467343c0dc4aDAB74Af84448D9c45D8ae6F" - }, - "hardhat": { - "address": "0xF0B4ACda6D679ea22AC5C4fD1973D0d58eA10ec1", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "MockFlashLoanReceiver": { - "buidlerevm": { - "address": "0x0459c841b02Aee8730730C737582c53B20a27288" - }, - "hardhat": { - "address": "0x2530ce07D254eA185E8e0bCC37a39e2FbA3bE548" - } - }, - "WalletBalanceProvider": { - "buidlerevm": { - "address": "0x77B0b5636fEA30eA79BB65AeCCdb599997A849A8", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "kovan": { - "address": "0x3aCd4b30bC70647620989B9f98C4E21867Bd753A", - "deployer": "0x85e4A467343c0dc4aDAB74Af84448D9c45D8ae6F" - }, - "hardhat": { - "address": "0xA17827A991EB72793fa437e580B084ceB25Ab0f9", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "MockAToken": { - "buidlerevm": { - "address": "0x0EBCa695959e5f138Af772FAa44ce1A9C7aEd921", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x33958cC3535Fc328369EAC2B2Bebd120D67C7fa1", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "MockStableDebtToken": { - "buidlerevm": { - "address": "0x417fc1038b2AF553D65F4fF2839efE9f93Ec1eac", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x2cBbbBE1B75Ad7848F0844215816F551f429c64f", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "MockVariableDebtToken": { - "buidlerevm": { - "address": "0x8BFFF31B1757da579Bb5B118489568526F7fb6D4", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0xbAc762e2000b6815268587b081Fd17aC25519aD5", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "WETHGateway": { - "buidlerevm": { - "address": "0x0Cf45557d25a4e4c0F1aC65EF6c48ae67c61a0E6", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "kovan": { - "address": "0x7d8B46401dC07ccA3f65F0FBBfE834D61C76C54f", - "deployer": "0x85e4A467343c0dc4aDAB74Af84448D9c45D8ae6F" - }, - "hardhat": { - "address": "0x8565Fb7dfB5D36b2aA00086ffc920cfF20db4F2f", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "WETHMocked": { - "buidlerevm": { - "address": "0xf784709d2317D872237C4bC22f867d1BAe2913AB", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x1d80315fac6aBd3EfeEbE97dEc44461ba7556160", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "MintableDelegationERC20": { - "buidlerevm": { - "address": "0x7fAeC7791277Ff512c41CA903c177B2Ed952dDAc", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x33958cC3535Fc328369EAC2B2Bebd120D67C7fa1", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "AAVE": { - "buidlerevm": { - "address": "0x8858eeB3DfffA017D4BCE9801D340D36Cf895CCf", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x8858eeB3DfffA017D4BCE9801D340D36Cf895CCf", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "REN": { - "buidlerevm": { - "address": "0x2D8553F9ddA85A9B3259F6Bf26911364B85556F5", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x2D8553F9ddA85A9B3259F6Bf26911364B85556F5", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "YFI": { - "buidlerevm": { - "address": "0x5bcb88A0d20426e451332eE6C4324b0e663c50E0", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x5bcb88A0d20426e451332eE6C4324b0e663c50E0", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "UNI": { - "buidlerevm": { - "address": "0x3521eF8AaB0323004A6dD8b03CE890F4Ea3A13f5", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x3521eF8AaB0323004A6dD8b03CE890F4Ea3A13f5", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "AToken": { - "buidlerevm": { - "address": "0x33958cC3535Fc328369EAC2B2Bebd120D67C7fa1", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x2cBbbBE1B75Ad7848F0844215816F551f429c64f", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "SelfdestructTransferMock": { - "buidlerevm": { - "address": "0x920d847fE49E54C19047ba8bc236C45A8068Bca7", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x2cBbbBE1B75Ad7848F0844215816F551f429c64f", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "ENJ": { - "buidlerevm": { - "address": "0x53369fd4680FfE3DfF39Fc6DDa9CfbfD43daeA2E", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - }, - "hardhat": { - "address": "0x53369fd4680FfE3DfF39Fc6DDa9CfbfD43daeA2E", - "deployer": "0xc783df8a850f42e7F7e57013759C285caa701eB6" - } - }, - "LendingPoolImpl": { - "kovan": { - "address": "0x301F889146aaFEfD88d5D442eEcd12AeAC3D1Fc3" - }, - "hardhat": { - "address": "0x500D1d6A4c7D8Ae28240b47c8FCde034D827fD5e" - }, - "tenderlyMain": { - "address": "0xd72EC88B9c173dF3a61eB7D9D33ECA59Ad57D7C2" - } - }, - "LendingPoolConfiguratorImpl": { - "kovan": { - "address": "0x25d9A07E6a749488f36e3c89A38C8235adb33AA2" - }, - "hardhat": { - "address": "0xD6C850aeBFDC46D7F4c207e445cC0d6B0919BDBe" - }, - "tenderlyMain": { - "address": "0x89898cF20C9BBFfBAC292aC89E078ae602268d0A" - } - }, - "LendingPoolCollateralManagerImpl": { - "kovan": { - "address": "0x15fF71A8F0B1E43AF2A0D3554c9F8E41601bCE6b" - }, - "hardhat": { - "address": "0xF0B4ACda6D679ea22AC5C4fD1973D0d58eA10ec1" - } - }, - "stableDebtAAVE": { - "kovan": { - "address": "0x9d6cD3e0cb7A916dD788BE8937Db2E28E653083F" - }, - "hardhat": { - "address": "0x9230C6B871c19A7A285E46bC59dbA99863ED267E" - } - }, - "variableDebtAAVE": { - "kovan": { - "address": "0x7069766BAEAE5042eF9Efa25D423853Fa244e03D" - }, - "hardhat": { - "address": "0x06134447473A1ad19dd05554780816C542486d15" - } - }, - "stableDebtBAT": { - "kovan": { - "address": "0x7bA20003bc65A551aAc9670b96520F544556025D" - }, - "hardhat": { - "address": "0xd5b242D4c92Cf99ad1b52097C02D6400a5042c07" - } - }, - "variableDebtBAT": { - "kovan": { - "address": "0x25bfFB7E493bAAd885Ad7EE676E5e32c6F85D6FE" - }, - "hardhat": { - "address": "0x38556B87c95aA00D1ac92f2Af5F24A62779c51f1" - } - }, - "stableDebtBUSD": { - "kovan": { - "address": "0xA5bb990BA8c1367dF8b34a7628Db1786790782E8" - }, - "hardhat": { - "address": "0x676FADAC7780FCF65e788209F4E91f2057508d24" - } - }, - "variableDebtBUSD": { - "kovan": { - "address": "0xa75EF57f21484029bA17cb31A59176500dA95Bf0" - }, - "hardhat": { - "address": "0x2481b47272CacFB4213493d899E1f7296C3a6751" - } - }, - "stableDebtDAI": { - "kovan": { - "address": "0x83B7666885dAC6D68f9f32569EC0F4585979d74B" - }, - "hardhat": { - "address": "0xbC0e31570E564642d279f3123923a58F64294CF0" - } - }, - "variableDebtDAI": { - "kovan": { - "address": "0x897d762EF8fe013a824503d5Eda2a329Ad98f7E0" - }, - "hardhat": { - "address": "0x73a571b6E3AFAc5574A328AB6B0e8150c520e631" - } - }, - "aAAVE": { - "kovan": { - "address": "0x74A4A2a5437bF9152A1abfa08f0E83D0737C588C" - }, - "hardhat": { - "address": "0xCd17f01812099F7B76098f9bdCb93eC1DfDF24de" - } - }, - "strategyAAVE": { - "kovan": { - "address": "0xeD83FCcA01A74690c9d0Bc75283F612655347f67" - }, - "hardhat": { - "address": "0xDA01D05d5760bB3Af2C576CD57185557a267c2C8" - } - }, - "aBAT": { - "kovan": { - "address": "0x35bCbf4f3d63dC55b79178A423b0e601b4ef5FD2" - }, - "hardhat": { - "address": "0x99B8b2AE7Be6D3ed40B3e608c2dCd8a514736e3e" - } - }, - "strategyBAT": { - "kovan": { - "address": "0x277b52f138647392496355d87bF03a1aB6c83024" - }, - "hardhat": { - "address": "0x2923ce81A7Ce7903578eE6385D055123179a88f1" - } - }, - "aBUSD": { - "kovan": { - "address": "0x9E709c81c73eEcE90766B277babCfa66F1965565" - }, - "hardhat": { - "address": "0x6ac418d1b0B86c3AcBB397dd8F1c76578F3A9AD9" - } - }, - "strategyBUSD": { - "kovan": { - "address": "0xe302038c6E3f7541ACe4DcCF08D666F845450166" - }, - "hardhat": { - "address": "0xd8aa714b8acbD1287790C965f4b308a113EAD2F4" - } - }, - "aDAI": { - "kovan": { - "address": "0x9edb979F40cA59f759e9Eca68a6dFeA56B8d299b" - }, - "hardhat": { - "address": "0x511586d245EC3b29E9f36057E4609096d8e5AA41" - } - }, - "strategyDAI": { - "kovan": { - "address": "0xa43a28500d79C25bf83ACAF5E90a46b689b3EB16" - }, - "hardhat": { - "address": "0x4F772132fF40d9d48557791F336012FD5bfaEA4e" - } - }, - "stableDebtENJ": { - "kovan": { - "address": "0x9fBE02f08e79f8aA129a46a23E8A18e027B6e2EF" - }, - "hardhat": { - "address": "0xa2f3D52731D5E6F090af969D1dD5Cb90A3834831" - } - }, - "variableDebtENJ": { - "kovan": { - "address": "0xFA80B658A4bacD6282267428206Afaa3Cf888cd6" - }, - "hardhat": { - "address": "0x9085F5C3B91aD148f9638caC09F3B53Dff160637" - } - }, - "stableDebtKNC": { - "kovan": { - "address": "0xAF9EfC82E89a872F8AEf28c81258dfEa712AfFfE" - }, - "hardhat": { - "address": "0x287B0459469355C0c443C79e45cdB1573C5Abc84" - } - }, - "variableDebtKNC": { - "kovan": { - "address": "0xa371C49E252d3c11e050A47ff88d8D15cDf114A1" - }, - "hardhat": { - "address": "0x5deC984578799Af449aa0A9739449148195b14Ea" - } - }, - "stableDebtLINK": { - "kovan": { - "address": "0xdF0812bdf765E3b77746e961C501313083b1aFa5" - }, - "hardhat": { - "address": "0xe3d9664D2a80d269940EcE9a744DC263c6a6959c" - } - }, - "variableDebtLINK": { - "kovan": { - "address": "0x3f7389a4e2A351Fd9107d645108a6535Ed1232E4" - }, - "hardhat": { - "address": "0x3b957FdA3e67D732031d41F0B4B832dcCD7005f6" - } - }, - "stableDebtMANA": { - "kovan": { - "address": "0x217013C9bFE969979eB8efe94f3dfAeE35492C50" - }, - "hardhat": { - "address": "0x273da316D8209A827cBADC4Fc914bB96dCd88397" - } - }, - "variableDebtMANA": { - "kovan": { - "address": "0x5945e37b1ef058c5847b048786ac3fCdd40e56DE" - }, - "hardhat": { - "address": "0xF6c722853fCE2c70d41ecc10b5e0aafc0BE782A4" - } - }, - "aENJ": { - "kovan": { - "address": "0xc8fad67D303D8fCF6abe3206E4BF94D797Ef71f3" - }, - "hardhat": { - "address": "0xeC70C41A36347b85A86d837D309c8CaB1540F1A8" - } - }, - "strategyENJ": { - "kovan": { - "address": "0x537d2F788d0B598D5a921532D4086EDE3B2cEd64" - }, - "hardhat": { - "address": "0x3908cB82076E45f97b80a210DcE9eea96eFdc3b6" - } - }, - "aKNC": { - "kovan": { - "address": "0x49c9eC52427E9ccd13eF0702d5b2e028Ce99A217" - }, - "hardhat": { - "address": "0xdF089cd4C344c859b022861a68cD2EfEEB21Eabe" - } - }, - "strategyKNC": { - "kovan": { - "address": "0x1308fCd27933fF5639C9f51c86A17A3645c5dED9" - }, - "hardhat": { - "address": "0xF6062f926ed0e708338e095d200668a31DeeCa8b" - } - }, - "aLINK": { - "kovan": { - "address": "0x917e32953DA5eA01fb7FAEB90A19aeb51Cd42c23" - }, - "hardhat": { - "address": "0x96d73a1fD875b959Dc05Ea823fBE323107DaCF0B" - } - }, - "strategyLINK": { - "kovan": { - "address": "0xA891181D5dca4b6a8F5d2607E456CFa9EB9D1D20" - }, - "hardhat": { - "address": "0x660a606C9828a74335A4333eD9d59CAf5800f486" - } - }, - "aMANA": { - "kovan": { - "address": "0x2419b9D71F42D8C72176bA5C2c7bF152F0692814" - }, - "hardhat": { - "address": "0xC840F4f12c5137fc08b56EBa82b23DCdF8B5ACd6" - } - }, - "strategyMANA": { - "kovan": { - "address": "0x886e231f0ca34deF2dBf091AA5d6be4cFa06B557" - }, - "hardhat": { - "address": "0xc009500eC821635E6110d494B4f45404E5586c59" - } - }, - "stableDebtMKR": { - "kovan": { - "address": "0x2a8617F6802a1CCA29f2974837eaBD6630E80994" - }, - "hardhat": { - "address": "0x9FE70690a18bBe8265a03f416fADbFB8A1983fBc" - } - }, - "variableDebtMKR": { - "kovan": { - "address": "0xF75cC2a6C928198681D35c8117df83699189169D" - }, - "hardhat": { - "address": "0xDb03E85f8bc2297f29839417D9A1E1362E2dD516" - } - }, - "stableDebtREN": { - "kovan": { - "address": "0x598F59917d13269D8D81ab21Ea37F4B8e099e875" - }, - "hardhat": { - "address": "0xc9C2968e383122Bba7FC6E87a840CDB5dC257314" - } - }, - "variableDebtREN": { - "kovan": { - "address": "0x3140a105ede15FEc9391fef89e6d14b62B86C39B" - }, - "hardhat": { - "address": "0x502b8Cd8A84178af0bD80b07fC23ADe345E0a89f" - } - }, - "stableDebtREP": { - "kovan": { - "address": "0x33160b3737a1869264601C4B8D97e98725920c16" - }, - "hardhat": { - "address": "0x9BDdf2F48828A9AE0EB488269470a5300dd55cAc" - } - }, - "variableDebtREP": { - "kovan": { - "address": "0x995487BB75AEc2375fdB216BfcB37b53f6Ab2abb" - }, - "hardhat": { - "address": "0xb434965dA49C5eF410445b4dF574c80FF372502A" - } - }, - "stableDebtSNX": { - "kovan": { - "address": "0x77E8Addb01e36c5d754E89d0E5Da951e202d9CE3" - }, - "hardhat": { - "address": "0x840f25B7fCC0f976D2E046DE8ab322B1accA6662" - } - }, - "variableDebtSNX": { - "kovan": { - "address": "0x969e82694032cc0C346f855e52c5503B4e42F850" - }, - "hardhat": { - "address": "0xAA92017604D953d4Bd837d980e953c541746D904" - } - }, - "aMKR": { - "kovan": { - "address": "0xc3b70569D534C3E17B06C4a25980Ab349b534263" - }, - "hardhat": { - "address": "0x154f0e6086D1F3A777ED4B448045Cd3455Ddf40C" - } - }, - "strategyMKR": { - "kovan": { - "address": "0x81DB8B1f3612FdAAA7A211d073dB4C8dcc5a98e7" - }, - "hardhat": { - "address": "0xE1C312F55E129b4aAf96725C193e925849707BA4" - } - }, - "aREN": { - "kovan": { - "address": "0x2Bed39d993276E548987e4271475696897254a17" - }, - "hardhat": { - "address": "0x403cf75AC7F7e0F9caC1f715e2Ac36f6007245eE" - } - }, - "strategyREN": { - "kovan": { - "address": "0x49a4CDd903A6644cF696F7E1d4404BBBC973470E" - }, - "hardhat": { - "address": "0xf996E1e0E0B527a2A179461627d3fCF66A6b0151" - } - }, - "aREP": { - "kovan": { - "address": "0x04adf3717C2066cd338804909467e67C968B7Dd7" - }, - "hardhat": { - "address": "0x2A508C4DA298bF87f35027D6616b5478cC5c513A" - } - }, - "strategyREP": { - "kovan": { - "address": "0x5D271675dA68679DB9a8A8E3501cB7c21fd84cE3" - }, - "hardhat": { - "address": "0x99AD43CDc5C9aD99670d110d22700062a931b774" - } - }, - "aSNX": { - "kovan": { - "address": "0x023eba3646A08BA06CfCCB5c8F684048d1B654bb" - }, - "hardhat": { - "address": "0xC75e2508dE6d8000FA5C97A635F4f48C7632d6AE" - } - }, - "strategySNX": { - "kovan": { - "address": "0x866a1F54F13a00B9747C7832881a15234284D38C" - }, - "hardhat": { - "address": "0xDea1DFeb04663B7B752573E046000Ee92D1C88b0" - } - }, - "stableDebtSUSD": { - "kovan": { - "address": "0x5Eac7b30C376081f293d5671f1B4a789a36Ba8C8" - }, - "hardhat": { - "address": "0xB500f1089B97ca4E6e0E2F496164b2Bf40702D18" - } - }, - "variableDebtSUSD": { - "kovan": { - "address": "0x34939cC14762b4993E0679231ECE9aC51836c071" - }, - "hardhat": { - "address": "0xB8B80D64ecfA2e79BF0212a8afFa86006244c74E" - } - }, - "stableDebtTUSD": { - "kovan": { - "address": "0xc3031590B298aB7591a59e467c944215236f7878" - }, - "hardhat": { - "address": "0xA857e276492E727d43C8332F90190035fe2cdF51" - } - }, - "variableDebtTUSD": { - "kovan": { - "address": "0x1E913eCe8FFcC67d86671ba3Ae7676F385722941" - }, - "hardhat": { - "address": "0xE9519f1b2B639e151A3C353a169e7B1c8106A789" - } - }, - "stableDebtUNI": { - "kovan": { - "address": "0x6C9ee95b637c44322C6fA244D0106a52Dc2cB6F9" - }, - "hardhat": { - "address": "0x16BFD34a59eB0Be88Bb6Af55CADc0ad32c724790" - } - }, - "variableDebtUNI": { - "kovan": { - "address": "0xFEbef6B52C72A49CD8150284aD7277a7454373e0" - }, - "hardhat": { - "address": "0x280430db0fe64B7F8c6a946655eB6752A9d714C2" - } - }, - "stableDebtUSDC": { - "kovan": { - "address": "0xaD56D9738Aa70D518298c37Cd7C5Fc81ba987023" - }, - "hardhat": { - "address": "0x0178F3259271CFC416750AF6c4F4f51a27D96bA9" - } - }, - "variableDebtUSDC": { - "kovan": { - "address": "0x38CA9234844ADBceB823462CC8666569883b9701" - }, - "hardhat": { - "address": "0x2d0931CbCF4D2bC7f91b7535b2eC3070d8552CAb" - } - }, - "aSUSD": { - "kovan": { - "address": "0x6EFA6906A391B4F62914f6Ae4650aC2154f89bE7" - }, - "hardhat": { - "address": "0x947A23f8E7f7382249398f683649c866bad87AcF" - } - }, - "strategySUSD": { - "kovan": { - "address": "0x144E8b18609B2dF30AD96789Db5c6feb9259626c" - }, - "hardhat": { - "address": "0xAce0e9788475E7a4266B157061b7c4c0F7aF57CC" - } - }, - "aTUSD": { - "kovan": { - "address": "0x88ab5455013e2c00De2ABA5F48DEff10CFEDb490" - }, - "hardhat": { - "address": "0x60694Ca48F51f2D34f4De5c3Cc688d00fbB71764" - } - }, - "strategyTUSD": { - "kovan": { - "address": "0xF862594F5C4061ac21547A9868716e12f0B59AC2" - }, - "hardhat": { - "address": "0x69E9492f702fBc2016a79106C50f1FbF67AcB77e" - } - }, - "aUNI": { - "kovan": { - "address": "0x5aEE290afe3778d218DcD59C61A18Bacfa22bBae" - }, - "hardhat": { - "address": "0x0E716694fA09843eb70735c1AdA5E51b20BFcC79" - } - }, - "strategyUNI": { - "kovan": { - "address": "0x21Fe360f849358e991Ea60Bd5C7569598788f46A" - }, - "hardhat": { - "address": "0xb5363644Fe3cb5109Ac8e3f3F9632238BfF4B4c8" - } - }, - "aUSDC": { - "kovan": { - "address": "0x4E2e684aA8fB7E15c487F2d922508dBCfdAfC921" - }, - "hardhat": { - "address": "0xfA6D6657161749272e3f158cdb3Af4E03015A727" - } - }, - "strategyUSDC": { - "kovan": { - "address": "0x8480DFf825B99622d0598826F5EE3B5d79bA92c5" - }, - "hardhat": { - "address": "0x609BD7680Ce4c46A867c2A0f9229b75d5a872ace" - } - }, - "stableDebtUSDT": { - "kovan": { - "address": "0x953Ae6D846feB7112Be1DD0a2c996CD37c51f127" - }, - "hardhat": { - "address": "0x88413e3FcE7fE0c8186cC877A9Ee50FbFC5b3b4e" - } - }, - "variableDebtUSDT": { - "kovan": { - "address": "0x443005Fad27A870ED9BCF4B048FdD6b79a7d2B15" - }, - "hardhat": { - "address": "0x1b023f0D66ad7390ADA99D2C0334921E4f9eee69" - } - }, - "stableDebtWBTC": { - "kovan": { - "address": "0xa5E61884083c243345449eAD5c70158F016F4df0" - }, - "hardhat": { - "address": "0xBfD89FE99Af3CB7b20F3CbA7a30cd838d46252dF" - } - }, - "variableDebtWBTC": { - "kovan": { - "address": "0xFD5194F07E652865671b1a8310Ac54a853985547" - }, - "hardhat": { - "address": "0x480B773De09C464DFDaa1043726Bb84EA34C1987" - } - }, - "stableDebtWETH": { - "kovan": { - "address": "0xcb19776e2B69595b6a3Ce4F44acb63e506bd8C1b" - }, - "hardhat": { - "address": "0xC23CA88a9f2E4a2a2d4afe6D49736CD79d04bA08" - } - }, - "variableDebtWETH": { - "kovan": { - "address": "0x755d5C1a5d82f26a92dFb793d0Da14eEd8Ec7435" - }, - "hardhat": { - "address": "0x8afF291013736bEA113Bebfb764996bB8e6271Fc" - } - }, - "stableDebtYFI": { - "kovan": { - "address": "0xd72a6AdE1ba573DA8398ff05426B8450Daeaa3e7" - }, - "hardhat": { - "address": "0x48071298E6825f5F60912fb99689003164FCe076" - } - }, - "variableDebtYFI": { - "kovan": { - "address": "0xa0cE46eA00e4ccE66d93e8465DCEDE0f5470d2A4" - }, - "hardhat": { - "address": "0x926A933dd2682BeD5Bd286C49828f6b6Ab78dB55" - } - }, - "aUSDT": { - "kovan": { - "address": "0x5109D69A94c7754251567aD12E0096368f6abcE5" - }, - "hardhat": { - "address": "0x3bBffe72b3D6EDdC9fD1925609F627e925CdD838" - } - }, - "strategyUSDT": { - "kovan": { - "address": "0x35716131aA6957eEF88c476a6a7e5f3cb6e2B4be" - }, - "hardhat": { - "address": "0x1011a3a55701E4070b348B90F206e261098AA789" - } - }, - "aWBTC": { - "kovan": { - "address": "0xe53a364A541fC87eecab96365C4BC3b4BA7Ad55f" - }, - "hardhat": { - "address": "0x4bdd8891be6a517793E65CD4F7288CA1aCBa84A1" - } - }, - "strategyWBTC": { - "kovan": { - "address": "0xD1A6A373A52FddceD8Eb630A6c230f39a53C15Ca" - }, - "hardhat": { - "address": "0x4B6653DD25F515b32656158AC3960Bc4efbf9fe9" - } - }, - "aWETH": { - "kovan": { - "address": "0xcBb1352688efC3B5741B60545F0A79B62A629702" - }, - "hardhat": { - "address": "0x6a839181b299D1c527C93Bf09660268C519401eF" - } - }, - "strategyWETH": { - "kovan": { - "address": "0xE05AA3A5A5Db7085A5A69402b1f7C033e4BC73d7" - }, - "hardhat": { - "address": "0x72b28fA48A598FB2A09362ceB5983fac64EF4d9c" - } - }, - "aYFI": { - "kovan": { - "address": "0x0C26B8dD7c55c4d090FBCD96c135e12f542Aef83" - }, - "hardhat": { - "address": "0x2F8fB24A9B1809229F52d9b9943DCcD75a5Ac8CE" - } - }, - "strategyYFI": { - "kovan": { - "address": "0x4a26cc7002e3ca88D8d3f72b9b6e7C7C4bF8923c" - }, - "hardhat": { - "address": "0x893e62B2BD2d652DB343DF18e6413c23fefA198d" - } - }, - "stableDebtZRX": { - "kovan": { - "address": "0xBA1EFBca9B5b4C7718A4374ec29c1671D972118A" - }, - "hardhat": { - "address": "0xF7FA52f20131fA0e8648A2464892e98c60bD665c" - } - }, - "variableDebtZRX": { - "kovan": { - "address": "0xfdf0AF23449181c404C15d0aA80D1355DC3FA460" - }, - "hardhat": { - "address": "0x1F6A681C043EA0e1c179888570819B2B4A6DC309" - } - }, - "aZRX": { - "kovan": { - "address": "0x9952c8EbFf001915a504D3E2B54D3bFD205C104B" - }, - "hardhat": { - "address": "0x9B23e3f9114B54C90a5731c9edCea483e512B72B" - } - }, - "strategyZRX": { - "kovan": { - "address": "0x2944f4c8b54410b61D3b305651a93547D24d691f" - }, - "hardhat": { - "address": "0x095baE292EC3Fd8303187cAACEBDa8c92D685aEa" - } - } -} diff --git a/helpers/configuration.ts b/helpers/configuration.ts index bc9d317a..eb8ee372 100644 --- a/helpers/configuration.ts +++ b/helpers/configuration.ts @@ -109,7 +109,7 @@ export const getLendingRateOracles = (poolConfig: ICommonConfiguration) => { ReserveAssets, } = poolConfig; - const MAINNET_FORK = process.env.MAINNET_FORK; + const MAINNET_FORK = process.env.MAINNET_FORK === 'true'; const network = MAINNET_FORK ? 'main' : DRE.network.name; return filterMapBy(LendingRateOracleRatesCommon, (key) => Object.keys(ReserveAssets[network]).includes(key) diff --git a/helpers/contracts-helpers.ts b/helpers/contracts-helpers.ts index 6552fc31..04403524 100644 --- a/helpers/contracts-helpers.ts +++ b/helpers/contracts-helpers.ts @@ -22,7 +22,7 @@ export type MockTokenMap = {[symbol: string]: MintableERC20}; export const registerContractInJsonDb = async (contractId: string, contractInstance: Contract) => { const currentNetwork = DRE.network.name; - const MAINNET_FORK = process.env.MAINNET_FORK; + const MAINNET_FORK = process.env.MAINNET_FORK === 'true'; if (MAINNET_FORK || (currentNetwork !== 'hardhat' && !currentNetwork.includes('coverage'))) { console.log(`*** ${contractId} ***\n`); console.log(`Network: ${currentNetwork}`); @@ -134,7 +134,7 @@ export const getParamPerNetwork = ( {kovan, ropsten, main, buidlerevm, coverage, tenderlyMain}: iParamsPerNetwork, network: eEthereumNetwork ) => { - const MAINNET_FORK = process.env.MAINNET_FORK; + const MAINNET_FORK = process.env.MAINNET_FORK === 'true'; if (MAINNET_FORK) { return main; } diff --git a/package.json b/package.json index 8668f6a8..90598d9c 100644 --- a/package.json +++ b/package.json @@ -11,21 +11,17 @@ "hardhat:main": "hardhat --network main", "hardhat:docker": "hardhat --network hardhatevm_docker", "compile": "SKIP_LOAD=true hardhat compile", - "test": "SKIP_LOAD=true TS_NODE_TRANSPILE_ONLY=1 hardhat test", + "test": "TS_NODE_TRANSPILE_ONLY=1 hardhat test ./test/*.spec.ts", "test-scenarios": "npm run test -- test/__setup.spec.ts test/scenario.spec.ts", "aave:evm:dev:migration": "hardhat aave:dev", - "aave:evm:full:migration": "hardhat aave:full", - "aave:docker:dev:migration": "npm run hardhat:docker -- aave:dev", "aave:docker:full:migration": "npm run hardhat:docker -- aave:full", - "aave:kovan:dev:migration": "npm run hardhat:kovan -- aave:dev --verify", "aave:kovan:full:migration": "npm run hardhat:kovan -- aave:full --verify", "aave:kovan:full:initialize": "npm run hardhat:kovan -- full:initialize-lending-pool --verify --pool Aave", - "aave:ropsten:dev:migration": "npm run hardhat:ropsten -- aave:dev --verify", "aave:ropsten:full:migration": "npm run hardhat:ropsten -- aave:full --verify", - "aave:fork:main:tenderly": "npm run hardhat:tenderly-main -- aave:full:fork", - "aave:fork:main": "MAINNET_FORK=true hardhat aave:full:fork", - "aave:main:dev:migration": "npm run hardhat:main -- aave:dev --verify", - "aave:main:full:migration": "npm run hardhat:main -- aave:full --verify", + "aave:fork:main:tenderly": "npm run hardhat:tenderly-main -- aave:mainnet", + "aave:fork:main": "MAINNET_FORK=true hardhat aave:mainnet", + "test:main:check-list": "MAINNET_FORK=true TS_NODE_TRANSPILE_ONLY=1 hardhat test test/__setup.spec.ts test/mainnet/check-list.spec.ts", + "aave:main:full:migration": "npm run hardhat:main -- aave:mainnet --verify", "uniswap:evm:dev:migration": "hardhat uniswap:dev", "uniswap:evm:full:migration": "hardhat uniswap:full --verify", "uniswap:kovan:dev:migration": "npm run hardhat:kovan -- uniswap:dev --verify", diff --git a/tasks/full/1_address_provider.ts b/tasks/full/1_address_provider.ts index 01485056..2397ea46 100644 --- a/tasks/full/1_address_provider.ts +++ b/tasks/full/1_address_provider.ts @@ -20,10 +20,10 @@ task( ) .addFlag('verify', 'Verify contracts at Etherscan') .addParam('pool', `Pool name to retrieve configuration, supported: ${Object.values(ConfigNames)}`) - .setAction(async ({verify, pool}, localBRE) => { - await localBRE.run('set-DRE'); - console.log('addresses', await getEthersSignersAddresses()); - const network = localBRE.network.name; + .setAction(async ({verify, pool}, DRE) => { + await DRE.run('set-DRE'); + + const network = DRE.network.name; const poolConfig = loadPoolConfig(pool); const {ProviderId} = poolConfig; @@ -31,7 +31,6 @@ task( // Deploy address provider and set genesis manager const addressesProvider = await deployLendingPoolAddressesProvider(verify); - console.log('prox', addressesProvider.address); await waitForTx(await addressesProvider.setPoolAdmin(await getGenesisPoolAdmin(poolConfig))); await waitForTx(await addressesProvider.setEmergencyAdmin(await getEmergencyAdmin(poolConfig))); diff --git a/tasks/full/2_lending_pool.ts b/tasks/full/2_lending_pool.ts index c0b4bc19..342d5365 100644 --- a/tasks/full/2_lending_pool.ts +++ b/tasks/full/2_lending_pool.ts @@ -23,16 +23,13 @@ task('full:deploy-lending-pool', 'Deploy lending pool for dev enviroment') try { await DRE.run('set-DRE'); - console.log('addresses', await getEthersSignersAddresses()); const addressesProvider = await getLendingPoolAddressesProvider(); // Deploy lending pool const lendingPoolImpl = await deployLendingPool(verify); - console.log('set lend poool', addressesProvider.address); // Set lending pool impl to address provider await waitForTx(await addressesProvider.setLendingPoolImpl(lendingPoolImpl.address)); - console.log('setted'); const address = await addressesProvider.getLendingPool(); const lendingPoolProxy = await getLendingPool(address); diff --git a/tasks/full/3_oracles.ts b/tasks/full/3_oracles.ts index fa569c66..16049d4b 100644 --- a/tasks/full/3_oracles.ts +++ b/tasks/full/3_oracles.ts @@ -27,7 +27,6 @@ task('full:deploy-oracles', 'Deploy oracles for dev enviroment') .addParam('pool', `Pool name to retrieve configuration, supported: ${Object.values(ConfigNames)}`) .setAction(async ({verify, pool}, DRE) => { try { - console.log('addresses', await getEthersSignersAddresses()); await DRE.run('set-DRE'); const network = DRE.network.name; const poolConfig = loadPoolConfig(pool); @@ -64,12 +63,6 @@ task('full:deploy-oracles', 'Deploy oracles for dev enviroment') const {USD, ...tokensAddressesWithoutUsd} = tokensToWatch; if (!lendingRateOracleAddress) { - console.log( - lendingRateOracles, - tokensAddressesWithoutUsd, - lendingRateOracle.address, - aggregators - ); await setInitialMarketRatesInRatesOracleByHelper( lendingRateOracles, tokensAddressesWithoutUsd, diff --git a/tasks/migrations/aave.full.ts b/tasks/migrations/aave.full.ts index 203c01f8..731984a3 100644 --- a/tasks/migrations/aave.full.ts +++ b/tasks/migrations/aave.full.ts @@ -25,7 +25,10 @@ task('aave:full', 'Deploy development enviroment') console.log('2. Deploy lending pool'); await localBRE.run('full:deploy-lending-pool'); - console.log('3. Initialize lending pool'); + console.log('3. Deploy data provider'); + await localBRE.run('full:data-provider'); + + console.log('4. Initialize lending pool'); await localBRE.run('full:initialize-lending-pool', {pool: POOL_NAME}); if (verify) { diff --git a/tasks/migrations/aave.mainnet.ts b/tasks/migrations/aave.mainnet.ts index d5ff76ac..c8ae5430 100644 --- a/tasks/migrations/aave.mainnet.ts +++ b/tasks/migrations/aave.mainnet.ts @@ -5,7 +5,7 @@ import {ConfigNames} from '../../helpers/configuration'; import {EthereumNetworkNames} from '../../helpers/types'; import {printContracts} from '../../helpers/misc-utils'; -task('aave:full:fork', 'Deploy development enviroment') +task('aave:mainnet', 'Deploy development enviroment') .addFlag('verify', 'Verify contracts at Etherscan') .setAction(async ({verify}, DRE) => { const POOL_NAME = ConfigNames.Aave; @@ -17,7 +17,6 @@ task('aave:full:fork', 'Deploy development enviroment') checkVerification(); } - // Set the ethers provider to the one we initialized so it targets the correct backend if (network.includes('tenderly')) { console.log('- Setting up Tenderly provider'); await DRE.tenderlyRPC.initializeFork(); @@ -36,7 +35,10 @@ task('aave:full:fork', 'Deploy development enviroment') console.log('3. Deploy oracles'); await DRE.run('full:deploy-oracles', {pool: POOL_NAME}); - console.log('4. Initialize lending pool'); + console.log('4. Deploy Data Provider'); + await DRE.run('full:data-provider', {pool: POOL_NAME}); + + console.log('5. Initialize lending pool'); await DRE.run('full:initialize-lending-pool', {pool: POOL_NAME}); if (verify) { diff --git a/test/__setup.spec.ts b/test/__setup.spec.ts index 559a8d08..cbce40a9 100644 --- a/test/__setup.spec.ts +++ b/test/__setup.spec.ts @@ -273,8 +273,15 @@ const buildTestEnv = async (deployer: Signer, secondaryWallet: Signer) => { before(async () => { await rawBRE.run('set-DRE'); const [deployer, secondaryWallet] = await getEthersSigners(); - console.log('-> Deploying test environment...'); - await buildTestEnv(deployer, secondaryWallet); + const MAINNET_FORK = process.env.MAINNET_FORK === 'true'; + + if (MAINNET_FORK) { + await rawBRE.run('aave:mainnet'); + } else { + console.log('-> Deploying test environment...'); + await buildTestEnv(deployer, secondaryWallet); + } + await initializeMakeSuite(); console.log('\n***************'); console.log('Setup and snapshot finished'); diff --git a/test/helpers/make-suite.ts b/test/helpers/make-suite.ts index cd927c5b..ec4f5533 100644 --- a/test/helpers/make-suite.ts +++ b/test/helpers/make-suite.ts @@ -106,14 +106,17 @@ export async function initializeMakeSuite() { testEnv.helpersContract = await getAaveProtocolDataProvider(); + console.log('het cpmtra'); const allTokens = await testEnv.helpersContract.getAllATokens(); - + console.log('tokann'); const aDaiAddress = allTokens.find((aToken) => aToken.symbol === 'aDAI')?.tokenAddress; const aWEthAddress = allTokens.find((aToken) => aToken.symbol === 'aWETH')?.tokenAddress; + console.log('priah'); const reservesTokens = await testEnv.helpersContract.getAllReservesTokens(); + console.log('all tokan'); const daiAddress = reservesTokens.find((token) => token.symbol === 'DAI')?.tokenAddress; const usdcAddress = reservesTokens.find((token) => token.symbol === 'USDC')?.tokenAddress; const aaveAddress = reservesTokens.find((token) => token.symbol === 'AAVE')?.tokenAddress; @@ -136,6 +139,7 @@ export async function initializeMakeSuite() { testEnv.aave = await getMintableErc20(aaveAddress); testEnv.weth = await getWETHMocked(wethAddress); testEnv.wethGateway = await getWETHGateway(); + console.log('laa'); } export function makeSuite(name: string, tests: (testEnv: TestEnv) => void) { diff --git a/test/mainnet/check-list.spec.ts b/test/mainnet/check-list.spec.ts new file mode 100644 index 00000000..08416eda --- /dev/null +++ b/test/mainnet/check-list.spec.ts @@ -0,0 +1,362 @@ +import {MAX_UINT_AMOUNT} from '../../helpers/constants'; +import {convertToCurrencyDecimals} from '../../helpers/contracts-helpers'; +import {makeSuite, TestEnv} from '../helpers/make-suite'; +import {parseEther} from 'ethers/lib/utils'; +import {DRE, waitForTx} from '../../helpers/misc-utils'; +import {BigNumber} from 'ethers'; +import {getStableDebtToken, getVariableDebtToken} from '../../helpers/contracts-getters'; +import {deploySelfdestructTransferMock} from '../../helpers/contracts-deployments'; +import {IUniswapV2Router02Factory} from '../../types/IUniswapV2Router02Factory'; + +const {expect} = require('chai'); + +const UNISWAP_ROUTER = '0x7a250d5630B4cF539739dF2C5dAcb4c659F2488D'; + +makeSuite('Mainnet Check list', (testEnv: TestEnv) => { + const zero = BigNumber.from('0'); + const depositSize = parseEther('5'); + + it('Deposit WETH', async () => { + const {users, wethGateway, aWETH, pool} = testEnv; + + const user = users[1]; + + // Deposit with native ETH + await wethGateway.connect(user.signer).depositETH(user.address, '0', {value: depositSize}); + + const aTokensBalance = await aWETH.balanceOf(user.address); + + expect(aTokensBalance).to.be.gt(zero); + expect(aTokensBalance).to.be.gte(depositSize); + }); + + it('Withdraw WETH - Partial', async () => { + const {users, wethGateway, aWETH, pool} = testEnv; + + const user = users[1]; + const priorEthersBalance = await user.signer.getBalance(); + const aTokensBalance = await aWETH.balanceOf(user.address); + + expect(aTokensBalance).to.be.gt(zero, 'User should have aTokens.'); + + // Partially withdraw native ETH + const partialWithdraw = await convertToCurrencyDecimals(aWETH.address, '2'); + + // Approve the aTokens to Gateway so Gateway can withdraw and convert to Ether + const approveTx = await aWETH + .connect(user.signer) + .approve(wethGateway.address, MAX_UINT_AMOUNT); + const {gasUsed: approveGas} = await waitForTx(approveTx); + + // Partial Withdraw and send native Ether to user + const {gasUsed: withdrawGas} = await waitForTx( + await wethGateway.connect(user.signer).withdrawETH(partialWithdraw, user.address) + ); + + const afterPartialEtherBalance = await user.signer.getBalance(); + const afterPartialATokensBalance = await aWETH.balanceOf(user.address); + const gasCosts = approveGas.add(withdrawGas).mul(approveTx.gasPrice); + + expect(afterPartialEtherBalance).to.be.equal( + priorEthersBalance.add(partialWithdraw).sub(gasCosts), + 'User ETHER balance should contain the partial withdraw' + ); + expect(afterPartialATokensBalance).to.be.equal( + aTokensBalance.sub(partialWithdraw), + 'User aWETH balance should be substracted' + ); + }); + + it('Withdraw WETH - Full', async () => { + const {users, aWETH, wethGateway, pool} = testEnv; + + const user = users[1]; + const priorEthersBalance = await user.signer.getBalance(); + const aTokensBalance = await aWETH.balanceOf(user.address); + + expect(aTokensBalance).to.be.gt(zero, 'User should have aTokens.'); + + // Approve the aTokens to Gateway so Gateway can withdraw and convert to Ether + const approveTx = await aWETH + .connect(user.signer) + .approve(wethGateway.address, MAX_UINT_AMOUNT); + const {gasUsed: approveGas} = await waitForTx(approveTx); + + // Full withdraw + const {gasUsed: withdrawGas} = await waitForTx( + await wethGateway.connect(user.signer).withdrawETH(MAX_UINT_AMOUNT, user.address) + ); + + const afterFullEtherBalance = await user.signer.getBalance(); + const afterFullATokensBalance = await aWETH.balanceOf(user.address); + const gasCosts = approveGas.add(withdrawGas).mul(approveTx.gasPrice); + + expect(afterFullEtherBalance).to.be.eq( + priorEthersBalance.add(aTokensBalance).sub(gasCosts), + 'User ETHER balance should contain the full withdraw' + ); + expect(afterFullATokensBalance).to.be.eq(0, 'User aWETH balance should be zero'); + }); + + it('Borrow stable WETH and Full Repay with ETH', async () => { + const {users, wethGateway, aWETH, weth, pool, helpersContract} = testEnv; + const borrowSize = parseEther('1'); + const repaySize = borrowSize.add(borrowSize.mul(5).div(100)); + const user = users[1]; + + const {stableDebtTokenAddress} = await helpersContract.getReserveTokensAddresses(weth.address); + + const stableDebtToken = await getStableDebtToken(stableDebtTokenAddress); + + // Deposit with native ETH + await wethGateway.connect(user.signer).depositETH(user.address, '0', {value: depositSize}); + + const aTokensBalance = await aWETH.balanceOf(user.address); + + expect(aTokensBalance).to.be.gt(zero); + expect(aTokensBalance).to.be.gte(depositSize); + + // Borrow WETH with WETH as collateral + await waitForTx( + await pool.connect(user.signer).borrow(weth.address, borrowSize, '1', '0', user.address) + ); + + const debtBalance = await stableDebtToken.balanceOf(user.address); + + expect(debtBalance).to.be.gt(zero); + + // Full Repay WETH with native ETH + await waitForTx( + await wethGateway + .connect(user.signer) + .repayETH(MAX_UINT_AMOUNT, '1', user.address, {value: repaySize}) + ); + + const debtBalanceAfterRepay = await stableDebtToken.balanceOf(user.address); + expect(debtBalanceAfterRepay).to.be.eq(zero); + }); + + it('Borrow variable WETH and Full Repay with ETH', async () => { + const {users, wethGateway, aWETH, weth, pool, helpersContract} = testEnv; + const borrowSize = parseEther('1'); + const repaySize = borrowSize.add(borrowSize.mul(5).div(100)); + const user = users[1]; + + const {variableDebtTokenAddress} = await helpersContract.getReserveTokensAddresses( + weth.address + ); + + const varDebtToken = await getVariableDebtToken(variableDebtTokenAddress); + + // Deposit with native ETH + await wethGateway.connect(user.signer).depositETH(user.address, '0', {value: depositSize}); + + const aTokensBalance = await aWETH.balanceOf(user.address); + + expect(aTokensBalance).to.be.gt(zero); + expect(aTokensBalance).to.be.gte(depositSize); + + // Borrow WETH with WETH as collateral + await waitForTx( + await pool.connect(user.signer).borrow(weth.address, borrowSize, '2', '0', user.address) + ); + + const debtBalance = await varDebtToken.balanceOf(user.address); + + expect(debtBalance).to.be.gt(zero); + + // Partial Repay WETH loan with native ETH + const partialPayment = repaySize.div(2); + await waitForTx( + await wethGateway + .connect(user.signer) + .repayETH(partialPayment, '2', user.address, {value: partialPayment}) + ); + + const debtBalanceAfterPartialRepay = await varDebtToken.balanceOf(user.address); + expect(debtBalanceAfterPartialRepay).to.be.lt(debtBalance); + + // Full Repay WETH loan with native ETH + await waitForTx( + await wethGateway + .connect(user.signer) + .repayETH(MAX_UINT_AMOUNT, '2', user.address, {value: repaySize}) + ); + const debtBalanceAfterFullRepay = await varDebtToken.balanceOf(user.address); + expect(debtBalanceAfterFullRepay).to.be.eq(zero); + }); + + it('Borrow ETH via delegateApprove ETH and repays back', async () => { + const {users, wethGateway, aWETH, weth, helpersContract} = testEnv; + const borrowSize = parseEther('1'); + const user = users[2]; + const {variableDebtTokenAddress} = await helpersContract.getReserveTokensAddresses( + weth.address + ); + const varDebtToken = await getVariableDebtToken(variableDebtTokenAddress); + + const priorDebtBalance = await varDebtToken.balanceOf(user.address); + expect(priorDebtBalance).to.be.eq(zero); + + // Deposit WETH with native ETH + await wethGateway.connect(user.signer).depositETH(user.address, '0', {value: depositSize}); + + const aTokensBalance = await aWETH.balanceOf(user.address); + + expect(aTokensBalance).to.be.gt(zero); + expect(aTokensBalance).to.be.gte(depositSize); + + // Delegates borrowing power of WETH to WETHGateway + await waitForTx( + await varDebtToken.connect(user.signer).approveDelegation(wethGateway.address, borrowSize) + ); + + // Borrows ETH with WETH as collateral + await waitForTx(await wethGateway.connect(user.signer).borrowETH(borrowSize, '2', '0')); + + const debtBalance = await varDebtToken.balanceOf(user.address); + + expect(debtBalance).to.be.gt(zero); + + // Full Repay WETH loan with native ETH + await waitForTx( + await wethGateway + .connect(user.signer) + .repayETH(MAX_UINT_AMOUNT, '2', user.address, {value: borrowSize.mul(2)}) + ); + const debtBalanceAfterFullRepay = await varDebtToken.balanceOf(user.address); + expect(debtBalanceAfterFullRepay).to.be.eq(zero); + }); + + it('Should revert if receiver function receives Ether if not WETH', async () => { + const {users, wethGateway} = testEnv; + const user = users[0]; + const amount = parseEther('1'); + + // Call receiver function (empty data + value) + await expect( + user.signer.sendTransaction({ + to: wethGateway.address, + value: amount, + gasLimit: DRE.network.config.gas, + }) + ).to.be.revertedWith('Receive not allowed'); + }); + + it('Should revert if fallback functions is called with Ether', async () => { + const {users, wethGateway} = testEnv; + const user = users[0]; + const amount = parseEther('1'); + const fakeABI = ['function wantToCallFallback()']; + const abiCoder = new DRE.ethers.utils.Interface(fakeABI); + const fakeMethodEncoded = abiCoder.encodeFunctionData('wantToCallFallback', []); + + // Call fallback function with value + await expect( + user.signer.sendTransaction({ + to: wethGateway.address, + data: fakeMethodEncoded, + value: amount, + gasLimit: DRE.network.config.gas, + }) + ).to.be.revertedWith('Fallback not allowed'); + }); + + it('Should revert if fallback functions is called', async () => { + const {users, wethGateway} = testEnv; + const user = users[0]; + + const fakeABI = ['function wantToCallFallback()']; + const abiCoder = new DRE.ethers.utils.Interface(fakeABI); + const fakeMethodEncoded = abiCoder.encodeFunctionData('wantToCallFallback', []); + + // Call fallback function without value + await expect( + user.signer.sendTransaction({ + to: wethGateway.address, + data: fakeMethodEncoded, + gasLimit: DRE.network.config.gas, + }) + ).to.be.revertedWith('Fallback not allowed'); + }); + + it('Getters should retrieve correct state', async () => { + const {aWETH, weth, pool, wethGateway} = testEnv; + + const WETHAddress = await wethGateway.getWETHAddress(); + const aWETHAddress = await wethGateway.getAWETHAddress(); + const poolAddress = await wethGateway.getLendingPoolAddress(); + + expect(WETHAddress).to.be.equal(weth.address); + expect(aWETHAddress).to.be.equal(aWETH.address); + expect(poolAddress).to.be.equal(pool.address); + }); + + it('Owner can do emergency token recovery', async () => { + const {users, weth, dai, wethGateway, deployer} = testEnv; + const user = users[0]; + const amount = parseEther('1'); + + const uniswapRouter = IUniswapV2Router02Factory.connect(UNISWAP_ROUTER, user.signer); + await uniswapRouter.swapETHForExactTokens( + amount, // 1 DAI + [weth.address, dai.address], // Uniswap paths WETH - DAI + user.address, + (await DRE.ethers.provider.getBlock('latest')).timestamp + 300, + { + value: amount, // 1 Ether, we get refund of the unneeded Ether to buy 1 DAI + } + ); + const daiBalanceAfterMint = await dai.balanceOf(user.address); + + await dai.connect(user.signer).transfer(wethGateway.address, amount); + const daiBalanceAfterBadTransfer = await dai.balanceOf(user.address); + expect(daiBalanceAfterBadTransfer).to.be.eq( + daiBalanceAfterMint.sub(amount), + 'User should have lost the funds here.' + ); + + await wethGateway + .connect(deployer.signer) + .emergencyTokenTransfer(dai.address, user.address, amount); + const daiBalanceAfterRecovery = await dai.balanceOf(user.address); + + expect(daiBalanceAfterRecovery).to.be.eq( + daiBalanceAfterMint, + 'User should recover the funds due emergency token transfer' + ); + }); + + it('Owner can do emergency native ETH recovery', async () => { + const {users, wethGateway, deployer} = testEnv; + const user = users[0]; + const amount = parseEther('1'); + const userBalancePriorCall = await user.signer.getBalance(); + + // Deploy contract with payable selfdestruct contract + const selfdestructContract = await deploySelfdestructTransferMock(); + + // Selfdestruct the mock, pointing to WETHGateway address + const callTx = await selfdestructContract + .connect(user.signer) + .destroyAndTransfer(wethGateway.address, {value: amount}); + const {gasUsed} = await waitForTx(callTx); + const gasFees = gasUsed.mul(callTx.gasPrice); + const userBalanceAfterCall = await user.signer.getBalance(); + + expect(userBalanceAfterCall).to.be.eq(userBalancePriorCall.sub(amount).sub(gasFees), ''); + 'User should have lost the funds'; + + // Recover the funds from the contract and sends back to the user + await wethGateway.connect(deployer.signer).emergencyEtherTransfer(user.address, amount); + + const userBalanceAfterRecovery = await user.signer.getBalance(); + const wethGatewayAfterRecovery = await DRE.ethers.provider.getBalance(wethGateway.address); + + expect(userBalanceAfterRecovery).to.be.eq( + userBalancePriorCall.sub(gasFees), + 'User should recover the funds due emergency eth transfer.' + ); + expect(wethGatewayAfterRecovery).to.be.eq('0', 'WETHGateway ether balance should be zero.'); + }); +});