├── .circleci
├── check_npm_version.sh
└── config.yml
├── .env.example
├── .gitattributes
├── .gitignore
├── LICENSE
├── README.md
├── assets
├── legos-autocomplete.gif
└── weight.png
├── docs
├── .nojekyll
├── README.md
├── _sidebar.md
├── aave.md
├── balancer.md
├── compound.md
├── curvefi.md
├── dydx.md
├── idle.md
├── index.html
├── kyber.md
├── maker.md
├── material-oceanic.css
├── mstable.md
├── onesplit.md
├── overview_mainnet_address.md
├── quickstart.md
├── synthetix.md
├── uniswap.md
└── uniswapV2.md
├── jest.config.js
├── package-lock.json
├── package.json
├── scripts
├── genAddrMainnetOverview.js
└── getAbisFromUMA.js
├── src
├── aave
│ ├── abi
│ │ ├── AToken.json
│ │ ├── LendingPool.json
│ │ ├── LendingPoolAddessProvider.json
│ │ └── LendingPoolCore.json
│ ├── contracts.ts
│ ├── contracts
│ │ ├── FlashloanReceiverBase.sol
│ │ ├── IFlashLoanReceiver.sol
│ │ ├── ILendingPool.sol
│ │ └── ILendingPoolAddressesProvider.sol
│ └── index.ts
├── balancer
│ ├── abi
│ │ ├── BActions.json
│ │ ├── BFactory.json
│ │ ├── BPool.json
│ │ └── ExchangeProxy.json
│ ├── contracts.ts
│ ├── contracts
│ │ ├── BFactory.sol
│ │ ├── BPool.sol
│ │ └── ExchangeProxy.sol
│ └── index.ts
├── compound
│ ├── README.md
│ ├── abi
│ │ ├── CEther.json
│ │ ├── CToken.json
│ │ ├── CompoundPriceOracle.json
│ │ └── Comptroller.json
│ ├── contracts.ts
│ ├── contracts
│ │ ├── ICEther.sol
│ │ ├── ICToken.sol
│ │ ├── ICompoundPriceOracle.sol
│ │ └── IComptroller.sol
│ └── index.ts
├── curvefi
│ ├── abi
│ │ ├── Curve.json
│ │ ├── PoolToken.json
│ │ └── Zap.json
│ ├── contracts.ts
│ ├── contracts
│ │ ├── ICurveFiCurve.sol
│ │ ├── ICurveFiPoolToken.sol
│ │ └── ICurveFiZap.sol
│ └── index.ts
├── dappsys
│ ├── abi
│ │ ├── DSProxy.json
│ │ └── DSProxyFactory.json
│ ├── contracts.ts
│ └── index.ts
├── dydx
│ ├── abi
│ │ ├── AdminImpl.json
│ │ ├── CanonicalOrders.json
│ │ ├── DaiPriceOracle.json
│ │ ├── Expiry.json
│ │ ├── ExpiryV2.json
│ │ ├── LimitOrders.json
│ │ ├── LiquidatorProxyV1ForSoloMargin.json
│ │ ├── OperationImpl.json
│ │ ├── PayableProxyForSoloMargin.json
│ │ ├── PolynomialInterestSetter.json
│ │ ├── Refunder.json
│ │ ├── SaiPriceOracle.json
│ │ ├── SignedOperationProxy.json
│ │ ├── SoloMargin.json
│ │ ├── StopLimitOrders.json
│ │ ├── UsdcPriceOracle.json
│ │ └── WethPriceOracle.json
│ ├── contracts.ts
│ ├── contracts
│ │ ├── DydxFlashloanBase.sol
│ │ ├── ICallee.sol
│ │ └── ISoloMargin.sol
│ └── index.ts
├── erc20
│ ├── README.md
│ ├── abi
│ │ ├── ERC20.json
│ │ └── WETH.json
│ ├── index.ts
│ └── tokens.ts
├── idle
│ ├── abi
│ │ └── IdleTokenV3.json
│ ├── contracts.ts
│ └── index.ts
├── index.ts
├── kyber
│ ├── abi
│ │ └── KyberNetworkProxy.json
│ ├── contracts.ts
│ ├── contracts
│ │ └── KyberNetworkProxy.sol
│ └── index.ts
├── maker
│ ├── abi
│ │ ├── DssCdpManager.json
│ │ ├── DssProxyActions.json
│ │ ├── Medianizer.json
│ │ └── ProxyRegistry.json
│ ├── contracts.ts
│ ├── contracts
│ │ ├── DssProxyActionsBase.sol
│ │ ├── IDssProxyActions.sol
│ │ └── IMedianizer.sol
│ ├── ilks.ts
│ ├── index.ts
│ └── priceFeeds.ts
├── mstable
│ ├── abi
│ │ ├── AaveIntegration.json
│ │ ├── BasketManager.json
│ │ ├── CompoundIntegration.json
│ │ ├── DelayedProxyAdmin.json
│ │ ├── ForgeValidator.json
│ │ ├── Masset.json
│ │ ├── MassetValidationHelper.json
│ │ ├── MetaToken.json
│ │ ├── Nexus.json
│ │ ├── RewardsDistributor.json
│ │ ├── SavingsContract.json
│ │ ├── SavingsManager.json
│ │ └── StakingRewardsWithPlatformToken.json
│ ├── contracts.ts
│ ├── contracts
│ │ ├── Masset.sol
│ │ └── StakingRewardsWithPlatformToken.sol
│ └── index.ts
├── onesplit
│ ├── abi
│ │ └── OneSplit.json
│ ├── contracts.ts
│ ├── contracts
│ │ └── IOneSplit.sol
│ └── index.ts
├── synthetix
│ ├── abi
│ │ ├── Depot.json
│ │ ├── ExchangeRates.json
│ │ ├── Exchanger.json
│ │ ├── ProxyERC20.json
│ │ ├── Synth.json
│ │ └── Synthetix.json
│ ├── contracts.ts
│ ├── contracts
│ │ ├── IDepot.sol
│ │ ├── ISynth.sol
│ │ └── ISynthetix.sol
│ └── index.ts
├── uma
│ ├── abi
│ │ ├── AddressWhitelist.json
│ │ ├── DesignatedVotingFactory.json
│ │ ├── ExpiringMultiParty.json
│ │ ├── ExpiringMultiPartyCreator.json
│ │ ├── ExpiringMultiPartyLib.json
│ │ ├── FinancialContractsAdmin.json
│ │ ├── Finder.json
│ │ ├── Governor.json
│ │ ├── IdentifierWhitelist.json
│ │ ├── Registry.json
│ │ ├── Store.json
│ │ ├── TokenFactory.json
│ │ ├── Voting.json
│ │ ├── VotingToken.json
│ │ └── WETH9.json
│ ├── contracts.ts
│ └── index.ts
├── uniswap
│ ├── abi
│ │ ├── Exchange.json
│ │ └── Factory.json
│ ├── contracts.ts
│ ├── contracts
│ │ ├── IUniswapExchange.sol
│ │ └── IUniswapFactory.sol
│ └── index.ts
└── uniswapV2
│ ├── abi
│ ├── IUniswapV2Factory.json
│ ├── IUniswapV2Pair.json
│ ├── IUniswapV2Router01.json
│ └── IUniswapV2Router02.json
│ ├── contracts.ts
│ ├── contracts
│ ├── IUniswapV2Factory.sol
│ ├── IUniswapV2Pair.sol
│ ├── IUniswapV2Router01.sol
│ └── IUniswapV2Router02.sol
│ └── index.ts
├── tests
├── aave.test.sol
├── aave.test.ts
├── balancer.test.ts
├── compound.test.sol
├── compound.test.ts
├── index.test.ts
├── kyber.test.sol
├── kyber.test.ts
├── maker.test.ts
├── medianizer.test.ts
├── mstable.test.ts
├── synthetix.test.ts
├── test-environment.js
├── uniswap.test.ts
├── uniswapV2.test.ts
└── utils.ts
├── tsconfig.json
└── yarn.lock
/.circleci/check_npm_version.sh:
--------------------------------------------------------------------------------
1 | #!/bin/bash
2 |
3 | set -o verbose
4 | set -v
5 |
6 | # https://stackoverflow.com/a/29394504/4634583
7 | # Compare semvar easily (this support 3 fields at most)
8 | function ver { printf "%03d%03d%03d" $(echo "$1" | tr '.' ' '); }
9 |
10 | PUBLISHED_PACKAGE_VER=$(npm view @studydefi/money-legos version)
11 | CURRENT_PACKAGE_VER=$(node -p "require('./package.json').version")
12 |
13 | if [[ $((10#$(ver $CURRENT_PACKAGE_VER))) -le $((10#$(ver $PUBLISHED_PACKAGE_VER))) ]]; then
14 | echo "Invalid package version"
15 | exit 1
16 | fi
17 |
--------------------------------------------------------------------------------
/.circleci/config.yml:
--------------------------------------------------------------------------------
1 | defaults: &defaults
2 | working_directory: ~/repo
3 | docker:
4 | - image: circleci/node:lts
5 |
6 | jobs:
7 | build:
8 | <<: *defaults
9 | steps:
10 | - checkout
11 |
12 | - restore_cache:
13 | name: Restore Yarn Package Cache
14 | keys:
15 | - yarn-packages-{{ checksum "yarn.lock" }}
16 |
17 | - run:
18 | name: Install Dependencies
19 | command: yarn install --frozen-lockfile
20 |
21 | - run:
22 | name: Run Tests
23 | command: yarn test
24 |
25 | - run:
26 | name: Build Project
27 | command: yarn build
28 |
29 | - save_cache:
30 | name: Save Yarn Package Cache
31 | key: yarn-packages-{{ checksum "yarn.lock" }}
32 | paths:
33 | - ~/.cache/yarn
34 |
35 | - persist_to_workspace:
36 | root: ~/repo
37 | paths: .
38 |
39 | publishDryRun:
40 | <<: *defaults
41 | steps:
42 | - attach_workspace:
43 | at: ~/repo
44 |
45 | - run:
46 | name: Check Package Version Valid on NPM
47 | command: ./.circleci/check_npm_version.sh
48 |
49 | publish:
50 | <<: *defaults
51 | steps:
52 | - attach_workspace:
53 | at: ~/repo
54 | - run:
55 | name: Authenticate with registry
56 | command: echo "//registry.npmjs.org/:_authToken=$npm_TOKEN" > ~/.npmrc
57 | - run:
58 | name: Publish package
59 | command: |
60 | # Sometimes we just wanna update the readme file
61 | if ./.circleci/check_npm_version.sh; then
62 | npm run dist
63 | fi
64 |
65 | workflows:
66 | version: 2
67 | install-publish:
68 | jobs:
69 | - build
70 | - publishDryRun:
71 | requires:
72 | - build
73 | filters:
74 | branches:
75 | ignore:
76 | - master
77 | - publish:
78 | requires:
79 | - build
80 | filters:
81 | branches:
82 | only:
83 | - master
84 |
--------------------------------------------------------------------------------
/.env.example:
--------------------------------------------------------------------------------
1 | PRIV_KEY=
2 | MAINNET_NODE_URL=
3 |
4 |
--------------------------------------------------------------------------------
/.gitattributes:
--------------------------------------------------------------------------------
1 | *.sol linguist-language=Solidity
2 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | node_modules
2 | dist
3 | .env
4 | .temp_*
5 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2020 StudyDeFi
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # money-legos
2 |
3 | [](https://app.circleci.com/pipelines/github/studydefi/money-legos)
4 | [](https://www.npmjs.com/package/@studydefi/money-legos)
5 | 
6 | 
7 |
8 | 
9 |
10 | > Get **ABIs**, **Addresses**, and **Solidity Interfaces** to popular DeFi protocols
11 |
12 | **Now with Typescript-powered autocomplete!**
13 |
14 | `money-legos` is an NPM package that provides you with the **mainnet addresses**, **ABIs**, and **Solidity interfaces** for popular DeFi protocols.
15 |
16 | ### Click [here](https://money-legos.studydefi.com/) for docs and visit our Discord [here](https://discord.gg/rBr3U32)!
17 |
18 | Protocols supported:
19 |
20 | - AAVE
21 | - Compound
22 | - Curve Finance
23 | - DappSys
24 | - DyDx
25 | - ERC20
26 | - Idle V3
27 | - Kyber.Network
28 | - MakerDAO
29 | - OneSplit
30 | - UMA Protocol
31 | - Uniswap v1
32 | - Synthetix
33 | - Balancer
34 | - mStable
35 | - Uniswap v2
36 |
37 | Importing specific protocols is also supported:
38 |
39 |
40 |
41 | ## Install
42 |
43 | ```bash
44 | npm install @studydefi/money-legos
45 | ```
46 |
47 | ## Usage
48 |
49 | ### JavaScript
50 |
51 | ```javascript
52 | import { legos } from "@studydefi/money-legos";
53 |
54 | // access ABIs and addresses
55 | legos.erc20.abi;
56 | legos.erc20.dai.address;
57 |
58 | // of many popular DeFi protocols
59 | legos.uniswap.factory.abi;
60 | legos.uniswap.factory.address;
61 |
62 | // import only the protocol you are interested in
63 | import uniswap from "@studydefi/money-legos/uniswap";
64 |
65 | uniswap.factory.abi;
66 | uniswap.factory.address;
67 | ```
68 |
69 | ### Solidity
70 |
71 | ```solidity
72 | pragma solidity ^0.5.0;
73 |
74 | import "@studydefi/money-legos/onesplit/contracts/IOneSplit.sol";
75 |
76 | import "@openzeppelin/contracts/token/ERC20/IERC20.sol";
77 |
78 |
79 | contract OneSplitSwapper {
80 | // Uniswap Mainnet factory address
81 | address constant OneSplitAddress = 0xC586BeF4a0992C495Cf22e1aeEE4E446CECDee0E;
82 |
83 | function _swap(address from, address to, uint256 amountWei) internal {
84 | IERC20 fromIERC20 = IERC20(from);
85 | IERC20 toIERC20 = IERC20(to);
86 |
87 | (uint256 returnAmount, uint256[] memory distribution) = IOneSplit(
88 | OneSplitAddress
89 | ).getExpectedReturn(
90 | fromIERC20,
91 | toIERC20,
92 | amountWei,
93 | 10,
94 | 0
95 | );
96 |
97 | IOneSplit(OneSplitAddress).swap(
98 | fromIERC20,
99 | toIERC20,
100 | amountWei,
101 | returnAmount,
102 | distribution,
103 | 0
104 | );
105 | }
106 | }
107 | ```
108 |
--------------------------------------------------------------------------------
/assets/legos-autocomplete.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/studydefi/money-legos/4e4cd1e45e2abeb0950e40c6fe70248322e1f5f2/assets/legos-autocomplete.gif
--------------------------------------------------------------------------------
/assets/weight.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/studydefi/money-legos/4e4cd1e45e2abeb0950e40c6fe70248322e1f5f2/assets/weight.png
--------------------------------------------------------------------------------
/docs/.nojekyll:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/studydefi/money-legos/4e4cd1e45e2abeb0950e40c6fe70248322e1f5f2/docs/.nojekyll
--------------------------------------------------------------------------------
/docs/README.md:
--------------------------------------------------------------------------------
1 | # money-legos
2 |
3 | 
4 | 
5 | 
6 | 
7 |
8 | > Get **ABIs**, **Addresses**, and **Solidity Interfaces** to popular DeFi protocols
9 |
10 | **Now with Typescript-powered autocomplete!**
11 |
12 | - Github: https://github.com/studydefi/money-legos
13 | - NPM: https://www.npmjs.com/package/@studydefi/money-legos
14 | - Twitter: https://twitter.com/studydefi
15 | - Discord: https://discord.gg/rBr3U32
16 |
17 | ## What is this?
18 |
19 | `money-legos` is an NPM package that provides you with the **mainnet addresses**, **ABIs**, and **Solidity interfaces** for popular DeFi protocols.
20 |
21 | 
22 |
23 | ## Protocols supported
24 |
25 | - AAVE
26 | - Compound
27 | - Curve Finance
28 | - DappSys
29 | - DyDx
30 | - ERC20
31 | - Idle V3
32 | - Kyber.Network
33 | - MakerDAO
34 | - OneSplit
35 | - UMA
36 | - Uniswap v1
37 | - Synthetix
38 | - Balancer
39 | - mStable
40 | - Uniswap v2
41 |
--------------------------------------------------------------------------------
/docs/_sidebar.md:
--------------------------------------------------------------------------------
1 |
2 |
3 | - Overview
4 |
5 | - [Quick start](quickstart.md)
6 | - [Addresses](overview_mainnet_address.md)
7 |
8 | - Reference Guides
9 | - [Aave](aave.md)
10 | - [Compound](compound.md)
11 | - [CurveFi](curvefi.md)
12 | - [DyDx](dydx.md)
13 | - [Idle V3](idle.md)
14 | - [Kyber Network](kyber.md)
15 | - [Maker](maker.md)
16 | - [OneSplit](onesplit.md)
17 | - [Uniswap V1](uniswap.md)
18 | - [Synthetix](synthetix.md)
19 | - [Balancer](balancer.md)
20 | - [mStable](mstable.md)
21 | - [Uniswap V2](uniswapV2.md)
22 |
--------------------------------------------------------------------------------
/docs/dydx.md:
--------------------------------------------------------------------------------
1 | # DyDx
2 |
3 | ## Flashloans On DyDx
4 |
5 | _Special thanks to [kollateral](http://github.com/kollateral/kollateral/) for open sourcing their implementation._
6 |
7 | DyDx [does not natively have a "flashloan" feature](https://help.dydx.exchange/en/articles/3724602-flash-loans). However you can achieve a similar behavior by executing a series of operations on the [SoloMargin contract](https://etherscan.io/address/0x1e0447b19bb6ecfdae1e4ae1694b0c3659614e4e). In order mimic an Aave flashloan on DyDx, you would need to:
8 |
9 | 1. Borrow `x` amount of tokens. ([Withdraw](https://docs.dydx.exchange/#/protocol?id=withdraw))
10 | 2. Call a function (i.e. Logic to handle flashloaned funds). ([Call](https://docs.dydx.exchange/#/protocol?id=call))
11 | 3. Deposit back `x` (+2 wei) amount of tokens. ([Deposit](https://docs.dydx.exchange/#/protocol?id=deposit))
12 |
13 | All within one transaction. The reason this works is because DyDx natively has this feature called [operate](https://docs.dydx.exchange/#/protocol?id=operations) which allows you to execute __a series of operations without checking if the state is valid until the final step__. That means that you can withdraw as much funds as you like, do anything with it, as long as you deposit back the funds (and have ~2 Wei of assets in your account) within the same transaction.
14 |
15 | Note that doing a flashloan in DyDx is similar to that of doing it in Aave, you'll need to:
16 |
17 | 1. Deploy a smart contract with specific logic to handle flashloaned asset.
18 | 2. Interact with the smart contract deployed from step 1.
19 |
20 | ### Flashloan Logic (Solidity)
21 |
22 | Your smart contract will need to inherit from `DydxFlashloanBase` and have two functions:
23 | 1. An entrypoint function where __you__ call to initiate the flashloan (`initiateFlashLoan` in the example below).
24 | 2. A callback function called `callFunction` that contains the action logic to perform once the loan is given to us.
25 |
26 |
27 | ```js
28 | pragma solidity ^0.5.0;
29 | pragma experimental ABIEncoderV2;
30 |
31 | import "@studydefi/money-legos/dydx/contracts/DydxFlashloanBase.sol";
32 | import "@studydefi/money-legos/dydx/contracts/ICallee.sol";
33 |
34 | import "@openzeppelin/contracts/token/ERC20/IERC20.sol";
35 |
36 |
37 | contract DydxFlashloaner is ICallee, DydxFlashloanBase {
38 | struct MyCustomData {
39 | address token;
40 | uint256 repayAmount;
41 | }
42 |
43 | // This is the function that will be called postLoan
44 | // i.e. Encode the logic to handle your flashloaned funds here
45 | function callFunction(
46 | address sender,
47 | Account.Info memory account,
48 | bytes memory data
49 | ) public {
50 | MyCustomData memory mcd = abi.decode(data, (MyCustomData));
51 | uint256 balOfLoanedToken = IERC20(mcd.token).balanceOf(address(this));
52 |
53 | // Note that you can ignore the line below
54 | // if your dydx account (this contract in this case)
55 | // has deposited at least ~2 Wei of assets into the account
56 | // to balance out the collaterization ratio
57 | require(
58 | balOfLoanedToken >= mcd.repayAmount,
59 | "Not enough funds to repay dydx loan!"
60 | );
61 |
62 | // TODO: Encode your logic here
63 | // E.g. arbitrage, liquidate accounts, etc
64 | revert("Hello, you haven't encoded your logic");
65 | }
66 |
67 | function initiateFlashLoan(address _solo, address _token, uint256 _amount)
68 | external
69 | {
70 | ISoloMargin solo = ISoloMargin(_solo);
71 |
72 | // Get marketId from token address
73 | uint256 marketId = _getMarketIdFromTokenAddress(_solo, _token);
74 |
75 | // Calculate repay amount (_amount + (2 wei))
76 | // Approve transfer from
77 | uint256 repayAmount = _getRepaymentAmountInternal(_amount);
78 | IERC20(_token).approve(_solo, repayAmount);
79 |
80 | // 1. Withdraw $
81 | // 2. Call callFunction(...)
82 | // 3. Deposit back $
83 | Actions.ActionArgs[] memory operations = new Actions.ActionArgs[](3);
84 |
85 | operations[0] = _getWithdrawAction(marketId, _amount);
86 | operations[1] = _getCallAction(
87 | // Encode MyCustomData for callFunction
88 | abi.encode(MyCustomData({token: _token, repayAmount: repayAmount}))
89 | );
90 | operations[2] = _getDepositAction(marketId, repayAmount);
91 |
92 | Account.Info[] memory accountInfos = new Account.Info[](1);
93 | accountInfos[0] = _getAccountInfo();
94 |
95 | solo.operate(accountInfos, operations);
96 | }
97 | }
98 | ```
99 |
100 | ### Flashloan Initiation (JavaScript)
101 |
102 | Once you've deployed the contract, you can then call initiate the flashloan using the example below. Note that you can `MyCustomData` can be anything you desire, and if you would like to encode the data from the JS side, you can use `ethers.utils.defaultAbiCoder`.
103 |
104 | ```js
105 | const dydxFlashloanerContract = new ethers.Contract(
106 | dydxFlashloanerAddress,
107 | def.abi,
108 | wallet
109 | );
110 |
111 | const main = async () => {
112 | const tx = await dydxFlashloanerContract.initiateFlashLoan(
113 | legos.dydx.soloMargin.address,
114 | legos.erc20.weth.address, // Wanna take out a WETH loan
115 | ethers.utils.parseEther("10"), // Wanna loan 10 WETH
116 | {
117 | gasLimit: 6000000,
118 | }
119 | );
120 | await tx.wait();
121 | };
122 | ```
123 |
--------------------------------------------------------------------------------
/docs/idle.md:
--------------------------------------------------------------------------------
1 | # Idle (V3)
2 |
3 | [Official Idle documentation](https://developers.idle.finance/)
4 |
5 | ## Examples
6 |
7 | Import `@studydefi/money-legos/idle` package
8 |
9 | ```js
10 | const idle = require("@studydefi/money-legos/idle");
11 | ```
12 |
13 | List of all available contracts
14 |
15 | ```js
16 | idle.maxYield.dai.address;
17 | idle.maxYield.usdc.address;
18 | idle.maxYield.usdt.address;
19 | idle.maxYield.susd.address;
20 | idle.maxYield.tusd.address;
21 | idle.maxYield.wbtc.address;
22 |
23 | idle.riskAdjusted.dai.address;
24 | idle.riskAdjusted.usdc.address;
25 | idle.riskAdjusted.usdt.address;
26 |
27 | idle.abi; // the same abi for each idle v3 contract
28 |
29 | idle.decimals; // idle mints ERC-20 tokens
30 | ```
31 |
32 | ### JavaScript
33 |
34 | #### `mintIdleToken`
35 |
36 | ```js
37 | const { ethers } = require("ethers");
38 | const erc20 = require("@studydefi/money-legos/erc20");
39 | const idle = require("@studydefi/money-legos/idle");
40 |
41 | const provider = new ethers.providers.JsonRpcProvider("http://localhost:8545");
42 | const wallet = new ethers.Wallet(process.env.GANACHE_PRIV_KEY, provider);
43 |
44 | // init contracts
45 | const daiContract = new ethers.Contract(erc20.dai.address, erc20.abi, wallet);
46 | const idleContract = new ethers.Contract(
47 | idle.maxYield.dai.address,
48 | idle.abi,
49 | wallet,
50 | );
51 |
52 | // approve Idle to spend your DAI
53 | const daiBalanceWei = await daiContract.balanceOf(wallet.address);
54 | await daiContract.approve(idle.maxYield.dai.address, daiBalanceWei);
55 |
56 | // mint idleDAIYield
57 | await idleContract.mintIdleToken(daiBalanceWei, true, {
58 | gasLimit: 4000000,
59 | });
60 |
61 | // check idleDAI balance
62 | const idleDaiBalance = await idleContract.balanceOf(wallet.address);
63 | console.log(
64 | `idleDAI: ${ethers.utils.formatUnits(idleDaiBalance, idle.decimals)}`,
65 | );
66 | ```
67 |
--------------------------------------------------------------------------------
/docs/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | money-legos docs
6 |
7 |
8 |
12 |
16 |
20 |
24 |
28 |
29 |
30 |
31 |
55 |
56 |
57 |
58 | Loading ...
59 |
105 |
106 |
107 |
108 |
109 |
110 |
111 |
112 |
113 |
114 |
115 |
116 |
--------------------------------------------------------------------------------
/docs/material-oceanic.css:
--------------------------------------------------------------------------------
1 | code[class*="language-"],
2 | pre[class*="language-"] {
3 | text-align: left;
4 | white-space: pre;
5 | word-spacing: normal;
6 | word-break: normal;
7 | word-wrap: normal;
8 | color: #c3cee3;
9 | background: #263238;
10 | font-family: Roboto Mono, monospace;
11 | font-size: 1em;
12 | line-height: 1.5em;
13 |
14 | -moz-tab-size: 4;
15 | -o-tab-size: 4;
16 | tab-size: 4;
17 |
18 | -webkit-hyphens: none;
19 | -moz-hyphens: none;
20 | -ms-hyphens: none;
21 | hyphens: none;
22 | }
23 |
24 | code[class*="language-"]::-moz-selection,
25 | pre[class*="language-"]::-moz-selection,
26 | code[class*="language-"] ::-moz-selection,
27 | pre[class*="language-"] ::-moz-selection {
28 | background: #363636;
29 | }
30 |
31 | code[class*="language-"]::selection,
32 | pre[class*="language-"]::selection,
33 | code[class*="language-"] ::selection,
34 | pre[class*="language-"] ::selection {
35 | background: #363636;
36 | }
37 |
38 | :not(pre) > code[class*="language-"] {
39 | white-space: normal;
40 | border-radius: 0.2em;
41 | padding: 0.1em;
42 | }
43 |
44 | pre[class*="language-"] {
45 | overflow: auto;
46 | position: relative;
47 | margin: 0.5em 0;
48 | padding: 1.25em 1em;
49 | }
50 |
51 | .language-css > code,
52 | .language-sass > code,
53 | .language-scss > code {
54 | color: #fd9170;
55 | }
56 |
57 | [class*="language-"] .namespace {
58 | opacity: 0.7;
59 | }
60 |
61 | .token.atrule {
62 | color: #c792ea;
63 | }
64 |
65 | .token.attr-name {
66 | color: #ffcb6b;
67 | }
68 |
69 | .token.attr-value {
70 | color: #c3e88d;
71 | }
72 |
73 | .token.attribute {
74 | color: #c3e88d;
75 | }
76 |
77 | .token.boolean {
78 | color: #c792ea;
79 | }
80 |
81 | .token.builtin {
82 | color: #ffcb6b;
83 | }
84 |
85 | .token.cdata {
86 | color: #80cbc4;
87 | }
88 |
89 | .token.char {
90 | color: #80cbc4;
91 | }
92 |
93 | .token.class {
94 | color: #ffcb6b;
95 | }
96 |
97 | .token.class-name {
98 | color: #f2ff00;
99 | }
100 |
101 | .token.color {
102 | color: #f2ff00;
103 | }
104 |
105 | .token.comment {
106 | color: #546e7a;
107 | }
108 |
109 | .token.constant {
110 | color: #c792ea;
111 | }
112 |
113 | .token.deleted {
114 | color: #f07178;
115 | }
116 |
117 | .token.doctype {
118 | color: #546e7a;
119 | }
120 |
121 | .token.entity {
122 | color: #f07178;
123 | }
124 |
125 | .token.function {
126 | color: #c792ea;
127 | }
128 |
129 | .token.hexcode {
130 | color: #f2ff00;
131 | }
132 |
133 | .token.id {
134 | color: #c792ea;
135 | font-weight: bold;
136 | }
137 |
138 | .token.important {
139 | color: #c792ea;
140 | font-weight: bold;
141 | }
142 |
143 | .token.inserted {
144 | color: #80cbc4;
145 | }
146 |
147 | .token.keyword {
148 | color: #c792ea;
149 | font-style: italic;
150 | }
151 |
152 | .token.number {
153 | color: #fd9170;
154 | }
155 |
156 | .token.operator {
157 | color: #89ddff;
158 | }
159 |
160 | .token.prolog {
161 | color: #546e7a;
162 | }
163 |
164 | .token.property {
165 | color: #80cbc4;
166 | }
167 |
168 | .token.pseudo-class {
169 | color: #c3e88d;
170 | }
171 |
172 | .token.pseudo-element {
173 | color: #c3e88d;
174 | }
175 |
176 | .token.punctuation {
177 | color: #89ddff;
178 | }
179 |
180 | .token.regex {
181 | color: #f2ff00;
182 | }
183 |
184 | .token.selector {
185 | color: #f07178;
186 | }
187 |
188 | .token.string {
189 | color: #c3e88d;
190 | }
191 |
192 | .token.symbol {
193 | color: #c792ea;
194 | }
195 |
196 | .token.tag {
197 | color: #f07178;
198 | }
199 |
200 | .token.unit {
201 | color: #f07178;
202 | }
203 |
204 | .token.url {
205 | color: #fd9170;
206 | }
207 |
208 | .token.variable {
209 | color: #f07178;
210 | }
--------------------------------------------------------------------------------
/docs/quickstart.md:
--------------------------------------------------------------------------------
1 | # Quickstart
2 |
3 | ## Install
4 |
5 | ```bash
6 | npm install @studydefi/money-legos
7 | ```
8 |
9 | ## Javascript Usage
10 |
11 | First import the module:
12 |
13 | ```js
14 | import { legos } from "@studydefi/money-legos";
15 | ```
16 |
17 | Navigate the JSON tree full of ABIs and addresses:
18 |
19 | ```js
20 | // protocols
21 | legos.uniswap.factory.abi;
22 | legos.uniswap.factory.address;
23 |
24 | // erc20 tokens
25 | legos.erc20.abi;
26 | legos.erc20.dai.address;
27 | ```
28 |
29 | You can also import specific protocols:
30 |
31 | ```js
32 | // import only the protocol you are interested in
33 | import uniswap from "@studydefi/money-legos/uniswap";
34 |
35 | uniswap.factory.abi;
36 | uniswap.factory.address;
37 | ```
38 |
39 | ## Solidity Usage
40 |
41 | ```js
42 | pragma solidity ^0.5.0;
43 |
44 | import "@studydefi/money-legos/onesplit/contracts/IOneSplit.sol";
45 |
46 | import "@openzeppelin/contracts/token/ERC20/IERC20.sol";
47 |
48 |
49 | contract OneSplitSwapper {
50 | // Uniswap Mainnet factory address
51 | address constant OneSplitAddress = 0xC586BeF4a0992C495Cf22e1aeEE4E446CECDee0E;
52 |
53 | function _swap(address from, address to, uint256 amountWei) internal {
54 | IERC20 fromIERC20 = IERC20(from);
55 | IERC20 toIERC20 = IERC20(to);
56 |
57 | (uint256 returnAmount, uint256[] memory distribution) = IOneSplit(
58 | OneSplitAddress
59 | ).getExpectedReturn(
60 | fromIERC20,
61 | toIERC20,
62 | amountWei,
63 | 10,
64 | 0
65 | );
66 |
67 | IOneSplit(OneSplitAddress).swap(
68 | fromIERC20,
69 | toIERC20,
70 | amountWei,
71 | returnAmount,
72 | distribution,
73 | 0
74 | );
75 | }
76 | }
77 | ```
78 |
--------------------------------------------------------------------------------
/jest.config.js:
--------------------------------------------------------------------------------
1 | module.exports = {
2 | preset: 'ts-jest',
3 | testEnvironment: './tests/test-environment.js',
4 | modulePathIgnorePatterns: ["/dist/"]
5 | };
6 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "@studydefi/money-legos",
3 | "version": "2.4.2",
4 | "main": "index.js",
5 | "types": "index.d.ts",
6 | "repository": "git@github.com:studydefi/money-legos.git",
7 | "author": "Adrian Li ",
8 | "license": "MIT",
9 | "scripts": {
10 | "clean": "rm -rf dist",
11 | "build": "yarn clean && tsc --declaration && cp package.json dist && cp README.md dist",
12 | "postbuild": "copyfiles --verbose -u 1 src/**/*.sol dist",
13 | "build:docs": "embedme docs/* && yarn build && node scripts/genAddrMainnetOverview.js > docs/overview_mainnet_address.md",
14 | "serve:docs": "docsify serve ./docs",
15 | "test": "jest --verbose",
16 | "link": "yarn build && cd dist && npm link",
17 | "prepublishOnly": "echo \"Error: Don't run 'npm publish' in root. Use 'npm run dist' instead.\" && exit 1",
18 | "dist": "cd dist && npm publish --ignore-scripts --access public"
19 | },
20 | "devDependencies": {
21 | "@types/jest": "^25.2.1",
22 | "@types/node": "^13.13.0",
23 | "copyfiles": "^2.2.0",
24 | "docsify-cli": "^4.4.0",
25 | "dotenv": "^8.2.0",
26 | "embedme": "^1.21.0",
27 | "ethers": "^4.0.46",
28 | "ganache-core": "^2.10.2",
29 | "jest": "^25.3.0",
30 | "json2md": "^1.7.0",
31 | "ts-jest": "^25.3.1",
32 | "typescript": "^3.8.3"
33 | },
34 | "prettier": {
35 | "trailingComma": "all"
36 | },
37 | "keywords": [
38 | "ethereum",
39 | "abi",
40 | "defi",
41 | "defi addresses",
42 | "defi abi",
43 | "ethereum abi",
44 | "ethereum address",
45 | "money-legos"
46 | ],
47 | "dependencies": {
48 | "@openzeppelin/contracts": "^2.5.0"
49 | }
50 | }
51 |
--------------------------------------------------------------------------------
/scripts/genAddrMainnetOverview.js:
--------------------------------------------------------------------------------
1 | const json2md = require("json2md");
2 | const { legos } = require("../dist");
3 |
4 | const prettyTitle = (t) => t.charAt(0).toUpperCase() + t.slice(1);
5 | const formatToEtherscanLink = (l) =>
6 | `[${l}](https://etherscan.io/address/${l})`;
7 |
8 | // Funky protocols with different structures
9 | // Need to construct the markdown a bit differently
10 | const funkyProtocols = ["curvefi", "idle"];
11 | const noRenderProtocols = ["dappsys"];
12 |
13 | // Generated markdown
14 | const markdown = [{ h1: "Mainnet Address Overview" }];
15 |
16 | // Builds the overview page
17 | Object.keys(legos)
18 | .sort()
19 | .forEach((curDefiProtocol) => {
20 | // Don't wanna render these defi libraries
21 | if (noRenderProtocols.includes(curDefiProtocol.toLowerCase())) {
22 | return;
23 | }
24 |
25 | markdown.push({
26 | h2: prettyTitle(curDefiProtocol),
27 | });
28 |
29 | markdown.push({
30 | link: {
31 | title: "Link to ABIs",
32 | source: `https://github.com/studydefi/money-legos/tree/master/src/${curDefiProtocol}/abi`,
33 | },
34 | });
35 |
36 | const contracts = legos[curDefiProtocol];
37 |
38 | // If its a funky protocol, we need to do some custom formatting
39 | // E.g. curveFi, where it has multiple contracts, each for a different
40 | //
41 | if (funkyProtocols.includes(curDefiProtocol.toLowerCase())) {
42 | Object.keys(contracts)
43 | .sort()
44 | .forEach((outerContractName) => {
45 | const ul = [];
46 |
47 | const innerContracts = contracts[outerContractName];
48 |
49 | Object.keys(innerContracts)
50 | .sort()
51 | .forEach((innerContractName) => {
52 | const innerContract = innerContracts[innerContractName];
53 | if (Object.keys(innerContract).includes("address")) {
54 | ul.push(
55 | `${innerContractName}: ${formatToEtherscanLink(
56 | innerContract["address"],
57 | )}`,
58 | );
59 | }
60 | });
61 |
62 | if (ul.length > 0) {
63 | markdown.push({
64 | h4: `${outerContractName}`,
65 | });
66 | markdown.push({ ul });
67 | }
68 | });
69 | }
70 | // If its a single contract with no one (e.g. oneSplit)
71 | else if (Object.keys(contracts).includes("address")) {
72 | const ul = [
73 | `${curDefiProtocol}: ${formatToEtherscanLink(contracts["address"])}`,
74 | ];
75 | markdown.push({ ul });
76 | }
77 | // Standard format
78 | else {
79 | const ul = [];
80 |
81 | // Otherwise we can just get k/v from the contracts key
82 | Object.keys(contracts)
83 | .sort()
84 | .forEach((contractName) => {
85 | // Quick reference
86 | const contract = contracts[contractName];
87 |
88 | // If the current key has "contract" in it
89 | if (Object.keys(contract).includes("address")) {
90 | ul.push(
91 | `${contractName}: ${formatToEtherscanLink(contract["address"])}`,
92 | );
93 | }
94 | });
95 |
96 | markdown.push({ ul });
97 | }
98 | });
99 |
100 | console.log(json2md(markdown));
101 |
--------------------------------------------------------------------------------
/scripts/getAbisFromUMA.js:
--------------------------------------------------------------------------------
1 | const path = require("path");
2 | const fs = require("fs");
3 |
4 | // Usage: node scripts/getAbisFromUMA.js
5 |
6 | // only include the following contracts
7 | const fileFilter = [
8 | "Finder",
9 | "VotingToken",
10 | "IdentifierWhitelist",
11 | "Voting",
12 | "Registry",
13 | "FinancialContractsAdmin",
14 | "Store",
15 | "Governor",
16 | "DesignatedVotingFactory",
17 | "WETH9",
18 | "ExpiringMultiPartyLib",
19 | "ExpiringMultiParty",
20 | "TokenFactory",
21 | "AddressWhitelist",
22 | "ExpiringMultiPartyCreator",
23 | ];
24 |
25 | // get all JSON files from their artifacts directory
26 | const inputPath = process.argv[2];
27 | const artifactPath = path.join(inputPath, "./core/build/contracts");
28 | const filenames = fs.readdirSync(artifactPath);
29 |
30 | // create a fresh temp folder to hold ABIs
31 | const outputDir = path.join(process.cwd(), "./src/uma/abi");
32 | if (fs.existsSync(outputDir)) {
33 | fs.rmdirSync(outputDir, { recursive: true });
34 | }
35 | fs.mkdirSync(outputDir);
36 |
37 | // write ABIs to new files
38 | filenames.forEach((filename) => {
39 | const contents = require(path.join(artifactPath, filename));
40 | const name = filename.split(".").slice(0, -1).join(".");
41 |
42 | if (fileFilter.includes(name)) {
43 | const outputPath = path.join(outputDir, filename);
44 | fs.writeFileSync(outputPath, JSON.stringify(contents.abi, null, 2));
45 | console.log("written:", outputPath);
46 | }
47 | });
48 |
--------------------------------------------------------------------------------
/src/aave/contracts.ts:
--------------------------------------------------------------------------------
1 | import ATokenAbi from "./abi/AToken.json";
2 | import LendingPoolAbi from "./abi/LendingPool.json";
3 | import LendingPoolAddressesProviderAbi from "./abi/LendingPoolAddessProvider.json";
4 | import LendingPoolCoreAbi from "./abi/LendingPoolCore.json";
5 |
6 | const contracts = {
7 | ATokenAbi,
8 | LendingPoolAddressesProvider: {
9 | abi: LendingPoolAddressesProviderAbi,
10 | address: "0x24a42fd28c976a61df5d00d0599c34c4f90748c8",
11 | },
12 | LendingPool: {
13 | abi: LendingPoolAbi,
14 | address: "0x398ec7346dcd622edc5ae82352f02be94c62d119",
15 | },
16 | LendingPoolCore: {
17 | abi: LendingPoolCoreAbi,
18 | address: "0x3dfd23a6c5e8bbcfc9581d2e864a68feb6a076d3",
19 | },
20 | aETH: {
21 | address: "0x3a3a65aab0dd2a17e3f1947ba16138cd37d08c04",
22 | abi: ATokenAbi,
23 | decimals: 18,
24 | },
25 | aDAI: {
26 | address: "0xfc1e690f61efd961294b3e1ce3313fbd8aa4f85d",
27 | abi: ATokenAbi,
28 | decimals: 18,
29 | },
30 | aUSDC: {
31 | address: "0x9ba00d6856a4edf4665bca2c2309936572473b7e",
32 | abi: ATokenAbi,
33 | decimals: 6,
34 | },
35 | aSUSD: {
36 | address: "0x625ae63000f46200499120b906716420bd059240",
37 | abi: ATokenAbi,
38 | decimals: 18,
39 | },
40 | aTUSD: {
41 | address: "0x4da9b813057d04baef4e5800e36083717b4a0341",
42 | abi: ATokenAbi,
43 | decimals: 18,
44 | },
45 | aUSDT: {
46 | address: "0x71fc860f7d3a592a4a98740e39db31d25db65ae8",
47 | abi: ATokenAbi,
48 | decimals: 6,
49 | },
50 | aBUSD: {
51 | address: "0x6ee0f7bb50a54ab5253da0667b0dc2ee526c30a8",
52 | abi: ATokenAbi,
53 | decimals: 18,
54 | },
55 | aBAT: {
56 | address: "0xe1ba0fb44ccb0d11b80f92f4f8ed94ca3ff51d00",
57 | abi: ATokenAbi,
58 | decimals: 18,
59 | },
60 | aKNC: {
61 | address: "0x9d91be44c06d373a8a226e1f3b146956083803eb",
62 | abi: ATokenAbi,
63 | decimals: 18,
64 | },
65 | aLEND: {
66 | address: "0x7d2d3688df45ce7c552e19c27e007673da9204b8",
67 | abi: ATokenAbi,
68 | decimals: 18,
69 | },
70 | aLINK: {
71 | address: "0xa64bd6c70cb9051f6a9ba1f163fdc07e0dfb5f84",
72 | abi: ATokenAbi,
73 | decimals: 18,
74 | },
75 | aMANA: {
76 | address: "0x6fce4a401b6b80ace52baaefe4421bd188e76f6f",
77 | abi: ATokenAbi,
78 | decimals: 18,
79 | },
80 | aMKR: {
81 | address: "0x7deb5e830be29f91e298ba5ff1356bb7f8146998",
82 | abi: ATokenAbi,
83 | decimals: 18,
84 | },
85 | aREP: {
86 | address: "0x71010a9d003445ac60c4e6a7017c1e89a477b438",
87 | abi: ATokenAbi,
88 | decimals: 18,
89 | },
90 | aSNX: {
91 | address: "0x328c4c80bc7aca0834db37e6600a6c49e12da4de",
92 | abi: ATokenAbi,
93 | decimals: 18,
94 | },
95 | aWBTC: {
96 | address: "0xfc4b8ed459e00e5400be803a9bb3954234fd50e3",
97 | abi: ATokenAbi,
98 | decimals: 8,
99 | },
100 | aZRX: {
101 | address: "0x6fb0855c404e09c47c3fbca25f08d4e41f9f062f",
102 | abi: ATokenAbi,
103 | decimals: 18,
104 | },
105 | };
106 |
107 | export default contracts;
108 |
--------------------------------------------------------------------------------
/src/aave/contracts/FlashloanReceiverBase.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | import "./IFlashLoanReceiver.sol";
4 |
5 | contract FlashLoanReceiverBase is IFlashLoanReceiver {
6 | using SafeMath for uint256;
7 |
8 | address constant ETHADDRESS = 0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE;
9 |
10 | ILendingPoolAddressesProvider public addressesProvider = ILendingPoolAddressesProvider(
11 | 0x24a42fD28C976A61Df5D00D0599C34c4f90748c8
12 | );
13 |
14 | function() external payable {}
15 |
16 | function transferFundsBackToPoolInternal(address _reserve, uint256 _amount)
17 | internal
18 | {
19 | address payable core = addressesProvider.getLendingPoolCore();
20 | transferInternal(core, _reserve, _amount);
21 | }
22 |
23 | function transferInternal(
24 | address payable _destination,
25 | address _reserve,
26 | uint256 _amount
27 | ) internal {
28 | if (_reserve == ETHADDRESS) {
29 | //solium-disable-next-line
30 | _destination.call.value(_amount)("");
31 | return;
32 | }
33 |
34 | IERC20(_reserve).transfer(_destination, _amount);
35 | }
36 |
37 | function getBalanceInternal(address _target, address _reserve)
38 | internal
39 | view
40 | returns (uint256)
41 | {
42 | if (_reserve == ETHADDRESS) {
43 | return _target.balance;
44 | }
45 |
46 | return IERC20(_reserve).balanceOf(_target);
47 | }
48 | }
49 |
--------------------------------------------------------------------------------
/src/aave/contracts/IFlashLoanReceiver.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | import "@openzeppelin/contracts/token/ERC20/IERC20.sol";
4 |
5 | import "./ILendingPoolAddressesProvider.sol";
6 |
7 |
8 | interface IFlashLoanReceiver {
9 | function executeOperation(
10 | address _reserve,
11 | uint256 _amount,
12 | uint256 _fee,
13 | bytes calldata _params
14 | ) external;
15 | }
16 |
17 |
18 |
--------------------------------------------------------------------------------
/src/aave/contracts/ILendingPool.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | interface ILendingPool {
4 | function addressesProvider () external view returns ( address );
5 | function deposit ( address _reserve, uint256 _amount, uint16 _referralCode ) external payable;
6 | function redeemUnderlying ( address _reserve, address _user, uint256 _amount ) external;
7 | function borrow ( address _reserve, uint256 _amount, uint256 _interestRateMode, uint16 _referralCode ) external;
8 | function repay ( address _reserve, uint256 _amount, address _onBehalfOf ) external payable;
9 | function swapBorrowRateMode ( address _reserve ) external;
10 | function rebalanceFixedBorrowRate ( address _reserve, address _user ) external;
11 | function setUserUseReserveAsCollateral ( address _reserve, bool _useAsCollateral ) external;
12 | function liquidationCall ( address _collateral, address _reserve, address _user, uint256 _purchaseAmount, bool _receiveAToken ) external payable;
13 | function flashLoan ( address _receiver, address _reserve, uint256 _amount, bytes calldata _params ) external;
14 | function getReserveConfigurationData ( address _reserve ) external view returns ( uint256 ltv, uint256 liquidationThreshold, uint256 liquidationDiscount, address interestRateStrategyAddress, bool usageAsCollateralEnabled, bool borrowingEnabled, bool fixedBorrowRateEnabled, bool isActive );
15 | function getReserveData ( address _reserve ) external view returns ( uint256 totalLiquidity, uint256 availableLiquidity, uint256 totalBorrowsFixed, uint256 totalBorrowsVariable, uint256 liquidityRate, uint256 variableBorrowRate, uint256 fixedBorrowRate, uint256 averageFixedBorrowRate, uint256 utilizationRate, uint256 liquidityIndex, uint256 variableBorrowIndex, address aTokenAddress, uint40 lastUpdateTimestamp );
16 | function getUserAccountData ( address _user ) external view returns ( uint256 totalLiquidityETH, uint256 totalCollateralETH, uint256 totalBorrowsETH, uint256 availableBorrowsETH, uint256 currentLiquidationThreshold, uint256 ltv, uint256 healthFactor );
17 | function getUserReserveData ( address _reserve, address _user ) external view returns ( uint256 currentATokenBalance, uint256 currentUnderlyingBalance, uint256 currentBorrowBalance, uint256 principalBorrowBalance, uint256 borrowRateMode, uint256 borrowRate, uint256 liquidityRate, uint256 originationFee, uint256 variableBorrowIndex, uint256 lastUpdateTimestamp, bool usageAsCollateralEnabled );
18 | function getReserves () external view;
19 | }
20 |
--------------------------------------------------------------------------------
/src/aave/contracts/ILendingPoolAddressesProvider.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | /**
4 | @title ILendingPoolAddressesProvider interface
5 | @notice provides the interface to fetch the LendingPoolCore address
6 | */
7 |
8 | contract ILendingPoolAddressesProvider {
9 |
10 | function getLendingPool() public view returns (address);
11 | function setLendingPoolImpl(address _pool) public;
12 |
13 | function getLendingPoolCore() public view returns (address payable);
14 | function setLendingPoolCoreImpl(address _lendingPoolCore) public;
15 |
16 | function getLendingPoolConfigurator() public view returns (address);
17 | function setLendingPoolConfiguratorImpl(address _configurator) public;
18 |
19 | function getLendingPoolDataProvider() public view returns (address);
20 | function setLendingPoolDataProviderImpl(address _provider) public;
21 |
22 | function getLendingPoolParametersProvider() public view returns (address);
23 | function setLendingPoolParametersProviderImpl(address _parametersProvider) public;
24 |
25 | function getTokenDistributor() public view returns (address);
26 | function setTokenDistributor(address _tokenDistributor) public;
27 |
28 | function getFeeProvider() public view returns (address);
29 | function setFeeProviderImpl(address _feeProvider) public;
30 |
31 | function getLendingPoolLiquidationManager() public view returns (address);
32 | function setLendingPoolLiquidationManager(address _manager) public;
33 |
34 | function getLendingPoolManager() public view returns (address);
35 | function setLendingPoolManager(address _lendingPoolManager) public;
36 |
37 | function getPriceOracle() public view returns (address);
38 | function setPriceOracle(address _priceOracle) public;
39 |
40 | function getLendingRateOracle() public view returns (address);
41 | function setLendingRateOracle(address _lendingRateOracle) public;
42 |
43 | }
--------------------------------------------------------------------------------
/src/aave/index.ts:
--------------------------------------------------------------------------------
1 | import { default as contracts } from "./contracts";
2 |
3 | export = {
4 | ...contracts,
5 | };
6 |
--------------------------------------------------------------------------------
/src/balancer/abi/BActions.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "constant": false,
4 | "inputs": [
5 | {
6 | "internalType": "contract BFactory",
7 | "name": "factory",
8 | "type": "address"
9 | },
10 | { "internalType": "address[]", "name": "tokens", "type": "address[]" },
11 | { "internalType": "uint256[]", "name": "balances", "type": "uint256[]" },
12 | { "internalType": "uint256[]", "name": "denorms", "type": "uint256[]" },
13 | { "internalType": "uint256", "name": "swapFee", "type": "uint256" },
14 | { "internalType": "bool", "name": "finalize", "type": "bool" }
15 | ],
16 | "name": "create",
17 | "outputs": [
18 | { "internalType": "contract BPool", "name": "pool", "type": "address" }
19 | ],
20 | "payable": false,
21 | "stateMutability": "nonpayable",
22 | "type": "function"
23 | },
24 | {
25 | "constant": false,
26 | "inputs": [
27 | { "internalType": "contract BPool", "name": "pool", "type": "address" }
28 | ],
29 | "name": "finalize",
30 | "outputs": [],
31 | "payable": false,
32 | "stateMutability": "nonpayable",
33 | "type": "function"
34 | },
35 | {
36 | "constant": false,
37 | "inputs": [
38 | { "internalType": "contract BPool", "name": "pool", "type": "address" },
39 | { "internalType": "uint256", "name": "poolAmountOut", "type": "uint256" },
40 | {
41 | "internalType": "uint256[]",
42 | "name": "maxAmountsIn",
43 | "type": "uint256[]"
44 | }
45 | ],
46 | "name": "joinPool",
47 | "outputs": [],
48 | "payable": false,
49 | "stateMutability": "nonpayable",
50 | "type": "function"
51 | },
52 | {
53 | "constant": false,
54 | "inputs": [
55 | { "internalType": "contract BPool", "name": "pool", "type": "address" },
56 | { "internalType": "address", "name": "tokenIn", "type": "address" },
57 | { "internalType": "uint256", "name": "tokenAmountIn", "type": "uint256" },
58 | {
59 | "internalType": "uint256",
60 | "name": "minPoolAmountOut",
61 | "type": "uint256"
62 | }
63 | ],
64 | "name": "joinswapExternAmountIn",
65 | "outputs": [],
66 | "payable": false,
67 | "stateMutability": "nonpayable",
68 | "type": "function"
69 | },
70 | {
71 | "constant": false,
72 | "inputs": [
73 | { "internalType": "contract BPool", "name": "pool", "type": "address" },
74 | { "internalType": "address", "name": "newController", "type": "address" }
75 | ],
76 | "name": "setController",
77 | "outputs": [],
78 | "payable": false,
79 | "stateMutability": "nonpayable",
80 | "type": "function"
81 | },
82 | {
83 | "constant": false,
84 | "inputs": [
85 | { "internalType": "contract BPool", "name": "pool", "type": "address" },
86 | { "internalType": "bool", "name": "publicSwap", "type": "bool" }
87 | ],
88 | "name": "setPublicSwap",
89 | "outputs": [],
90 | "payable": false,
91 | "stateMutability": "nonpayable",
92 | "type": "function"
93 | },
94 | {
95 | "constant": false,
96 | "inputs": [
97 | { "internalType": "contract BPool", "name": "pool", "type": "address" },
98 | { "internalType": "uint256", "name": "newFee", "type": "uint256" }
99 | ],
100 | "name": "setSwapFee",
101 | "outputs": [],
102 | "payable": false,
103 | "stateMutability": "nonpayable",
104 | "type": "function"
105 | },
106 | {
107 | "constant": false,
108 | "inputs": [
109 | { "internalType": "contract BPool", "name": "pool", "type": "address" },
110 | { "internalType": "address[]", "name": "tokens", "type": "address[]" },
111 | { "internalType": "uint256[]", "name": "balances", "type": "uint256[]" },
112 | { "internalType": "uint256[]", "name": "denorms", "type": "uint256[]" }
113 | ],
114 | "name": "setTokens",
115 | "outputs": [],
116 | "payable": false,
117 | "stateMutability": "nonpayable",
118 | "type": "function"
119 | }
120 | ]
121 |
--------------------------------------------------------------------------------
/src/balancer/abi/BFactory.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "inputs": [],
4 | "payable": false,
5 | "stateMutability": "nonpayable",
6 | "type": "constructor"
7 | },
8 | {
9 | "anonymous": false,
10 | "inputs": [
11 | {
12 | "indexed": true,
13 | "internalType": "address",
14 | "name": "caller",
15 | "type": "address"
16 | },
17 | {
18 | "indexed": true,
19 | "internalType": "address",
20 | "name": "blabs",
21 | "type": "address"
22 | }
23 | ],
24 | "name": "LOG_BLABS",
25 | "type": "event"
26 | },
27 | {
28 | "anonymous": false,
29 | "inputs": [
30 | {
31 | "indexed": true,
32 | "internalType": "address",
33 | "name": "caller",
34 | "type": "address"
35 | },
36 | {
37 | "indexed": true,
38 | "internalType": "address",
39 | "name": "pool",
40 | "type": "address"
41 | }
42 | ],
43 | "name": "LOG_NEW_POOL",
44 | "type": "event"
45 | },
46 | {
47 | "constant": false,
48 | "inputs": [
49 | { "internalType": "contract BPool", "name": "pool", "type": "address" }
50 | ],
51 | "name": "collect",
52 | "outputs": [],
53 | "payable": false,
54 | "stateMutability": "nonpayable",
55 | "type": "function"
56 | },
57 | {
58 | "constant": true,
59 | "inputs": [],
60 | "name": "getBLabs",
61 | "outputs": [{ "internalType": "address", "name": "", "type": "address" }],
62 | "payable": false,
63 | "stateMutability": "view",
64 | "type": "function"
65 | },
66 | {
67 | "constant": true,
68 | "inputs": [],
69 | "name": "getColor",
70 | "outputs": [{ "internalType": "bytes32", "name": "", "type": "bytes32" }],
71 | "payable": false,
72 | "stateMutability": "view",
73 | "type": "function"
74 | },
75 | {
76 | "constant": true,
77 | "inputs": [{ "internalType": "address", "name": "b", "type": "address" }],
78 | "name": "isBPool",
79 | "outputs": [{ "internalType": "bool", "name": "", "type": "bool" }],
80 | "payable": false,
81 | "stateMutability": "view",
82 | "type": "function"
83 | },
84 | {
85 | "constant": false,
86 | "inputs": [],
87 | "name": "newBPool",
88 | "outputs": [
89 | { "internalType": "contract BPool", "name": "", "type": "address" }
90 | ],
91 | "payable": false,
92 | "stateMutability": "nonpayable",
93 | "type": "function"
94 | },
95 | {
96 | "constant": false,
97 | "inputs": [{ "internalType": "address", "name": "b", "type": "address" }],
98 | "name": "setBLabs",
99 | "outputs": [],
100 | "payable": false,
101 | "stateMutability": "nonpayable",
102 | "type": "function"
103 | }
104 | ]
105 |
--------------------------------------------------------------------------------
/src/balancer/contracts.ts:
--------------------------------------------------------------------------------
1 | import BActions from "./abi/BActions.json";
2 | import ExchangeProxy from "./abi/ExchangeProxy.json";
3 | import BFactory from "./abi/BFactory.json";
4 | import BPool from "./abi/BPool.json";
5 |
6 | const contracts = {
7 | PoolFactory: {
8 | abi: BFactory,
9 | address: "0x9424B1412450D0f8Fc2255FAf6046b98213B76Bd",
10 | },
11 | BActions: {
12 | abi: BActions,
13 | address: "0xde4A25A0b9589689945d842c5ba0CF4f0D4eB3ac",
14 | },
15 | ExchangeProxy: {
16 | abi: ExchangeProxy,
17 | address: "0x6317C5e82A06E1d8bf200d21F4510Ac2c038AC81",
18 | },
19 | BPool: {
20 | abi: BPool,
21 | },
22 | };
23 |
24 | export default contracts;
25 |
--------------------------------------------------------------------------------
/src/balancer/contracts/BFactory.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | import "./BPool.sol";
4 |
5 | interface BFactory {
6 |
7 | function isBPool(address b) external view returns (bool);
8 | function newBPool() external returns (BPool);
9 |
10 | }
--------------------------------------------------------------------------------
/src/balancer/contracts/ExchangeProxy.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 |
4 | interface ExchangeProxy {
5 |
6 | function batchSwapExactIn(
7 | Swap[] memory swaps,
8 | address tokenIn,
9 | address tokenOut,
10 | uint totalAmountIn,
11 | uint minTotalAmountOut
12 | ) public returns (uint totalAmountOut);
13 |
14 | function batchSwapExactOut(
15 | Swap[] memory swaps,
16 | address tokenIn,
17 | address tokenOut,
18 | uint maxTotalAmountIn
19 | ) public returns (uint totalAmountIn);
20 |
21 | function batchEthInSwapExactIn(
22 | Swap[] memory swaps,
23 | address tokenOut,
24 | uint minTotalAmountOut
25 | ) public payable returns (uint totalAmountOut);
26 |
27 | function batchEthOutSwapExactIn(
28 | Swap[] memory swaps,
29 | address tokenIn,
30 | uint totalAmountIn,
31 | uint minTotalAmountOut
32 | ) public returns (uint totalAmountOut);
33 |
34 | function batchEthInSwapExactOut(
35 | Swap[] memory swaps,
36 | address tokenOut
37 | ) public payable returns (uint totalAmountIn);
38 |
39 | function batchEthOutSwapExactOut(
40 | Swap[] memory swaps,
41 | address tokenIn,
42 | uint maxTotalAmountIn
43 | ) public returns (uint totalAmountIn);
44 |
45 | }
--------------------------------------------------------------------------------
/src/balancer/index.ts:
--------------------------------------------------------------------------------
1 | import { default as contracts } from "./contracts";
2 |
3 | export = {
4 | ...contracts,
5 | };
6 |
--------------------------------------------------------------------------------
/src/compound/README.md:
--------------------------------------------------------------------------------
1 | # Compound
2 |
--------------------------------------------------------------------------------
/src/compound/contracts.ts:
--------------------------------------------------------------------------------
1 | import ComptrollerAbi from "./abi/Comptroller.json";
2 | import CompoundPriceOracleAbi from "./abi/CompoundPriceOracle.json";
3 | import CTokenAbi from "./abi/CToken.json";
4 | import CEtherAbi from "./abi/CEther.json";
5 |
6 | const contracts = {
7 | cToken: { abi: CTokenAbi },
8 | comptroller: {
9 | address: "0x3d9819210a31b4961b30ef54be2aed79b9c9cd3b",
10 | abi: ComptrollerAbi,
11 | },
12 | priceOracle: {
13 | address: "0xDDc46a3B076aec7ab3Fc37420A8eDd2959764Ec4",
14 | abi: CompoundPriceOracleAbi,
15 | },
16 | cEther: {
17 | decimals: 8,
18 | address: "0x4Ddc2D193948926D02f9B1fE9e1daa0718270ED5",
19 | abi: CEtherAbi,
20 | },
21 | cDAI: {
22 | decimals: 8,
23 | address: "0x5d3a536E4D6DbD6114cc1Ead35777bAB948E3643",
24 | abi: CTokenAbi,
25 | },
26 | cSAI: {
27 | decimals: 8,
28 | address: "0xf5dce57282a584d2746faf1593d3121fcac444dc",
29 | abi: CTokenAbi,
30 | },
31 | cBAT: {
32 | decimals: 8,
33 | address: "0x6c8c6b02e7b2be14d4fa6022dfd6d75921d90e4e",
34 | abi: CTokenAbi,
35 | },
36 | cZRX: {
37 | decimals: 8,
38 | address: "0xb3319f5d18bc0d84dd1b4825dcde5d5f7266d407",
39 | abi: CTokenAbi,
40 | },
41 | cUSDC: {
42 | decimals: 8,
43 | address: "0x39aa39c021dfbae8fac545936693ac917d5e7563",
44 | abi: CTokenAbi,
45 | },
46 | cREP: {
47 | decimals: 8,
48 | address: "0x158079ee67fce2f58472a96584a73c7ab9ac95c1",
49 | abi: CTokenAbi,
50 | },
51 | cWBTC: {
52 | decimals: 8,
53 | address: "0xc11b1268c1a384e55c48c2391d8d480264a3a7f4",
54 | abi: CTokenAbi,
55 | },
56 | };
57 |
58 | export default contracts;
59 |
--------------------------------------------------------------------------------
/src/compound/contracts/ICEther.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | contract ICEther {
4 | function mint() external payable;
5 | function borrow(uint borrowAmount) external returns (uint);
6 | function redeem(uint redeemTokens) external returns (uint);
7 | function redeemUnderlying(uint redeemAmount) external returns (uint);
8 | function repayBorrow() external payable;
9 | function repayBorrowBehalf(address borrower) external payable;
10 | function borrowBalanceCurrent(address account) external returns (uint);
11 | function borrowBalanceStored(address account) external view returns (uint256);
12 | function balanceOfUnderlying(address account) external returns (uint);
13 | function balanceOf(address owner) external view returns (uint256);
14 | function getAccountSnapshot(address account) external view returns (uint, uint, uint, uint);
15 | }
--------------------------------------------------------------------------------
/src/compound/contracts/ICToken.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | interface ICToken {
4 | function mint(uint mintAmount) external returns (uint);
5 | function redeem(uint redeemTokens) external returns (uint);
6 | function redeemUnderlying(uint redeemAmount) external returns (uint);
7 | function borrow(uint borrowAmount) external returns (uint);
8 | function repayBorrow(uint repayAmount) external returns (uint);
9 | function repayBorrowBehalf(address borrower, uint repayAmount) external returns (uint);
10 | function exchangeRateCurrent() external returns (uint);
11 | function borrowBalanceCurrent(address account) external returns (uint);
12 | function borrowBalanceStored(address account) external view returns (uint256);
13 | function balanceOfUnderlying(address account) external returns (uint);
14 | function getAccountSnapshot(address account) external view returns (uint, uint, uint, uint);
15 |
16 | function underlying() external view returns (address);
17 | function totalSupply() external view returns (uint256);
18 | function balanceOf(address owner) external view returns (uint256 balance);
19 | function allowance(address, address) external view returns (uint);
20 | function approve(address, uint) external;
21 | function transfer(address, uint) external returns (bool);
22 | function transferFrom(address, address, uint) external returns (bool);
23 | }
24 |
--------------------------------------------------------------------------------
/src/compound/contracts/ICompoundPriceOracle.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | contract ICompoundPriceOracle {
4 | function getUnderlyingPrice(address cToken) external view returns (uint256);
5 | }
--------------------------------------------------------------------------------
/src/compound/contracts/IComptroller.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | interface IComptroller {
4 | /**
5 | * @notice Marker function used for light validation when updating the comptroller of a market
6 | * @dev Implementations should simply return true.
7 | * @return true
8 | */
9 | function isComptroller() external view returns (bool);
10 |
11 | /*** Assets You Are In ***/
12 |
13 | function enterMarkets(address[] calldata cTokens) external returns (uint[] memory);
14 | function exitMarket(address cToken) external returns (uint);
15 |
16 | /*** Policy Hooks ***/
17 |
18 | function getAccountLiquidity(address account) external view returns (uint, uint, uint);
19 | function getAssetsIn(address account) external view returns (address[] memory);
20 |
21 | function mintAllowed(address cToken, address minter, uint mintAmount) external returns (uint);
22 | function mintVerify(address cToken, address minter, uint mintAmount, uint mintTokens) external;
23 |
24 | function redeemAllowed(address cToken, address redeemer, uint redeemTokens) external returns (uint);
25 | function redeemVerify(address cToken, address redeemer, uint redeemAmount, uint redeemTokens) external;
26 |
27 | function borrowAllowed(address cToken, address borrower, uint borrowAmount) external returns (uint);
28 | function borrowVerify(address cToken, address borrower, uint borrowAmount) external;
29 |
30 | function repayBorrowAllowed(
31 | address cToken,
32 | address payer,
33 | address borrower,
34 | uint repayAmount) external returns (uint);
35 | function repayBorrowVerify(
36 | address cToken,
37 | address payer,
38 | address borrower,
39 | uint repayAmount,
40 | uint borrowerIndex) external;
41 |
42 | function liquidateBorrowAllowed(
43 | address cTokenBorrowed,
44 | address cTokenCollateral,
45 | address liquidator,
46 | address borrower,
47 | uint repayAmount) external returns (uint);
48 | function liquidateBorrowVerify(
49 | address cTokenBorrowed,
50 | address cTokenCollateral,
51 | address liquidator,
52 | address borrower,
53 | uint repayAmount,
54 | uint seizeTokens) external;
55 |
56 | function seizeAllowed(
57 | address cTokenCollateral,
58 | address cTokenBorrowed,
59 | address liquidator,
60 | address borrower,
61 | uint seizeTokens) external returns (uint);
62 | function seizeVerify(
63 | address cTokenCollateral,
64 | address cTokenBorrowed,
65 | address liquidator,
66 | address borrower,
67 | uint seizeTokens) external;
68 |
69 | function transferAllowed(address cToken, address src, address dst, uint transferTokens) external returns (uint);
70 | function transferVerify(address cToken, address src, address dst, uint transferTokens) external;
71 |
72 | /*** Liquidity/Liquidation Calculations ***/
73 |
74 | function liquidateCalculateSeizeTokens(
75 | address cTokenBorrowed,
76 | address cTokenCollateral,
77 | uint repayAmount) external view returns (uint, uint);
78 | }
--------------------------------------------------------------------------------
/src/compound/index.ts:
--------------------------------------------------------------------------------
1 | import { default as contracts } from "./contracts";
2 |
3 | export = {
4 | ...contracts,
5 | };
6 |
--------------------------------------------------------------------------------
/src/curvefi/abi/PoolToken.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "name": "Transfer",
4 | "inputs": [
5 | { "type": "address", "name": "_from", "indexed": true },
6 | { "type": "address", "name": "_to", "indexed": true },
7 | { "type": "uint256", "name": "_value", "indexed": false }
8 | ],
9 | "anonymous": false,
10 | "type": "event"
11 | },
12 | {
13 | "name": "Approval",
14 | "inputs": [
15 | { "type": "address", "name": "_owner", "indexed": true },
16 | { "type": "address", "name": "_spender", "indexed": true },
17 | { "type": "uint256", "name": "_value", "indexed": false }
18 | ],
19 | "anonymous": false,
20 | "type": "event"
21 | },
22 | {
23 | "outputs": [],
24 | "inputs": [
25 | { "type": "string", "name": "_name" },
26 | { "type": "string", "name": "_symbol" },
27 | { "type": "uint256", "name": "_decimals" },
28 | { "type": "uint256", "name": "_supply" }
29 | ],
30 | "constant": false,
31 | "payable": false,
32 | "type": "constructor"
33 | },
34 | {
35 | "name": "set_minter",
36 | "outputs": [],
37 | "inputs": [{ "type": "address", "name": "_minter" }],
38 | "constant": false,
39 | "payable": false,
40 | "type": "function",
41 | "gas": 36247
42 | },
43 | {
44 | "name": "totalSupply",
45 | "outputs": [{ "type": "uint256", "name": "out" }],
46 | "inputs": [],
47 | "constant": true,
48 | "payable": false,
49 | "type": "function",
50 | "gas": 1181
51 | },
52 | {
53 | "name": "allowance",
54 | "outputs": [{ "type": "uint256", "name": "out" }],
55 | "inputs": [
56 | { "type": "address", "name": "_owner" },
57 | { "type": "address", "name": "_spender" }
58 | ],
59 | "constant": true,
60 | "payable": false,
61 | "type": "function",
62 | "gas": 1519
63 | },
64 | {
65 | "name": "transfer",
66 | "outputs": [{ "type": "bool", "name": "out" }],
67 | "inputs": [
68 | { "type": "address", "name": "_to" },
69 | { "type": "uint256", "name": "_value" }
70 | ],
71 | "constant": false,
72 | "payable": false,
73 | "type": "function",
74 | "gas": 74802
75 | },
76 | {
77 | "name": "transferFrom",
78 | "outputs": [{ "type": "bool", "name": "out" }],
79 | "inputs": [
80 | { "type": "address", "name": "_from" },
81 | { "type": "address", "name": "_to" },
82 | { "type": "uint256", "name": "_value" }
83 | ],
84 | "constant": false,
85 | "payable": false,
86 | "type": "function",
87 | "gas": 111953
88 | },
89 | {
90 | "name": "approve",
91 | "outputs": [{ "type": "bool", "name": "out" }],
92 | "inputs": [
93 | { "type": "address", "name": "_spender" },
94 | { "type": "uint256", "name": "_value" }
95 | ],
96 | "constant": false,
97 | "payable": false,
98 | "type": "function",
99 | "gas": 39012
100 | },
101 | {
102 | "name": "mint",
103 | "outputs": [],
104 | "inputs": [
105 | { "type": "address", "name": "_to" },
106 | { "type": "uint256", "name": "_value" }
107 | ],
108 | "constant": false,
109 | "payable": false,
110 | "type": "function",
111 | "gas": 75733
112 | },
113 | {
114 | "name": "burn",
115 | "outputs": [],
116 | "inputs": [{ "type": "uint256", "name": "_value" }],
117 | "constant": false,
118 | "payable": false,
119 | "type": "function",
120 | "gas": 75605
121 | },
122 | {
123 | "name": "burnFrom",
124 | "outputs": [],
125 | "inputs": [
126 | { "type": "address", "name": "_to" },
127 | { "type": "uint256", "name": "_value" }
128 | ],
129 | "constant": false,
130 | "payable": false,
131 | "type": "function",
132 | "gas": 112752
133 | },
134 | {
135 | "name": "name",
136 | "outputs": [{ "type": "string", "name": "out" }],
137 | "inputs": [],
138 | "constant": true,
139 | "payable": false,
140 | "type": "function",
141 | "gas": 7853
142 | },
143 | {
144 | "name": "symbol",
145 | "outputs": [{ "type": "string", "name": "out" }],
146 | "inputs": [],
147 | "constant": true,
148 | "payable": false,
149 | "type": "function",
150 | "gas": 6906
151 | },
152 | {
153 | "name": "decimals",
154 | "outputs": [{ "type": "uint256", "name": "out" }],
155 | "inputs": [],
156 | "constant": true,
157 | "payable": false,
158 | "type": "function",
159 | "gas": 1511
160 | },
161 | {
162 | "name": "balanceOf",
163 | "outputs": [{ "type": "uint256", "name": "out" }],
164 | "inputs": [{ "type": "address", "name": "arg0" }],
165 | "constant": true,
166 | "payable": false,
167 | "type": "function",
168 | "gas": 1695
169 | }
170 | ]
171 |
--------------------------------------------------------------------------------
/src/curvefi/abi/Zap.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "outputs": [],
4 | "inputs": [
5 | { "type": "address[2]", "name": "_coins" },
6 | { "type": "address[2]", "name": "_underlying_coins" },
7 | { "type": "address", "name": "_curve" },
8 | { "type": "address", "name": "_token" }
9 | ],
10 | "constant": false,
11 | "payable": false,
12 | "type": "constructor"
13 | },
14 | {
15 | "name": "add_liquidity",
16 | "outputs": [],
17 | "inputs": [
18 | { "type": "uint256[2]", "name": "uamounts" },
19 | { "type": "uint256", "name": "min_mint_amount" }
20 | ],
21 | "constant": false,
22 | "payable": false,
23 | "type": "function",
24 | "gas": 117283
25 | },
26 | {
27 | "name": "remove_liquidity",
28 | "outputs": [],
29 | "inputs": [
30 | { "type": "uint256", "name": "_amount" },
31 | { "type": "uint256[2]", "name": "min_uamounts" }
32 | ],
33 | "constant": false,
34 | "payable": false,
35 | "type": "function",
36 | "gas": 83606
37 | },
38 | {
39 | "name": "remove_liquidity_imbalance",
40 | "outputs": [],
41 | "inputs": [
42 | { "type": "uint256[2]", "name": "uamounts" },
43 | { "type": "uint256", "name": "max_burn_amount" }
44 | ],
45 | "constant": false,
46 | "payable": false,
47 | "type": "function",
48 | "gas": 96829
49 | },
50 | {
51 | "name": "calc_withdraw_one_coin",
52 | "outputs": [{ "type": "uint256", "name": "" }],
53 | "inputs": [
54 | { "type": "uint256", "name": "_token_amount" },
55 | { "type": "int128", "name": "i" }
56 | ],
57 | "constant": true,
58 | "payable": false,
59 | "type": "function",
60 | "gas": 2945630
61 | },
62 | {
63 | "name": "remove_liquidity_one_coin",
64 | "outputs": [],
65 | "inputs": [
66 | { "type": "uint256", "name": "_token_amount" },
67 | { "type": "int128", "name": "i" },
68 | { "type": "uint256", "name": "min_uamount" }
69 | ],
70 | "constant": false,
71 | "payable": false,
72 | "type": "function"
73 | },
74 | {
75 | "name": "remove_liquidity_one_coin",
76 | "outputs": [],
77 | "inputs": [
78 | { "type": "uint256", "name": "_token_amount" },
79 | { "type": "int128", "name": "i" },
80 | { "type": "uint256", "name": "min_uamount" },
81 | { "type": "bool", "name": "donate_dust" }
82 | ],
83 | "constant": false,
84 | "payable": false,
85 | "type": "function"
86 | },
87 | {
88 | "name": "withdraw_donated_dust",
89 | "outputs": [],
90 | "inputs": [],
91 | "constant": false,
92 | "payable": false,
93 | "type": "function",
94 | "gas": 63973
95 | },
96 | {
97 | "name": "coins",
98 | "outputs": [{ "type": "address", "name": "" }],
99 | "inputs": [{ "type": "int128", "name": "arg0" }],
100 | "constant": true,
101 | "payable": false,
102 | "type": "function",
103 | "gas": 1680
104 | },
105 | {
106 | "name": "underlying_coins",
107 | "outputs": [{ "type": "address", "name": "" }],
108 | "inputs": [{ "type": "int128", "name": "arg0" }],
109 | "constant": true,
110 | "payable": false,
111 | "type": "function",
112 | "gas": 1710
113 | },
114 | {
115 | "name": "curve",
116 | "outputs": [{ "type": "address", "name": "" }],
117 | "inputs": [],
118 | "constant": true,
119 | "payable": false,
120 | "type": "function",
121 | "gas": 1541
122 | },
123 | {
124 | "name": "token",
125 | "outputs": [{ "type": "address", "name": "" }],
126 | "inputs": [],
127 | "constant": true,
128 | "payable": false,
129 | "type": "function",
130 | "gas": 1571
131 | }
132 | ]
133 |
--------------------------------------------------------------------------------
/src/curvefi/contracts.ts:
--------------------------------------------------------------------------------
1 | import curveAbi from "./abi/Curve.json";
2 | import poolTokenAbi from "./abi/PoolToken.json";
3 | import zapAbi from "./abi/Zap.json";
4 |
5 | // Reference: https://github.com/curvefi/curve-contract/
6 |
7 | const contracts = {
8 | poolTokenAbi,
9 | curveAbi,
10 | zapAbi,
11 | cDai_cUsdc: {
12 | nCoins: 2,
13 | indexes: {
14 | dai: 0,
15 | usdc: 1,
16 | },
17 | zap: {
18 | address: "0xeB21209ae4C2c9FF2a86ACA31E123764A3B6Bc06",
19 | },
20 | curve: {
21 | address: "0xa2b47e3d5c44877cca798226b7b8118f9bfb7a56",
22 | },
23 | poolToken: {
24 | address: "0x845838df265dcd2c412a1dc9e959c7d08537f8a2",
25 | },
26 | },
27 | cDai_cUsdc_Usdt: {
28 | nCoins: 3,
29 | indexes: {
30 | dai: 0,
31 | usdc: 1,
32 | usdt: 2,
33 | },
34 | zap: {
35 | address: "0xac795D2c97e60DF6a99ff1c814727302fD747a80",
36 | },
37 | curve: {
38 | address: "0x52ea46506b9cc5ef470c5bf89f17dc28bb35d85c",
39 | },
40 | poolToken: {
41 | address: "0x9fc689ccada600b6df723d9e47d84d76664a1f23",
42 | },
43 | },
44 | yDai_yUsdc_yUsdt_ytUsd: {
45 | nCoins: 4,
46 | indexes: {
47 | dai: 0,
48 | usdc: 1,
49 | usdt: 2,
50 | tusd: 3,
51 | },
52 | zap: {
53 | address: "0xbBC81d23Ea2c3ec7e56D39296F0cbB648873a5d3",
54 | },
55 | curve: {
56 | address: "0x45f783cce6b7ff23b2ab2d70e416cdb7d6055f51",
57 | },
58 | poolToken: {
59 | address: "0xdf5e0e81dff6faf3a7e52ba697820c5e32d806a8",
60 | },
61 | },
62 | };
63 |
64 | export default contracts;
65 |
--------------------------------------------------------------------------------
/src/curvefi/contracts/ICurveFiCurve.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | contract ICurveFiCurve {
4 | function get_virtual_price() external returns (uint256 out);
5 |
6 | function add_liquidity(uint256[2] calldata amounts, uint256 deadline) external;
7 |
8 | function get_dy(int128 i, int128 j, uint256 dx)
9 | external
10 | returns (uint256 out);
11 |
12 | function get_dy_underlying(int128 i, int128 j, uint256 dx)
13 | external
14 | returns (uint256 out);
15 |
16 | function exchange(
17 | int128 i,
18 | int128 j,
19 | uint256 dx,
20 | uint256 min_dy
21 | ) external;
22 |
23 | function exchange(
24 | int128 i,
25 | int128 j,
26 | uint256 dx,
27 | uint256 min_dy,
28 | uint256 deadline
29 | ) external;
30 |
31 | function exchange_underlying(
32 | int128 i,
33 | int128 j,
34 | uint256 dx,
35 | uint256 min_dy
36 | ) external;
37 |
38 | function exchange_underlying(
39 | int128 i,
40 | int128 j,
41 | uint256 dx,
42 | uint256 min_dy,
43 | uint256 deadline
44 | ) external;
45 |
46 | function remove_liquidity(
47 | uint256 _amount,
48 | uint256 deadline,
49 | uint256[2] calldata min_amounts
50 | ) external;
51 |
52 | function remove_liquidity_imbalance(uint256[2] calldata amounts, uint256 deadline)
53 | external;
54 |
55 | function commit_new_parameters(
56 | int128 amplification,
57 | int128 new_fee,
58 | int128 new_admin_fee
59 | ) external;
60 |
61 | function apply_new_parameters() external;
62 |
63 | function revert_new_parameters() external;
64 |
65 | function commit_transfer_ownership(address _owner) external;
66 |
67 | function apply_transfer_ownership() external;
68 |
69 | function revert_transfer_ownership() external;
70 |
71 | function withdraw_admin_fees() external;
72 |
73 | function coins(int128 arg0) external returns (address out);
74 |
75 | function underlying_coins(int128 arg0) external returns (address out);
76 |
77 | function balances(int128 arg0) external returns (uint256 out);
78 |
79 | function A() external returns (int128 out);
80 |
81 | function fee() external returns (int128 out);
82 |
83 | function admin_fee() external returns (int128 out);
84 |
85 | function owner() external returns (address out);
86 |
87 | function admin_actions_deadline() external returns (uint256 out);
88 |
89 | function transfer_ownership_deadline() external returns (uint256 out);
90 |
91 | function future_A() external returns (int128 out);
92 |
93 | function future_fee() external returns (int128 out);
94 |
95 | function future_admin_fee() external returns (int128 out);
96 |
97 | function future_owner() external returns (address out);
98 | }
99 |
--------------------------------------------------------------------------------
/src/curvefi/contracts/ICurveFiPoolToken.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | contract ICurveFiPoolToken {
4 | function set_minter(address _minter) external;
5 |
6 | function totalSupply() external returns (uint256 out);
7 |
8 | function allowance(address _owner, address _spender)
9 | external
10 | returns (uint256 out);
11 |
12 | function transfer(address _to, uint256 _value) external returns (bool out);
13 |
14 | function transferFrom(address _from, address _to, uint256 _value)
15 | external
16 | returns (bool out);
17 |
18 | function approve(address _spender, uint256 _value)
19 | external
20 | returns (bool out);
21 |
22 | function mint(address _to, uint256 _value) external;
23 |
24 | function burn(uint256 _value) external;
25 |
26 | function burnFrom(address _to, uint256 _value) external;
27 |
28 | function name() external returns (string memory out);
29 |
30 | function symbol() external returns (string memory out);
31 |
32 | function decimals() external returns (uint256 out);
33 |
34 | function balanceOf(address arg0) external returns (uint256 out);
35 | }
36 |
--------------------------------------------------------------------------------
/src/curvefi/contracts/ICurveFiZap.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 |
4 | contract ICurveFiZap {
5 | function add_liquidity(
6 | uint256[2] calldata uamounts,
7 | uint256 min_mint_amount
8 | ) external;
9 |
10 | function remove_liquidity(uint256 _amount, uint256[2] calldata min_uamounts)
11 | external;
12 |
13 | function remove_liquidity_imbalance(
14 | uint256[2] calldata uamounts,
15 | uint256 max_burn_amount
16 | ) external;
17 |
18 | function calc_withdraw_one_coin(uint256 _token_amount, int128 i)
19 | external
20 | returns (uint256);
21 |
22 | function remove_liquidity_one_coin(
23 | uint256 _token_amount,
24 | int128 i,
25 | uint256 min_uamount
26 | ) external;
27 |
28 | function remove_liquidity_one_coin(
29 | uint256 _token_amount,
30 | int128 i,
31 | uint256 min_uamount,
32 | bool donate_dust
33 | ) external;
34 |
35 | function withdraw_donated_dust() external;
36 |
37 | function coins(int128 arg0) external returns (address);
38 |
39 | function underlying_coins(int128 arg0) external returns (address);
40 |
41 | function curve() external returns (address);
42 |
43 | function token() external returns (address);
44 | }
45 |
--------------------------------------------------------------------------------
/src/curvefi/index.ts:
--------------------------------------------------------------------------------
1 | import { default as contracts } from "./contracts";
2 |
3 | export = {
4 | ...contracts,
5 | };
6 |
--------------------------------------------------------------------------------
/src/dappsys/abi/DSProxyFactory.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "inputs": [],
4 | "payable": false,
5 | "stateMutability": "nonpayable",
6 | "type": "constructor"
7 | },
8 | {
9 | "anonymous": false,
10 | "inputs": [
11 | {
12 | "indexed": true,
13 | "internalType": "address",
14 | "name": "sender",
15 | "type": "address"
16 | },
17 | {
18 | "indexed": true,
19 | "internalType": "address",
20 | "name": "owner",
21 | "type": "address"
22 | },
23 | {
24 | "indexed": false,
25 | "internalType": "address",
26 | "name": "proxy",
27 | "type": "address"
28 | },
29 | {
30 | "indexed": false,
31 | "internalType": "address",
32 | "name": "cache",
33 | "type": "address"
34 | }
35 | ],
36 | "name": "Created",
37 | "type": "event"
38 | },
39 | {
40 | "constant": false,
41 | "inputs": [],
42 | "name": "build",
43 | "outputs": [
44 | {
45 | "internalType": "address payable",
46 | "name": "proxy",
47 | "type": "address"
48 | }
49 | ],
50 | "payable": false,
51 | "stateMutability": "nonpayable",
52 | "type": "function"
53 | },
54 | {
55 | "constant": false,
56 | "inputs": [
57 | {
58 | "internalType": "address",
59 | "name": "owner",
60 | "type": "address"
61 | }
62 | ],
63 | "name": "build",
64 | "outputs": [
65 | {
66 | "internalType": "address payable",
67 | "name": "proxy",
68 | "type": "address"
69 | }
70 | ],
71 | "payable": false,
72 | "stateMutability": "nonpayable",
73 | "type": "function"
74 | },
75 | {
76 | "constant": true,
77 | "inputs": [],
78 | "name": "cache",
79 | "outputs": [
80 | {
81 | "internalType": "contract DSProxyCache",
82 | "name": "",
83 | "type": "address"
84 | }
85 | ],
86 | "payable": false,
87 | "stateMutability": "view",
88 | "type": "function"
89 | },
90 | {
91 | "constant": true,
92 | "inputs": [
93 | {
94 | "internalType": "address",
95 | "name": "",
96 | "type": "address"
97 | }
98 | ],
99 | "name": "isProxy",
100 | "outputs": [
101 | {
102 | "internalType": "bool",
103 | "name": "",
104 | "type": "bool"
105 | }
106 | ],
107 | "payable": false,
108 | "stateMutability": "view",
109 | "type": "function"
110 | }
111 | ]
--------------------------------------------------------------------------------
/src/dappsys/contracts.ts:
--------------------------------------------------------------------------------
1 | import dsProxyAbi from "./abi/DSProxy.json";
2 | import dsProxyFactoryAbi from "./abi/DSProxyFactory.json";
3 |
4 | const contracts = {
5 | dsProxy: {
6 | abi: dsProxyAbi,
7 | },
8 | dsProxyFactory: {
9 | abi: dsProxyFactoryAbi,
10 | },
11 | };
12 |
13 | export default contracts;
14 |
--------------------------------------------------------------------------------
/src/dappsys/index.ts:
--------------------------------------------------------------------------------
1 | import { default as contracts } from "./contracts";
2 |
3 | export = {
4 | ...contracts,
5 | };
6 |
--------------------------------------------------------------------------------
/src/dydx/abi/AdminImpl.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "anonymous": false,
4 | "inputs": [
5 | { "indexed": false, "name": "token", "type": "address" },
6 | { "indexed": false, "name": "amount", "type": "uint256" }
7 | ],
8 | "name": "LogWithdrawExcessTokens",
9 | "type": "event"
10 | },
11 | {
12 | "anonymous": false,
13 | "inputs": [
14 | { "indexed": false, "name": "marketId", "type": "uint256" },
15 | { "indexed": false, "name": "token", "type": "address" }
16 | ],
17 | "name": "LogAddMarket",
18 | "type": "event"
19 | },
20 | {
21 | "anonymous": false,
22 | "inputs": [
23 | { "indexed": false, "name": "marketId", "type": "uint256" },
24 | { "indexed": false, "name": "isClosing", "type": "bool" }
25 | ],
26 | "name": "LogSetIsClosing",
27 | "type": "event"
28 | },
29 | {
30 | "anonymous": false,
31 | "inputs": [
32 | { "indexed": false, "name": "marketId", "type": "uint256" },
33 | { "indexed": false, "name": "priceOracle", "type": "address" }
34 | ],
35 | "name": "LogSetPriceOracle",
36 | "type": "event"
37 | },
38 | {
39 | "anonymous": false,
40 | "inputs": [
41 | { "indexed": false, "name": "marketId", "type": "uint256" },
42 | { "indexed": false, "name": "interestSetter", "type": "address" }
43 | ],
44 | "name": "LogSetInterestSetter",
45 | "type": "event"
46 | },
47 | {
48 | "anonymous": false,
49 | "inputs": [
50 | { "indexed": false, "name": "marketId", "type": "uint256" },
51 | {
52 | "components": [{ "name": "value", "type": "uint256" }],
53 | "indexed": false,
54 | "name": "marginPremium",
55 | "type": "tuple"
56 | }
57 | ],
58 | "name": "LogSetMarginPremium",
59 | "type": "event"
60 | },
61 | {
62 | "anonymous": false,
63 | "inputs": [
64 | { "indexed": false, "name": "marketId", "type": "uint256" },
65 | {
66 | "components": [{ "name": "value", "type": "uint256" }],
67 | "indexed": false,
68 | "name": "spreadPremium",
69 | "type": "tuple"
70 | }
71 | ],
72 | "name": "LogSetSpreadPremium",
73 | "type": "event"
74 | },
75 | {
76 | "anonymous": false,
77 | "inputs": [
78 | {
79 | "components": [{ "name": "value", "type": "uint256" }],
80 | "indexed": false,
81 | "name": "marginRatio",
82 | "type": "tuple"
83 | }
84 | ],
85 | "name": "LogSetMarginRatio",
86 | "type": "event"
87 | },
88 | {
89 | "anonymous": false,
90 | "inputs": [
91 | {
92 | "components": [{ "name": "value", "type": "uint256" }],
93 | "indexed": false,
94 | "name": "liquidationSpread",
95 | "type": "tuple"
96 | }
97 | ],
98 | "name": "LogSetLiquidationSpread",
99 | "type": "event"
100 | },
101 | {
102 | "anonymous": false,
103 | "inputs": [
104 | {
105 | "components": [{ "name": "value", "type": "uint256" }],
106 | "indexed": false,
107 | "name": "earningsRate",
108 | "type": "tuple"
109 | }
110 | ],
111 | "name": "LogSetEarningsRate",
112 | "type": "event"
113 | },
114 | {
115 | "anonymous": false,
116 | "inputs": [
117 | {
118 | "components": [{ "name": "value", "type": "uint256" }],
119 | "indexed": false,
120 | "name": "minBorrowedValue",
121 | "type": "tuple"
122 | }
123 | ],
124 | "name": "LogSetMinBorrowedValue",
125 | "type": "event"
126 | },
127 | {
128 | "anonymous": false,
129 | "inputs": [
130 | { "indexed": false, "name": "operator", "type": "address" },
131 | { "indexed": false, "name": "approved", "type": "bool" }
132 | ],
133 | "name": "LogSetGlobalOperator",
134 | "type": "event"
135 | }
136 | ]
137 |
--------------------------------------------------------------------------------
/src/dydx/abi/LiquidatorProxyV1ForSoloMargin.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "constant": true,
4 | "inputs": [],
5 | "name": "SOLO_MARGIN",
6 | "outputs": [{ "name": "", "type": "address" }],
7 | "payable": false,
8 | "stateMutability": "view",
9 | "type": "function"
10 | },
11 | {
12 | "constant": false,
13 | "inputs": [
14 | {
15 | "components": [
16 | { "name": "owner", "type": "address" },
17 | { "name": "number", "type": "uint256" }
18 | ],
19 | "name": "fromAccount",
20 | "type": "tuple"
21 | },
22 | {
23 | "components": [
24 | { "name": "owner", "type": "address" },
25 | { "name": "number", "type": "uint256" }
26 | ],
27 | "name": "liquidAccount",
28 | "type": "tuple"
29 | },
30 | {
31 | "components": [{ "name": "value", "type": "uint256" }],
32 | "name": "minLiquidatorRatio",
33 | "type": "tuple"
34 | },
35 | { "name": "minValueLiquidated", "type": "uint256" },
36 | { "name": "owedPreferences", "type": "uint256[]" },
37 | { "name": "heldPreferences", "type": "uint256[]" }
38 | ],
39 | "name": "liquidate",
40 | "outputs": [],
41 | "payable": false,
42 | "stateMutability": "nonpayable",
43 | "type": "function"
44 | },
45 | {
46 | "inputs": [{ "name": "soloMargin", "type": "address" }],
47 | "payable": false,
48 | "stateMutability": "nonpayable",
49 | "type": "constructor"
50 | }
51 | ]
52 |
--------------------------------------------------------------------------------
/src/dydx/abi/OperationImpl.json:
--------------------------------------------------------------------------------
1 | []
--------------------------------------------------------------------------------
/src/dydx/abi/PayableProxyForSoloMargin.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "constant": true,
4 | "inputs": [],
5 | "name": "SOLO_MARGIN",
6 | "outputs": [{ "name": "", "type": "address" }],
7 | "payable": false,
8 | "stateMutability": "view",
9 | "type": "function"
10 | },
11 | {
12 | "constant": true,
13 | "inputs": [],
14 | "name": "WETH",
15 | "outputs": [{ "name": "", "type": "address" }],
16 | "payable": false,
17 | "stateMutability": "view",
18 | "type": "function"
19 | },
20 | {
21 | "constant": false,
22 | "inputs": [
23 | {
24 | "components": [
25 | { "name": "owner", "type": "address" },
26 | { "name": "number", "type": "uint256" }
27 | ],
28 | "name": "accounts",
29 | "type": "tuple[]"
30 | },
31 | {
32 | "components": [
33 | { "name": "actionType", "type": "uint8" },
34 | { "name": "accountId", "type": "uint256" },
35 | {
36 | "components": [
37 | { "name": "sign", "type": "bool" },
38 | { "name": "denomination", "type": "uint8" },
39 | { "name": "ref", "type": "uint8" },
40 | { "name": "value", "type": "uint256" }
41 | ],
42 | "name": "amount",
43 | "type": "tuple"
44 | },
45 | { "name": "primaryMarketId", "type": "uint256" },
46 | { "name": "secondaryMarketId", "type": "uint256" },
47 | { "name": "otherAddress", "type": "address" },
48 | { "name": "otherAccountId", "type": "uint256" },
49 | { "name": "data", "type": "bytes" }
50 | ],
51 | "name": "actions",
52 | "type": "tuple[]"
53 | },
54 | { "name": "sendEthTo", "type": "address" }
55 | ],
56 | "name": "operate",
57 | "outputs": [],
58 | "payable": true,
59 | "stateMutability": "payable",
60 | "type": "function"
61 | },
62 | {
63 | "inputs": [
64 | { "name": "soloMargin", "type": "address" },
65 | { "name": "weth", "type": "address" }
66 | ],
67 | "payable": false,
68 | "stateMutability": "nonpayable",
69 | "type": "constructor"
70 | },
71 | { "payable": true, "stateMutability": "payable", "type": "fallback" }
72 | ]
73 |
--------------------------------------------------------------------------------
/src/dydx/abi/PolynomialInterestSetter.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "constant": true,
4 | "inputs": [],
5 | "name": "getMaxAPR",
6 | "outputs": [{ "name": "", "type": "uint256" }],
7 | "payable": false,
8 | "stateMutability": "view",
9 | "type": "function"
10 | },
11 | {
12 | "constant": true,
13 | "inputs": [],
14 | "name": "getCoefficients",
15 | "outputs": [{ "name": "", "type": "uint256[]" }],
16 | "payable": false,
17 | "stateMutability": "view",
18 | "type": "function"
19 | },
20 | {
21 | "constant": true,
22 | "inputs": [
23 | { "name": "", "type": "address" },
24 | { "name": "borrowWei", "type": "uint256" },
25 | { "name": "supplyWei", "type": "uint256" }
26 | ],
27 | "name": "getInterestRate",
28 | "outputs": [
29 | {
30 | "components": [{ "name": "value", "type": "uint256" }],
31 | "name": "",
32 | "type": "tuple"
33 | }
34 | ],
35 | "payable": false,
36 | "stateMutability": "view",
37 | "type": "function"
38 | },
39 | {
40 | "inputs": [
41 | {
42 | "components": [
43 | { "name": "maxAPR", "type": "uint128" },
44 | { "name": "coefficients", "type": "uint128" }
45 | ],
46 | "name": "params",
47 | "type": "tuple"
48 | }
49 | ],
50 | "payable": false,
51 | "stateMutability": "nonpayable",
52 | "type": "constructor"
53 | }
54 | ]
55 |
--------------------------------------------------------------------------------
/src/dydx/abi/Refunder.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "constant": true,
4 | "inputs": [{ "name": "", "type": "address" }],
5 | "name": "g_givers",
6 | "outputs": [{ "name": "", "type": "bool" }],
7 | "payable": false,
8 | "stateMutability": "view",
9 | "type": "function"
10 | },
11 | {
12 | "constant": true,
13 | "inputs": [],
14 | "name": "SOLO_MARGIN",
15 | "outputs": [{ "name": "", "type": "address" }],
16 | "payable": false,
17 | "stateMutability": "view",
18 | "type": "function"
19 | },
20 | {
21 | "constant": false,
22 | "inputs": [
23 | { "name": "inputMarketId", "type": "uint256" },
24 | { "name": "", "type": "uint256" },
25 | {
26 | "components": [
27 | { "name": "owner", "type": "address" },
28 | { "name": "number", "type": "uint256" }
29 | ],
30 | "name": "makerAccount",
31 | "type": "tuple"
32 | },
33 | {
34 | "components": [
35 | { "name": "owner", "type": "address" },
36 | { "name": "number", "type": "uint256" }
37 | ],
38 | "name": "takerAccount",
39 | "type": "tuple"
40 | },
41 | {
42 | "components": [
43 | { "name": "sign", "type": "bool" },
44 | { "name": "value", "type": "uint128" }
45 | ],
46 | "name": "",
47 | "type": "tuple"
48 | },
49 | {
50 | "components": [
51 | { "name": "sign", "type": "bool" },
52 | { "name": "value", "type": "uint128" }
53 | ],
54 | "name": "",
55 | "type": "tuple"
56 | },
57 | {
58 | "components": [
59 | { "name": "sign", "type": "bool" },
60 | { "name": "value", "type": "uint256" }
61 | ],
62 | "name": "inputWei",
63 | "type": "tuple"
64 | },
65 | { "name": "", "type": "bytes" }
66 | ],
67 | "name": "getTradeCost",
68 | "outputs": [
69 | {
70 | "components": [
71 | { "name": "sign", "type": "bool" },
72 | { "name": "denomination", "type": "uint8" },
73 | { "name": "ref", "type": "uint8" },
74 | { "name": "value", "type": "uint256" }
75 | ],
76 | "name": "",
77 | "type": "tuple"
78 | }
79 | ],
80 | "payable": false,
81 | "stateMutability": "nonpayable",
82 | "type": "function"
83 | },
84 | {
85 | "constant": false,
86 | "inputs": [{ "name": "giver", "type": "address" }],
87 | "name": "addGiver",
88 | "outputs": [],
89 | "payable": false,
90 | "stateMutability": "nonpayable",
91 | "type": "function"
92 | },
93 | {
94 | "constant": false,
95 | "inputs": [{ "name": "giver", "type": "address" }],
96 | "name": "removeGiver",
97 | "outputs": [],
98 | "payable": false,
99 | "stateMutability": "nonpayable",
100 | "type": "function"
101 | },
102 | {
103 | "constant": false,
104 | "inputs": [],
105 | "name": "renounceOwnership",
106 | "outputs": [],
107 | "payable": false,
108 | "stateMutability": "nonpayable",
109 | "type": "function"
110 | },
111 | {
112 | "constant": true,
113 | "inputs": [],
114 | "name": "owner",
115 | "outputs": [{ "name": "", "type": "address" }],
116 | "payable": false,
117 | "stateMutability": "view",
118 | "type": "function"
119 | },
120 | {
121 | "constant": true,
122 | "inputs": [],
123 | "name": "isOwner",
124 | "outputs": [{ "name": "", "type": "bool" }],
125 | "payable": false,
126 | "stateMutability": "view",
127 | "type": "function"
128 | },
129 | {
130 | "constant": false,
131 | "inputs": [{ "name": "newOwner", "type": "address" }],
132 | "name": "transferOwnership",
133 | "outputs": [],
134 | "payable": false,
135 | "stateMutability": "nonpayable",
136 | "type": "function"
137 | },
138 | {
139 | "inputs": [
140 | { "name": "soloMargin", "type": "address" },
141 | { "name": "givers", "type": "address[]" }
142 | ],
143 | "payable": false,
144 | "stateMutability": "nonpayable",
145 | "type": "constructor"
146 | },
147 | {
148 | "anonymous": false,
149 | "inputs": [{ "indexed": false, "name": "giver", "type": "address" }],
150 | "name": "LogGiverAdded",
151 | "type": "event"
152 | },
153 | {
154 | "anonymous": false,
155 | "inputs": [{ "indexed": false, "name": "giver", "type": "address" }],
156 | "name": "LogGiverRemoved",
157 | "type": "event"
158 | },
159 | {
160 | "anonymous": false,
161 | "inputs": [
162 | {
163 | "components": [
164 | { "name": "owner", "type": "address" },
165 | { "name": "number", "type": "uint256" }
166 | ],
167 | "indexed": false,
168 | "name": "account",
169 | "type": "tuple"
170 | },
171 | { "indexed": false, "name": "marketId", "type": "uint256" },
172 | { "indexed": false, "name": "amount", "type": "uint256" }
173 | ],
174 | "name": "LogRefund",
175 | "type": "event"
176 | },
177 | {
178 | "anonymous": false,
179 | "inputs": [
180 | { "indexed": true, "name": "previousOwner", "type": "address" },
181 | { "indexed": true, "name": "newOwner", "type": "address" }
182 | ],
183 | "name": "OwnershipTransferred",
184 | "type": "event"
185 | }
186 | ]
187 |
--------------------------------------------------------------------------------
/src/dydx/abi/UsdcPriceOracle.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "constant": true,
4 | "inputs": [{ "name": "", "type": "address" }],
5 | "name": "getPrice",
6 | "outputs": [
7 | {
8 | "components": [{ "name": "value", "type": "uint256" }],
9 | "name": "",
10 | "type": "tuple"
11 | }
12 | ],
13 | "payable": false,
14 | "stateMutability": "view",
15 | "type": "function"
16 | },
17 | {
18 | "constant": true,
19 | "inputs": [],
20 | "name": "ONE_DOLLAR",
21 | "outputs": [{ "name": "", "type": "uint256" }],
22 | "payable": false,
23 | "stateMutability": "view",
24 | "type": "function"
25 | }
26 | ]
27 |
--------------------------------------------------------------------------------
/src/dydx/abi/WethPriceOracle.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "constant": true,
4 | "inputs": [{ "name": "", "type": "address" }],
5 | "name": "getPrice",
6 | "outputs": [
7 | {
8 | "components": [{ "name": "value", "type": "uint256" }],
9 | "name": "",
10 | "type": "tuple"
11 | }
12 | ],
13 | "payable": false,
14 | "stateMutability": "view",
15 | "type": "function"
16 | },
17 | {
18 | "constant": true,
19 | "inputs": [],
20 | "name": "ONE_DOLLAR",
21 | "outputs": [{ "name": "", "type": "uint256" }],
22 | "payable": false,
23 | "stateMutability": "view",
24 | "type": "function"
25 | },
26 | {
27 | "constant": true,
28 | "inputs": [],
29 | "name": "MEDIANIZER",
30 | "outputs": [{ "name": "", "type": "address" }],
31 | "payable": false,
32 | "stateMutability": "view",
33 | "type": "function"
34 | },
35 | {
36 | "inputs": [{ "name": "medianizer", "type": "address" }],
37 | "payable": false,
38 | "stateMutability": "nonpayable",
39 | "type": "constructor"
40 | }
41 | ]
42 |
--------------------------------------------------------------------------------
/src/dydx/contracts.ts:
--------------------------------------------------------------------------------
1 | import soloMarginAbi from "./abi/SoloMargin.json";
2 | import payableProxyForSoloMarginAbi from "./abi/PayableProxyForSoloMargin.json";
3 | import polynomialInterestSetterAbi from "./abi/PolynomialInterestSetter.json";
4 | import expiryAbi from "./abi/Expiry.json";
5 | import expiryV2Abi from "./abi/ExpiryV2.json";
6 | import daiPriceOracleAbi from "./abi/DaiPriceOracle.json";
7 | import saiPriceOracleAbi from "./abi/SaiPriceOracle.json";
8 | import wethPriceOracleAbi from "./abi/WethPriceOracle.json";
9 | import usdcPriceOracleAbi from "./abi/UsdcPriceOracle.json";
10 | import adminImplAbi from "./abi/AdminImpl.json";
11 | import operationImplAbi from "./abi/OperationImpl.json";
12 | import liquidatorProxyV1ForSoloMarginAbi from "./abi/LiquidatorProxyV1ForSoloMargin.json";
13 | import limitOrdersAbi from "./abi/LimitOrders.json";
14 | import stopLimitOrdersAbi from "./abi/StopLimitOrders.json";
15 | import canonicalOrdersAbi from "./abi/CanonicalOrders.json";
16 | import signedOperationProxyAbi from "./abi/SignedOperationProxy.json";
17 | import refunderAbi from "./abi/Refunder.json";
18 |
19 | const contracts = {
20 | soloMargin: {
21 | address: "0x1e0447b19bb6ecfdae1e4ae1694b0c3659614e4e",
22 | abi: soloMarginAbi,
23 | },
24 | payableProxyForSoloMargin: {
25 | abi: payableProxyForSoloMarginAbi,
26 | address: "0xa8b39829cE2246f89B31C013b8Cde15506Fb9A76",
27 | },
28 | polynomialInterestSetter: {
29 | abi: polynomialInterestSetterAbi,
30 | address: "0xaEE83ca85Ad63DFA04993adcd76CB2B3589eCa49",
31 | },
32 | expiry: {
33 | abi: expiryAbi,
34 | address: "0x0ECE224FBC24D40B446c6a94a142dc41fAe76f2d",
35 | },
36 | expiryV2: {
37 | abi: expiryV2Abi,
38 | address: "0x739A1DF6725657f6a16dC2d5519DC36FD7911A12",
39 | },
40 | daiPriceOracle: {
41 | abi: daiPriceOracleAbi,
42 | address: "0x0fBd14718d8FAB8f9f40Ee5c5612b1F0717100A2",
43 | },
44 | saiPriceOracle: {
45 | abi: saiPriceOracleAbi,
46 | address: "0x787F552BDC17332c98aA360748884513e3cB401a",
47 | },
48 | wethPriceOracle: {
49 | abi: wethPriceOracleAbi,
50 | address: "0xf61AE328463CD997C7b58e7045CdC613e1cFdb69",
51 | },
52 | usdcPriceOracle: {
53 | abi: usdcPriceOracleAbi,
54 | address: "0x52f1c952A48a4588f9ae615d38cfdbf8dF036e60",
55 | },
56 | adminImpl: {
57 | abi: adminImplAbi,
58 | address: "0x8a6629fEba4196E0A61B8E8C94D4905e525bc055",
59 | },
60 | operationImpl: {
61 | abi: operationImplAbi,
62 | address: "0x56E7d4520ABFECf10b38368b00723d9BD3c21ee1",
63 | },
64 | liquidatorProxyV1ForSoloMargin: {
65 | abi: liquidatorProxyV1ForSoloMarginAbi,
66 | address: "0xD4B6cd147ad8A0D5376b6FDBa85fE8128C6f0686",
67 | },
68 | limitOrders: {
69 | abi: limitOrdersAbi,
70 | address: "0xDEf136D9884528e1EB302f39457af0E4d3AD24EB",
71 | },
72 | stopLimitOrders: {
73 | abi: stopLimitOrdersAbi,
74 | address: "0xbFb635e8c6689ac3874aD9A60FaB1c29270f1710",
75 | },
76 | canonicalOrders: {
77 | abi: canonicalOrdersAbi,
78 | address: "0xCd81398895bEa7AD9EFF273aeFFc41A9d83B4dAD",
79 | },
80 | signedOperationProxy: {
81 | abi: signedOperationProxyAbi,
82 | address: "0x2a842bC64343FAD4Ec4a8424ba7ff3c0A70b6e55",
83 | },
84 | refunder: {
85 | abi: refunderAbi,
86 | address: "0x7454dF5d0758D4E7A538c3aCF4841FA9137F0f74",
87 | },
88 | };
89 |
90 | export default contracts;
91 |
--------------------------------------------------------------------------------
/src/dydx/contracts/DydxFlashloanBase.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 | pragma experimental ABIEncoderV2;
3 |
4 | import "@openzeppelin/contracts/token/ERC20/IERC20.sol";
5 |
6 | import "./ISoloMargin.sol";
7 |
8 |
9 | contract DydxFlashloanBase {
10 | using SafeMath for uint256;
11 |
12 | // -- Internal Helper functions -- //
13 |
14 | function _getMarketIdFromTokenAddress(address _solo, address token)
15 | internal
16 | view
17 | returns (uint256)
18 | {
19 | ISoloMargin solo = ISoloMargin(_solo);
20 |
21 | uint256 numMarkets = solo.getNumMarkets();
22 |
23 | address curToken;
24 | for (uint256 i = 0; i < numMarkets; i++) {
25 | curToken = solo.getMarketTokenAddress(i);
26 |
27 | if (curToken == token) {
28 | return i;
29 | }
30 | }
31 |
32 | revert("No marketId found for provided token");
33 | }
34 |
35 | function _getRepaymentAmountInternal(uint256 amount)
36 | internal
37 | view
38 | returns (uint256)
39 | {
40 | // Needs to be overcollateralize
41 | // Needs to provide +2 wei to be safe
42 | return amount + 2;
43 | }
44 |
45 | function _getAccountInfo() internal view returns (Account.Info memory) {
46 | return Account.Info({owner: address(this), number: 1});
47 | }
48 |
49 | function _getWithdrawAction(uint marketId, uint256 amount)
50 | internal
51 | view
52 | returns (Actions.ActionArgs memory)
53 | {
54 | return
55 | Actions.ActionArgs({
56 | actionType: Actions.ActionType.Withdraw,
57 | accountId: 0,
58 | amount: Types.AssetAmount({
59 | sign: false,
60 | denomination: Types.AssetDenomination.Wei,
61 | ref: Types.AssetReference.Delta,
62 | value: amount
63 | }),
64 | primaryMarketId: marketId,
65 | secondaryMarketId: 0,
66 | otherAddress: address(this),
67 | otherAccountId: 0,
68 | data: ""
69 | });
70 | }
71 |
72 | function _getCallAction(bytes memory data)
73 | internal
74 | view
75 | returns (Actions.ActionArgs memory)
76 | {
77 | return
78 | Actions.ActionArgs({
79 | actionType: Actions.ActionType.Call,
80 | accountId: 0,
81 | amount: Types.AssetAmount({
82 | sign: false,
83 | denomination: Types.AssetDenomination.Wei,
84 | ref: Types.AssetReference.Delta,
85 | value: 0
86 | }),
87 | primaryMarketId: 0,
88 | secondaryMarketId: 0,
89 | otherAddress: address(this),
90 | otherAccountId: 0,
91 | data: data
92 | });
93 | }
94 |
95 | function _getDepositAction(uint marketId, uint256 amount)
96 | internal
97 | view
98 | returns (Actions.ActionArgs memory)
99 | {
100 | return
101 | Actions.ActionArgs({
102 | actionType: Actions.ActionType.Deposit,
103 | accountId: 0,
104 | amount: Types.AssetAmount({
105 | sign: true,
106 | denomination: Types.AssetDenomination.Wei,
107 | ref: Types.AssetReference.Delta,
108 | value: amount
109 | }),
110 | primaryMarketId: marketId,
111 | secondaryMarketId: 0,
112 | otherAddress: address(this),
113 | otherAccountId: 0,
114 | data: ""
115 | });
116 | }
117 | }
118 |
--------------------------------------------------------------------------------
/src/dydx/contracts/ICallee.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 | pragma experimental ABIEncoderV2;
3 |
4 | import { Account } from "./ISoloMargin.sol";
5 |
6 |
7 | /**
8 | * @title ICallee
9 | * @author dYdX
10 | *
11 | * Interface that Callees for Solo must implement in order to ingest data.
12 | */
13 | contract ICallee {
14 |
15 | // ============ Public Functions ============
16 |
17 | /**
18 | * Allows users to send this contract arbitrary data.
19 | *
20 | * @param sender The msg.sender to Solo
21 | * @param accountInfo The account from which the data is being sent
22 | * @param data Arbitrary data given by the sender
23 | */
24 | function callFunction(
25 | address sender,
26 | Account.Info memory accountInfo,
27 | bytes memory data
28 | )
29 | public;
30 | }
--------------------------------------------------------------------------------
/src/dydx/index.ts:
--------------------------------------------------------------------------------
1 | import { default as contracts } from "./contracts";
2 |
3 | export = {
4 | ...contracts,
5 | };
6 |
--------------------------------------------------------------------------------
/src/erc20/README.md:
--------------------------------------------------------------------------------
1 | # ERC20 Token
2 |
--------------------------------------------------------------------------------
/src/erc20/abi/WETH.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "constant": true,
4 | "inputs": [],
5 | "name": "name",
6 | "outputs": [{ "name": "", "type": "string" }],
7 | "payable": false,
8 | "stateMutability": "view",
9 | "type": "function"
10 | },
11 | {
12 | "constant": false,
13 | "inputs": [
14 | { "name": "guy", "type": "address" },
15 | { "name": "wad", "type": "uint256" }
16 | ],
17 | "name": "approve",
18 | "outputs": [{ "name": "", "type": "bool" }],
19 | "payable": false,
20 | "stateMutability": "nonpayable",
21 | "type": "function"
22 | },
23 | {
24 | "constant": true,
25 | "inputs": [],
26 | "name": "totalSupply",
27 | "outputs": [{ "name": "", "type": "uint256" }],
28 | "payable": false,
29 | "stateMutability": "view",
30 | "type": "function"
31 | },
32 | {
33 | "constant": false,
34 | "inputs": [
35 | { "name": "src", "type": "address" },
36 | { "name": "dst", "type": "address" },
37 | { "name": "wad", "type": "uint256" }
38 | ],
39 | "name": "transferFrom",
40 | "outputs": [{ "name": "", "type": "bool" }],
41 | "payable": false,
42 | "stateMutability": "nonpayable",
43 | "type": "function"
44 | },
45 | {
46 | "constant": false,
47 | "inputs": [{ "name": "wad", "type": "uint256" }],
48 | "name": "withdraw",
49 | "outputs": [],
50 | "payable": false,
51 | "stateMutability": "nonpayable",
52 | "type": "function"
53 | },
54 | {
55 | "constant": true,
56 | "inputs": [],
57 | "name": "decimals",
58 | "outputs": [{ "name": "", "type": "uint8" }],
59 | "payable": false,
60 | "stateMutability": "view",
61 | "type": "function"
62 | },
63 | {
64 | "constant": true,
65 | "inputs": [{ "name": "", "type": "address" }],
66 | "name": "balanceOf",
67 | "outputs": [{ "name": "", "type": "uint256" }],
68 | "payable": false,
69 | "stateMutability": "view",
70 | "type": "function"
71 | },
72 | {
73 | "constant": true,
74 | "inputs": [],
75 | "name": "symbol",
76 | "outputs": [{ "name": "", "type": "string" }],
77 | "payable": false,
78 | "stateMutability": "view",
79 | "type": "function"
80 | },
81 | {
82 | "constant": false,
83 | "inputs": [
84 | { "name": "dst", "type": "address" },
85 | { "name": "wad", "type": "uint256" }
86 | ],
87 | "name": "transfer",
88 | "outputs": [{ "name": "", "type": "bool" }],
89 | "payable": false,
90 | "stateMutability": "nonpayable",
91 | "type": "function"
92 | },
93 | {
94 | "constant": false,
95 | "inputs": [],
96 | "name": "deposit",
97 | "outputs": [],
98 | "payable": true,
99 | "stateMutability": "payable",
100 | "type": "function"
101 | },
102 | {
103 | "constant": true,
104 | "inputs": [
105 | { "name": "", "type": "address" },
106 | { "name": "", "type": "address" }
107 | ],
108 | "name": "allowance",
109 | "outputs": [{ "name": "", "type": "uint256" }],
110 | "payable": false,
111 | "stateMutability": "view",
112 | "type": "function"
113 | },
114 | { "payable": true, "stateMutability": "payable", "type": "fallback" },
115 | {
116 | "anonymous": false,
117 | "inputs": [
118 | { "indexed": true, "name": "src", "type": "address" },
119 | { "indexed": true, "name": "guy", "type": "address" },
120 | { "indexed": false, "name": "wad", "type": "uint256" }
121 | ],
122 | "name": "Approval",
123 | "type": "event"
124 | },
125 | {
126 | "anonymous": false,
127 | "inputs": [
128 | { "indexed": true, "name": "src", "type": "address" },
129 | { "indexed": true, "name": "dst", "type": "address" },
130 | { "indexed": false, "name": "wad", "type": "uint256" }
131 | ],
132 | "name": "Transfer",
133 | "type": "event"
134 | },
135 | {
136 | "anonymous": false,
137 | "inputs": [
138 | { "indexed": true, "name": "dst", "type": "address" },
139 | { "indexed": false, "name": "wad", "type": "uint256" }
140 | ],
141 | "name": "Deposit",
142 | "type": "event"
143 | },
144 | {
145 | "anonymous": false,
146 | "inputs": [
147 | { "indexed": true, "name": "src", "type": "address" },
148 | { "indexed": false, "name": "wad", "type": "uint256" }
149 | ],
150 | "name": "Withdrawal",
151 | "type": "event"
152 | }
153 | ]
154 |
--------------------------------------------------------------------------------
/src/erc20/index.ts:
--------------------------------------------------------------------------------
1 | import { default as tokens } from "./tokens";
2 | import abi from "./abi/ERC20.json";
3 |
4 | export = {
5 | ...tokens,
6 | abi,
7 | };
8 |
--------------------------------------------------------------------------------
/src/erc20/tokens.ts:
--------------------------------------------------------------------------------
1 | import ERC20Abi from "./abi/ERC20.json";
2 | import WETHAbi from "./abi/WETH.json";
3 |
4 | const tokens = {
5 | eth: {
6 | symbol: "ETH",
7 | decimals: 18,
8 | address: "0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE",
9 | },
10 | bat: {
11 | symbol: "BAT",
12 | decimals: 18,
13 | address: "0x0d8775f648430679a709e98d2b0cb6250d2887ef",
14 | abi: ERC20Abi,
15 | },
16 | dai: {
17 | symbol: "DAI",
18 | decimals: 18,
19 | address: "0x6B175474E89094C44Da98b954EedeAC495271d0F",
20 | abi: ERC20Abi,
21 | },
22 | rep: {
23 | symbol: "REP",
24 | decimals: 18,
25 | address: "0x1985365e9f78359a9B6AD760e32412f4a445E862",
26 | abi: ERC20Abi,
27 | },
28 | sai: {
29 | symbol: "SAI",
30 | decimals: 18,
31 | address: "0x89d24a6b4ccb1b6faa2625fe562bdd9a23260359",
32 | abi: ERC20Abi,
33 | },
34 | snx: {
35 | symbol: "SNX",
36 | decimals: 18,
37 | address: "0xc011a73ee8576fb46f5e1c5751ca3b9fe0af2a6f",
38 | abi: ERC20Abi,
39 | },
40 | usdc: {
41 | symbol: "USDC",
42 | decimals: 6,
43 | address: "0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48",
44 | abi: ERC20Abi,
45 | },
46 | weth: {
47 | symbol: "WETH",
48 | decimals: 18,
49 | address: "0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2",
50 | abi: WETHAbi,
51 | },
52 | wbtc: {
53 | symbol: "WBTC",
54 | decimals: 8,
55 | address: "0x2260fac5e5542a773aa44fbcfedf7c193bc2c599",
56 | abi: ERC20Abi,
57 | },
58 | zrx: {
59 | symbol: "ZRX",
60 | decimals: 18,
61 | address: "0xE41d2489571d322189246DaFA5ebDe1F4699F498",
62 | abi: ERC20Abi,
63 | },
64 | bal: {
65 | symbol: "BAL",
66 | decimals: 18,
67 | address: "0xba100000625a3754423978a60c9317c58a424e3D",
68 | abi: ERC20Abi,
69 | },
70 | };
71 |
72 | export default tokens;
73 |
--------------------------------------------------------------------------------
/src/idle/contracts.ts:
--------------------------------------------------------------------------------
1 | const contracts = {
2 | maxYield: {
3 | dai: {
4 | address: "0x78751B12Da02728F467A44eAc40F5cbc16Bd7934",
5 | },
6 | usdc: {
7 | address: "0x12B98C621E8754Ae70d0fDbBC73D6208bC3e3cA6",
8 | },
9 | usdt: {
10 | address: "0x63D27B3DA94A9E871222CB0A32232674B02D2f2D",
11 | },
12 | susd: {
13 | address: "0xE79E177d2a5c7085027d7C64c8F271c81430fc9b",
14 | },
15 | tusd: {
16 | address: "0x51C77689A9c2e8cCBEcD4eC9770a1fA5fA83EeF1",
17 | },
18 | wbtc: {
19 | address: "0xD6f279B7ccBCD70F8be439d25B9Df93AEb60eC55",
20 | },
21 | },
22 | riskAdjusted: {
23 | dai: {
24 | address: "0x1846bdfDB6A0f5c473dEc610144513bd071999fB",
25 | },
26 | usdc: {
27 | address: "0xcDdB1Bceb7a1979C6caa0229820707429dd3Ec6C",
28 | },
29 | usdt: {
30 | address: "0x42740698959761BAF1B06baa51EfBD88CB1D862B",
31 | },
32 | },
33 | };
34 |
35 | export default contracts;
36 |
--------------------------------------------------------------------------------
/src/idle/index.ts:
--------------------------------------------------------------------------------
1 | import { default as contracts } from "./contracts";
2 | import abi from "./abi/IdleTokenV3.json";
3 |
4 | export = {
5 | ...contracts,
6 | abi,
7 | decimals: 18,
8 | };
9 |
--------------------------------------------------------------------------------
/src/index.ts:
--------------------------------------------------------------------------------
1 | import { default as aave } from "./aave";
2 | import { default as balancer } from "./balancer";
3 | import { default as compound } from "./compound";
4 | import { default as curvefi } from "./curvefi";
5 | import { default as dappsys } from "./dappsys";
6 | import { default as dydx } from "./dydx";
7 | import { default as erc20 } from "./erc20";
8 | import { default as idle } from "./idle";
9 | import { default as kyber } from "./kyber";
10 | import { default as maker } from "./maker";
11 | import { default as mstable } from "./mstable";
12 | import { default as onesplit } from "./onesplit";
13 | import { default as synthetix } from "./synthetix";
14 | import { default as uma } from "./uma";
15 | import { default as uniswap } from "./uniswap";
16 | import { default as uniswapV2 } from "./uniswapV2";
17 |
18 | export const legos = {
19 | aave,
20 | balancer,
21 | compound,
22 | curvefi,
23 | dappsys,
24 | dydx,
25 | erc20,
26 | idle,
27 | kyber,
28 | maker,
29 | mstable,
30 | onesplit,
31 | synthetix,
32 | uma,
33 | uniswap,
34 | uniswapV2,
35 | };
36 |
--------------------------------------------------------------------------------
/src/kyber/contracts.ts:
--------------------------------------------------------------------------------
1 | import networkProxyAbi from "./abi/KyberNetworkProxy.json";
2 |
3 | const contracts = {
4 | network: {
5 | address: "0x818E6FECD516Ecc3849DAf6845e3EC868087B755",
6 | abi: networkProxyAbi,
7 | },
8 | };
9 |
10 | export default contracts;
11 |
--------------------------------------------------------------------------------
/src/kyber/contracts/KyberNetworkProxy.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | // Note: Kyber uses it owns ERC20 interface
4 | // See: https://github.com/KyberNetwork/smart-contracts/blob/master/contracts/ERC20Interface.sol
5 | import { IERC20 as ERC20 } from "@openzeppelin/contracts/token/ERC20/IERC20.sol";
6 |
7 | interface KyberNetworkProxyInterface {
8 | function maxGasPrice() external view returns(uint);
9 | function getUserCapInWei(address user) external view returns(uint);
10 | function getUserCapInTokenWei(address user, ERC20 token) external view returns(uint);
11 | function enabled() external view returns(bool);
12 | function info(bytes32 id) external view returns(uint);
13 |
14 | function getExpectedRate(ERC20 src, ERC20 dest, uint srcQty) external view
15 | returns (uint expectedRate, uint slippageRate);
16 |
17 | function tradeWithHint(ERC20 src, uint srcAmount, ERC20 dest, address destAddress, uint maxDestAmount,
18 | uint minConversionRate, address walletId, bytes calldata hint) external payable returns(uint);
19 | }
20 |
21 | interface SimpleNetworkInterface {
22 | function swapTokenToToken(ERC20 src, uint srcAmount, ERC20 dest, uint minConversionRate) external returns(uint);
23 | function swapEtherToToken(ERC20 token, uint minConversionRate) external payable returns(uint);
24 | function swapTokenToEther(ERC20 token, uint srcAmount, uint minConversionRate) external returns(uint);
25 | }
26 |
27 | contract KyberNetworkProxy is KyberNetworkProxyInterface, SimpleNetworkInterface {}
--------------------------------------------------------------------------------
/src/kyber/index.ts:
--------------------------------------------------------------------------------
1 | import { default as contracts } from "./contracts";
2 |
3 | export = {
4 | ...contracts,
5 | };
6 |
--------------------------------------------------------------------------------
/src/maker/abi/Medianizer.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "constant": false,
4 | "inputs": [{ "name": "owner_", "type": "address" }],
5 | "name": "setOwner",
6 | "outputs": [],
7 | "payable": false,
8 | "type": "function"
9 | },
10 | {
11 | "constant": false,
12 | "inputs": [{ "name": "", "type": "bytes32" }],
13 | "name": "poke",
14 | "outputs": [],
15 | "payable": false,
16 | "type": "function"
17 | },
18 | {
19 | "constant": false,
20 | "inputs": [],
21 | "name": "poke",
22 | "outputs": [],
23 | "payable": false,
24 | "type": "function"
25 | },
26 | {
27 | "constant": true,
28 | "inputs": [],
29 | "name": "compute",
30 | "outputs": [
31 | { "name": "", "type": "bytes32" },
32 | { "name": "", "type": "bool" }
33 | ],
34 | "payable": false,
35 | "type": "function"
36 | },
37 | {
38 | "constant": false,
39 | "inputs": [{ "name": "wat", "type": "address" }],
40 | "name": "set",
41 | "outputs": [],
42 | "payable": false,
43 | "type": "function"
44 | },
45 | {
46 | "constant": false,
47 | "inputs": [{ "name": "wat", "type": "address" }],
48 | "name": "unset",
49 | "outputs": [],
50 | "payable": false,
51 | "type": "function"
52 | },
53 | {
54 | "constant": true,
55 | "inputs": [{ "name": "", "type": "address" }],
56 | "name": "indexes",
57 | "outputs": [{ "name": "", "type": "bytes12" }],
58 | "payable": false,
59 | "type": "function"
60 | },
61 | {
62 | "constant": true,
63 | "inputs": [],
64 | "name": "next",
65 | "outputs": [{ "name": "", "type": "bytes12" }],
66 | "payable": false,
67 | "type": "function"
68 | },
69 | {
70 | "constant": true,
71 | "inputs": [],
72 | "name": "read",
73 | "outputs": [{ "name": "", "type": "bytes32" }],
74 | "payable": false,
75 | "type": "function"
76 | },
77 | {
78 | "constant": true,
79 | "inputs": [],
80 | "name": "peek",
81 | "outputs": [
82 | { "name": "", "type": "bytes32" },
83 | { "name": "", "type": "bool" }
84 | ],
85 | "payable": false,
86 | "type": "function"
87 | },
88 | {
89 | "constant": true,
90 | "inputs": [{ "name": "", "type": "bytes12" }],
91 | "name": "values",
92 | "outputs": [{ "name": "", "type": "address" }],
93 | "payable": false,
94 | "type": "function"
95 | },
96 | {
97 | "constant": false,
98 | "inputs": [{ "name": "min_", "type": "uint96" }],
99 | "name": "setMin",
100 | "outputs": [],
101 | "payable": false,
102 | "type": "function"
103 | },
104 | {
105 | "constant": false,
106 | "inputs": [{ "name": "authority_", "type": "address" }],
107 | "name": "setAuthority",
108 | "outputs": [],
109 | "payable": false,
110 | "type": "function"
111 | },
112 | {
113 | "constant": true,
114 | "inputs": [],
115 | "name": "owner",
116 | "outputs": [{ "name": "", "type": "address" }],
117 | "payable": false,
118 | "type": "function"
119 | },
120 | {
121 | "constant": false,
122 | "inputs": [],
123 | "name": "void",
124 | "outputs": [],
125 | "payable": false,
126 | "type": "function"
127 | },
128 | {
129 | "constant": false,
130 | "inputs": [
131 | { "name": "pos", "type": "bytes12" },
132 | { "name": "wat", "type": "address" }
133 | ],
134 | "name": "set",
135 | "outputs": [],
136 | "payable": false,
137 | "type": "function"
138 | },
139 | {
140 | "constant": true,
141 | "inputs": [],
142 | "name": "authority",
143 | "outputs": [{ "name": "", "type": "address" }],
144 | "payable": false,
145 | "type": "function"
146 | },
147 | {
148 | "constant": false,
149 | "inputs": [{ "name": "pos", "type": "bytes12" }],
150 | "name": "unset",
151 | "outputs": [],
152 | "payable": false,
153 | "type": "function"
154 | },
155 | {
156 | "constant": false,
157 | "inputs": [{ "name": "next_", "type": "bytes12" }],
158 | "name": "setNext",
159 | "outputs": [],
160 | "payable": false,
161 | "type": "function"
162 | },
163 | {
164 | "constant": true,
165 | "inputs": [],
166 | "name": "min",
167 | "outputs": [{ "name": "", "type": "uint96" }],
168 | "payable": false,
169 | "type": "function"
170 | },
171 | {
172 | "anonymous": true,
173 | "inputs": [
174 | { "indexed": true, "name": "sig", "type": "bytes4" },
175 | { "indexed": true, "name": "guy", "type": "address" },
176 | { "indexed": true, "name": "foo", "type": "bytes32" },
177 | { "indexed": true, "name": "bar", "type": "bytes32" },
178 | { "indexed": false, "name": "wad", "type": "uint256" },
179 | { "indexed": false, "name": "fax", "type": "bytes" }
180 | ],
181 | "name": "LogNote",
182 | "type": "event"
183 | },
184 | {
185 | "anonymous": false,
186 | "inputs": [{ "indexed": true, "name": "authority", "type": "address" }],
187 | "name": "LogSetAuthority",
188 | "type": "event"
189 | },
190 | {
191 | "anonymous": false,
192 | "inputs": [{ "indexed": true, "name": "owner", "type": "address" }],
193 | "name": "LogSetOwner",
194 | "type": "event"
195 | }
196 | ]
197 |
--------------------------------------------------------------------------------
/src/maker/abi/ProxyRegistry.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "inputs": [
4 | {
5 | "internalType": "address",
6 | "name": "factory_",
7 | "type": "address"
8 | }
9 | ],
10 | "payable": false,
11 | "stateMutability": "nonpayable",
12 | "type": "constructor"
13 | },
14 | {
15 | "constant": false,
16 | "inputs": [],
17 | "name": "build",
18 | "outputs": [
19 | {
20 | "internalType": "address payable",
21 | "name": "proxy",
22 | "type": "address"
23 | }
24 | ],
25 | "payable": false,
26 | "stateMutability": "nonpayable",
27 | "type": "function"
28 | },
29 | {
30 | "constant": false,
31 | "inputs": [
32 | {
33 | "internalType": "address",
34 | "name": "owner",
35 | "type": "address"
36 | }
37 | ],
38 | "name": "build",
39 | "outputs": [
40 | {
41 | "internalType": "address payable",
42 | "name": "proxy",
43 | "type": "address"
44 | }
45 | ],
46 | "payable": false,
47 | "stateMutability": "nonpayable",
48 | "type": "function"
49 | },
50 | {
51 | "constant": true,
52 | "inputs": [
53 | {
54 | "internalType": "address",
55 | "name": "",
56 | "type": "address"
57 | }
58 | ],
59 | "name": "proxies",
60 | "outputs": [
61 | {
62 | "internalType": "contract DSProxy",
63 | "name": "",
64 | "type": "address"
65 | }
66 | ],
67 | "payable": false,
68 | "stateMutability": "view",
69 | "type": "function"
70 | }
71 | ]
--------------------------------------------------------------------------------
/src/maker/contracts.ts:
--------------------------------------------------------------------------------
1 | import makerProxyRegistryAbi from "./abi/ProxyRegistry.json";
2 | import dssCdpManagerAbi from "./abi/DssCdpManager.json";
3 | import dssProxyActionsAbi from "./abi/DssProxyActions.json";
4 |
5 | // Reference: https://changelog.makerdao.com/
6 |
7 | const contracts = {
8 | proxyRegistry: {
9 | address: "0x4678f0a6958e4D2Bc4F1BAF7Bc52E8F3564f3fE4",
10 | abi: makerProxyRegistryAbi,
11 | },
12 | dssCdpManager: {
13 | address: "0x5ef30b9986345249bc32d8928B7ee64DE9435E39",
14 | abi: dssCdpManagerAbi,
15 | },
16 | dssProxyActions: {
17 | address: "0x82ecd135dce65fbc6dbdd0e4237e0af93ffd5038",
18 | abi: dssProxyActionsAbi,
19 | },
20 | jug: {
21 | address: "0x19c0976f590D67707E62397C87829d896Dc0f1F1",
22 | },
23 | daiJoin: {
24 | address: "0x9759A6Ac90977b93B58547b4A71c78317f391A28",
25 | },
26 | batAJoin: {
27 | address: "0x3D0B1912B66114d4096F48A8CEe3A56C231772cA",
28 | },
29 | ethAJoin: {
30 | address: "0x2F0b23f53734252Bda2277357e97e1517d6B042A",
31 | },
32 | usdcJoin: {
33 | address: "0xA191e578a6736167326d05c119CE0c90849E84B7",
34 | },
35 | };
36 |
37 | export default contracts;
38 |
--------------------------------------------------------------------------------
/src/maker/contracts/IMedianizer.sol:
--------------------------------------------------------------------------------
1 | interface IMedianizer {
2 | function setOwner(address owner_) external;
3 |
4 | function poke(bytes32) external;
5 |
6 | function poke() external;
7 |
8 | function compute() external returns (bytes32, bool);
9 |
10 | function set(address wat) external;
11 |
12 | function unset(address wat) external;
13 |
14 | function indexes(address) external returns (bytes12);
15 |
16 | function next() external returns (bytes12);
17 |
18 | function read() external returns (bytes32);
19 |
20 | function peek() external returns (bytes32, bool);
21 |
22 | function values(bytes12) external returns (address);
23 |
24 | function setMin(uint96 min_) external;
25 |
26 | function setAuthority(address authority_) external;
27 |
28 | function owner() external returns (address);
29 |
30 | function void() external;
31 |
32 | function set(bytes12 pos, address wat) external;
33 |
34 | function authority() external returns (address);
35 |
36 | function unset(bytes12 pos) external;
37 |
38 | function setNext(bytes12 next_) external;
39 |
40 | function min() external returns (uint96);
41 | }
42 |
--------------------------------------------------------------------------------
/src/maker/ilks.ts:
--------------------------------------------------------------------------------
1 | import erc20 from "../erc20";
2 |
3 | const ilks = {
4 | batA: {
5 | symbol: "BAT-A",
6 | token: { address: erc20.bat.address },
7 | },
8 | ethA: {
9 | symbol: "ETH-A",
10 | token: { address: erc20.eth.address },
11 | },
12 | usdcA: {
13 | symbol: "USDC-A",
14 | token: { address: erc20.usdc.address },
15 | },
16 | };
17 |
18 | export default ilks;
19 |
--------------------------------------------------------------------------------
/src/maker/index.ts:
--------------------------------------------------------------------------------
1 | import { default as contracts } from "./contracts";
2 | import { default as ilks } from "./ilks";
3 | import { default as priceFeeds } from "./priceFeeds";
4 |
5 | export = {
6 | ...contracts,
7 | ...ilks,
8 | ...priceFeeds
9 | };
10 |
--------------------------------------------------------------------------------
/src/maker/priceFeeds.ts:
--------------------------------------------------------------------------------
1 | import medianizerAbi from "./abi/Medianizer.json";
2 |
3 | const priceFeeds = {
4 | ethUsdPriceFeed: {
5 | address: "0x729d19f657bd0614b4985cf1d82531c67569197b",
6 | abi: medianizerAbi,
7 | }
8 | };
9 |
10 | export default priceFeeds;
11 |
--------------------------------------------------------------------------------
/src/mstable/abi/MassetValidationHelper.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "constant": true,
4 | "inputs": [
5 | { "internalType": "address", "name": "_mAsset", "type": "address" },
6 | { "internalType": "address", "name": "_input", "type": "address" },
7 | { "internalType": "address", "name": "_output", "type": "address" }
8 | ],
9 | "name": "getMaxSwap",
10 | "outputs": [
11 | { "internalType": "bool", "name": "", "type": "bool" },
12 | { "internalType": "string", "name": "", "type": "string" },
13 | { "internalType": "uint256", "name": "", "type": "uint256" },
14 | { "internalType": "uint256", "name": "", "type": "uint256" }
15 | ],
16 | "payable": false,
17 | "stateMutability": "view",
18 | "type": "function"
19 | },
20 | {
21 | "constant": true,
22 | "inputs": [
23 | { "internalType": "address", "name": "_mAsset", "type": "address" },
24 | {
25 | "internalType": "uint256",
26 | "name": "_mAssetQuantity",
27 | "type": "uint256"
28 | },
29 | { "internalType": "address", "name": "_outputBasset", "type": "address" }
30 | ],
31 | "name": "getRedeemValidity",
32 | "outputs": [
33 | { "internalType": "bool", "name": "", "type": "bool" },
34 | { "internalType": "string", "name": "", "type": "string" },
35 | { "internalType": "uint256", "name": "output", "type": "uint256" },
36 | {
37 | "internalType": "uint256",
38 | "name": "bassetQuantityArg",
39 | "type": "uint256"
40 | }
41 | ],
42 | "payable": false,
43 | "stateMutability": "view",
44 | "type": "function"
45 | },
46 | {
47 | "constant": true,
48 | "inputs": [
49 | { "internalType": "address", "name": "_mAsset", "type": "address" }
50 | ],
51 | "name": "suggestMintAsset",
52 | "outputs": [
53 | { "internalType": "bool", "name": "", "type": "bool" },
54 | { "internalType": "string", "name": "", "type": "string" },
55 | { "internalType": "address", "name": "", "type": "address" }
56 | ],
57 | "payable": false,
58 | "stateMutability": "view",
59 | "type": "function"
60 | },
61 | {
62 | "constant": true,
63 | "inputs": [
64 | { "internalType": "address", "name": "_mAsset", "type": "address" }
65 | ],
66 | "name": "suggestRedeemAsset",
67 | "outputs": [
68 | { "internalType": "bool", "name": "", "type": "bool" },
69 | { "internalType": "string", "name": "", "type": "string" },
70 | { "internalType": "address", "name": "", "type": "address" }
71 | ],
72 | "payable": false,
73 | "stateMutability": "view",
74 | "type": "function"
75 | }
76 | ]
77 |
--------------------------------------------------------------------------------
/src/mstable/abi/RewardsDistributor.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "inputs": [
4 | {
5 | "internalType": "address",
6 | "name": "_nexus",
7 | "type": "address"
8 | },
9 | {
10 | "internalType": "address[]",
11 | "name": "_fundManagers",
12 | "type": "address[]"
13 | }
14 | ],
15 | "payable": false,
16 | "stateMutability": "nonpayable",
17 | "type": "constructor"
18 | },
19 | {
20 | "anonymous": false,
21 | "inputs": [
22 | {
23 | "indexed": false,
24 | "internalType": "address",
25 | "name": "funder",
26 | "type": "address"
27 | },
28 | {
29 | "indexed": false,
30 | "internalType": "address",
31 | "name": "recipient",
32 | "type": "address"
33 | },
34 | {
35 | "indexed": false,
36 | "internalType": "address",
37 | "name": "rewardToken",
38 | "type": "address"
39 | },
40 | {
41 | "indexed": false,
42 | "internalType": "uint256",
43 | "name": "amount",
44 | "type": "uint256"
45 | }
46 | ],
47 | "name": "DistributedReward",
48 | "type": "event"
49 | },
50 | {
51 | "anonymous": false,
52 | "inputs": [
53 | {
54 | "indexed": true,
55 | "internalType": "address",
56 | "name": "_address",
57 | "type": "address"
58 | }
59 | ],
60 | "name": "RemovedFundManager",
61 | "type": "event"
62 | },
63 | {
64 | "anonymous": false,
65 | "inputs": [
66 | {
67 | "indexed": true,
68 | "internalType": "address",
69 | "name": "_address",
70 | "type": "address"
71 | }
72 | ],
73 | "name": "Whitelisted",
74 | "type": "event"
75 | },
76 | {
77 | "constant": true,
78 | "inputs": [],
79 | "name": "nexus",
80 | "outputs": [
81 | {
82 | "internalType": "contract INexus",
83 | "name": "",
84 | "type": "address"
85 | }
86 | ],
87 | "payable": false,
88 | "stateMutability": "view",
89 | "type": "function"
90 | },
91 | {
92 | "constant": true,
93 | "inputs": [
94 | {
95 | "internalType": "address",
96 | "name": "",
97 | "type": "address"
98 | }
99 | ],
100 | "name": "whitelist",
101 | "outputs": [
102 | {
103 | "internalType": "bool",
104 | "name": "",
105 | "type": "bool"
106 | }
107 | ],
108 | "payable": false,
109 | "stateMutability": "view",
110 | "type": "function"
111 | },
112 | {
113 | "constant": false,
114 | "inputs": [
115 | {
116 | "internalType": "address",
117 | "name": "_address",
118 | "type": "address"
119 | }
120 | ],
121 | "name": "addFundManager",
122 | "outputs": [],
123 | "payable": false,
124 | "stateMutability": "nonpayable",
125 | "type": "function"
126 | },
127 | {
128 | "constant": false,
129 | "inputs": [
130 | {
131 | "internalType": "address",
132 | "name": "_address",
133 | "type": "address"
134 | }
135 | ],
136 | "name": "removeFundManager",
137 | "outputs": [],
138 | "payable": false,
139 | "stateMutability": "nonpayable",
140 | "type": "function"
141 | },
142 | {
143 | "constant": false,
144 | "inputs": [
145 | {
146 | "internalType": "contract IRewardsDistributionRecipient[]",
147 | "name": "_recipients",
148 | "type": "address[]"
149 | },
150 | {
151 | "internalType": "uint256[]",
152 | "name": "_amounts",
153 | "type": "uint256[]"
154 | }
155 | ],
156 | "name": "distributeRewards",
157 | "outputs": [],
158 | "payable": false,
159 | "stateMutability": "nonpayable",
160 | "type": "function"
161 | }
162 | ]
163 |
--------------------------------------------------------------------------------
/src/mstable/contracts.ts:
--------------------------------------------------------------------------------
1 | import Masset from "./abi/Masset.json";
2 | import MetaToken from "./abi/MetaToken.json";
3 | import MassetValidationHelper from "./abi/MassetValidationHelper.json";
4 | import ForgeValidator from "./abi/ForgeValidator.json";
5 | import BasketManager from "./abi/BasketManager.json";
6 | import AaveIntegration from "./abi/AaveIntegration.json";
7 | import CompoundIntegration from "./abi/CompoundIntegration.json";
8 | import Nexus from "./abi/Nexus.json";
9 | import DelayedProxyAdmin from "./abi/DelayedProxyAdmin.json";
10 | import SavingsManager from "./abi/SavingsManager.json";
11 | import SavingsContract from "./abi/SavingsContract.json";
12 | import RewardsDistributor from "./abi/RewardsDistributor.json";
13 | import StakingRewardsWithPlatformToken from "./abi/StakingRewardsWithPlatformToken.json";
14 |
15 | const contracts = {
16 | mUSD: {
17 | symbol: "mUSD",
18 | decimals: 18,
19 | abi: Masset,
20 | address: "0xe2f2a5C287993345a840Db3B0845fbC70f5935a5",
21 | },
22 | MTA: {
23 | abi: MetaToken,
24 | address: "0xa3bed4e1c75d00fa6f4e5e6922db7261b5e9acd2",
25 | },
26 | MassetValidationHelper: {
27 | abi: MassetValidationHelper,
28 | address: "0xabcc93c3be238884cc3309c19afd128fafc16911",
29 | },
30 | ForgeValidator: {
31 | abi: ForgeValidator,
32 | address: "0xbB90D06371030fFa150E463621c22950b212eaa1",
33 | },
34 | BasketManager: {
35 | abi: BasketManager,
36 | address: "0x66126B4aA2a1C07536Ef8E5e8bD4EfDA1FdEA96D",
37 | },
38 | AaveIntegration: {
39 | abi: AaveIntegration,
40 | address: "0xf617346a0fb6320e9e578e0c9b2a4588283d9d39",
41 | },
42 | CompoundIntegration: {
43 | abi: CompoundIntegration,
44 | address: "0xd55684f4369040c12262949ff78299f2bc9db735",
45 | },
46 | Nexus: {
47 | abi: Nexus,
48 | address: "0xAFcE80b19A8cE13DEc0739a1aaB7A028d6845Eb3",
49 | },
50 | DelayedProxyAdmin: {
51 | abi: DelayedProxyAdmin,
52 | address: "0x5C8eb57b44C1c6391fC7a8A0cf44d26896f92386",
53 | },
54 | SavingsManager: {
55 | abi: SavingsManager,
56 | address: "0x7046b0bfc4c5eeb90559c0805dd9c1a6f4815370",
57 | },
58 | SavingsContract: {
59 | abi: SavingsContract,
60 | address: "0xcf3f73290803fc04425bee135a4caeb2bab2c2a1",
61 | },
62 | RewardsDistributor: {
63 | abi: RewardsDistributor,
64 | address: "0x04dfdfa471b79cc9e6e8c355e6c71f8ec4916c50",
65 | },
66 | StakingRewardsWithPlatformToken: {
67 | abi: StakingRewardsWithPlatformToken,
68 | },
69 | };
70 |
71 | export default contracts;
72 |
--------------------------------------------------------------------------------
/src/mstable/contracts/Masset.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | interface Masset {
4 |
5 | /**
6 | * @dev Mint a single bAsset, at a 1:1 ratio with the bAsset. This contract
7 | * must have approval to spend the senders bAsset
8 | * @param _bAsset Address of the bAsset to mint
9 | * @param _bAssetQuantity Quantity in bAsset units
10 | * @return massetMinted Number of newly minted mAssets
11 | */
12 | function mint(address _bAsset, uint256 _bAssetQuantity) external returns (uint256 massetMinted);
13 |
14 |
15 | /**
16 | * @dev Mint a single bAsset, at a 1:1 ratio with the bAsset. This contract
17 | * must have approval to spend the senders bAsset
18 | * @param _bAsset Address of the bAsset to mint
19 | * @param _bAssetQuantity Quantity in bAsset units
20 | * @param _recipient receipient of the newly minted mAsset tokens
21 | * @return massetMinted Number of newly minted mAssets
22 | */
23 | function mintTo(address _bAsset, uint256 _bAssetQuantity, address _recipient) external returns (uint256 massetMinted);
24 |
25 |
26 | /**
27 | * @dev Mint with multiple bAssets, at a 1:1 ratio to mAsset. This contract
28 | * must have approval to spend the senders bAssets
29 | * @param _bAssets Non-duplicate address array of bAssets with which to mint
30 | * @param _bAssetQuantity Quantity of each bAsset to mint. Order of array
31 | * should mirror the above
32 | * @param _recipient Address to receive the newly minted mAsset tokens
33 | * @return massetMinted Number of newly minted mAssets
34 | */
35 | function mintMulti(address[] calldata _bAssets, uint256[] calldata _bAssetQuantity, address _recipient) external returns(uint256 massetMinted);
36 |
37 |
38 | /**
39 | * @dev Simply swaps one bAsset for another bAsset or this mAsset at a 1:1 ratio.
40 | * bAsset <> bAsset swaps will incur a small fee (swapFee()). Swap
41 | * is valid if it does not result in the input asset exceeding its maximum weight.
42 | * @param _input bAsset to deposit
43 | * @param _output Asset to receive - either a bAsset or mAsset(this)
44 | * @param _quantity Units of input bAsset to swap
45 | * @param _recipient Address to credit output asset
46 | * @return output Units of output asset returned
47 | */
48 | function swap(address _input, address _output, uint256 _quantity, address _recipient) external returns (uint256 output);
49 |
50 |
51 |
52 | /**
53 | * @dev Determines both if a trade is valid, and the expected fee or output.
54 | * Swap is valid if it does not result in the input asset exceeding its maximum weight.
55 | * @param _input bAsset to deposit
56 | * @param _output Asset to receive - bAsset or mAsset(this)
57 | * @param _quantity Units of input bAsset to swap
58 | * @return valid Bool to signify that swap is current valid
59 | * @return reason If swap is invalid, this is the reason
60 | * @return output Units of _output asset the trade would return
61 | */
62 | function getSwapOutput(address _input, address _output, uint256 _quantity) external view returns (bool, string memory, uint256 output);
63 |
64 |
65 | /**
66 | * @dev Credits the sender with a certain quantity of selected bAsset, in exchange for burning the
67 | * relative mAsset quantity from the sender. Sender also incurs a small mAsset fee, if any.
68 | * @param _bAsset Address of the bAsset to redeem
69 | * @param _bAssetQuantity Units of the bAsset to redeem
70 | * @return massetMinted Relative number of mAsset units burned to pay for the bAssets
71 | */
72 | function redeem(address _bAsset, uint256 _bAssetQuantity) external returns (uint256 massetRedeemed);
73 |
74 |
75 | /**
76 | * @dev Credits a recipient with a certain quantity of selected bAsset, in exchange for burning the
77 | * relative Masset quantity from the sender. Sender also incurs a small fee, if any.
78 | * @param _bAsset Address of the bAsset to redeem
79 | * @param _bAssetQuantity Units of the bAsset to redeem
80 | * @param _recipient Address to credit with withdrawn bAssets
81 | * @return massetMinted Relative number of mAsset units burned to pay for the bAssets
82 | */
83 | function redeemTo(address _bAsset, uint256 _bAssetQuantity, address _recipient) external returns (uint256 massetRedeemed);
84 |
85 |
86 |
87 | /**
88 | * @dev Credits a recipient with a proportionate amount of bAssets, relative to current vault
89 | * balance levels and desired mAsset quantity. Burns the mAsset as payment.
90 | * @param _mAssetQuantity Quantity of mAsset to redeem
91 | * @param _recipient Address to credit the withdrawn bAssets
92 | */
93 | function redeemMasset(uint256 _mAssetQuantity, address _recipient) external;
94 | }
--------------------------------------------------------------------------------
/src/mstable/contracts/StakingRewardsWithPlatformToken.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | import "@openzeppelin/contracts/token/ERC20/IERC20.sol";
4 |
5 | interface StakingRewardsWithPlatformToken {
6 |
7 | /**
8 | * @dev Stakes a given amount of the StakingToken for the sender
9 | * @param _amount Units of StakingToken
10 | */
11 | function stake(uint256 _amount) external;
12 |
13 |
14 | /**
15 | * @dev Stakes a given amount of the StakingToken for a given beneficiary
16 | * @param _beneficiary Staked tokens are credited to this address
17 | * @param _amount Units of StakingToken
18 | */
19 | function stake(address _beneficiary, uint256 _amount) external;
20 |
21 |
22 | /**
23 | * @dev Withdraws stake from pool and claims any rewards
24 | */
25 | function exit() external;
26 |
27 |
28 | /**
29 | * @dev Withdraws given stake amount from the pool
30 | * @param _amount Units of the staked token to withdraw
31 | */
32 | function withdraw(uint256 _amount) external;
33 |
34 |
35 | /**
36 | * @dev Claims outstanding rewards (both platform and native) for the sender.
37 | * First updates outstanding reward allocation and then transfers.
38 | */
39 | function claimReward() external;
40 |
41 |
42 | /**
43 | * @dev Claims outstanding rewards for the sender. Only the native
44 | * rewards token, and not the platform rewards
45 | */
46 | function claimRewardOnly() external;
47 |
48 |
49 | /**
50 | * @dev Gets the RewardsToken
51 | */
52 | function getRewardToken() external view returns (IERC20);
53 |
54 |
55 | /**
56 | * @dev Gets the last applicable timestamp for this reward period
57 | */
58 | function lastTimeRewardApplicable() external view returns (uint256);
59 |
60 |
61 | /**
62 | * @dev Calculates the amount of unclaimed rewards a user has earned
63 | * @return 'Reward' per staked token
64 | */
65 | function rewardPerToken() external view returns (uint256, uint256);
66 |
67 |
68 | /**
69 | * @dev Calculates the amount of unclaimed rewards a user has earned
70 | * @param _account User address
71 | * @return Total reward amount earned
72 | */
73 | function earned(address _account) external view returns (uint256, uint256);
74 | }
--------------------------------------------------------------------------------
/src/mstable/index.ts:
--------------------------------------------------------------------------------
1 | import { default as contracts } from "./contracts";
2 |
3 | export = {
4 | ...contracts,
5 | };
6 |
--------------------------------------------------------------------------------
/src/onesplit/contracts.ts:
--------------------------------------------------------------------------------
1 | import oneSplitAbi from "./abi/OneSplit.json";
2 |
3 | const contracts = {
4 | address: "0xC586BeF4a0992C495Cf22e1aeEE4E446CECDee0E", // Alternatively 1split.eth
5 | abi: oneSplitAbi,
6 | };
7 |
8 | export default contracts;
9 |
--------------------------------------------------------------------------------
/src/onesplit/contracts/IOneSplit.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | import "@openzeppelin/contracts/token/ERC20/IERC20.sol";
4 |
5 |
6 | contract IOneSplitConsts {
7 | // disableFlags = FLAG_DISABLE_UNISWAP + FLAG_DISABLE_KYBER + ...
8 | uint256 public constant FLAG_DISABLE_UNISWAP = 0x01;
9 | uint256 public constant FLAG_DISABLE_KYBER = 0x02;
10 | uint256 public constant FLAG_ENABLE_KYBER_UNISWAP_RESERVE = 0x100000000; // Turned off by default
11 | uint256 public constant FLAG_ENABLE_KYBER_OASIS_RESERVE = 0x200000000; // Turned off by default
12 | uint256 public constant FLAG_ENABLE_KYBER_BANCOR_RESERVE = 0x400000000; // Turned off by default
13 | uint256 public constant FLAG_DISABLE_BANCOR = 0x04;
14 | uint256 public constant FLAG_DISABLE_OASIS = 0x08;
15 | uint256 public constant FLAG_DISABLE_COMPOUND = 0x10;
16 | uint256 public constant FLAG_DISABLE_FULCRUM = 0x20;
17 | uint256 public constant FLAG_DISABLE_CHAI = 0x40;
18 | uint256 public constant FLAG_DISABLE_AAVE = 0x80;
19 | uint256 public constant FLAG_DISABLE_SMART_TOKEN = 0x100;
20 | uint256 public constant FLAG_ENABLE_MULTI_PATH_ETH = 0x200; // Turned off by default
21 | uint256 public constant FLAG_DISABLE_BDAI = 0x400;
22 | uint256 public constant FLAG_DISABLE_IEARN = 0x800;
23 | uint256 public constant FLAG_DISABLE_CURVE_COMPOUND = 0x1000;
24 | uint256 public constant FLAG_DISABLE_CURVE_USDT = 0x2000;
25 | uint256 public constant FLAG_DISABLE_CURVE_Y = 0x4000;
26 | uint256 public constant FLAG_DISABLE_CURVE_BINANCE = 0x8000;
27 | uint256 public constant FLAG_ENABLE_MULTI_PATH_DAI = 0x10000; // Turned off by default
28 | uint256 public constant FLAG_ENABLE_MULTI_PATH_USDC = 0x20000; // Turned off by default
29 | uint256 public constant FLAG_DISABLE_CURVE_SYNTHETIX = 0x40000;
30 | uint256 public constant FLAG_DISABLE_WETH = 0x80000;
31 | uint256 public constant FLAG_ENABLE_UNISWAP_COMPOUND = 0x100000; // Works only when one of assets is ETH or FLAG_ENABLE_MULTI_PATH_ETH
32 | uint256 public constant FLAG_ENABLE_UNISWAP_CHAI = 0x200000; // Works only when ETH<>DAI or FLAG_ENABLE_MULTI_PATH_ETH
33 | uint256 public constant FLAG_ENABLE_UNISWAP_AAVE = 0x400000; // Works only when one of assets is ETH or FLAG_ENABLE_MULTI_PATH_ETH
34 | uint256 public constant FLAG_DISABLE_IDLE = 0x800000;
35 | }
36 |
37 |
38 | contract IOneSplit is IOneSplitConsts {
39 | function getExpectedReturn(
40 | IERC20 fromToken,
41 | IERC20 toToken,
42 | uint256 amount,
43 | uint256 parts,
44 | uint256 disableFlags
45 | )
46 | public
47 | view
48 | returns(
49 | uint256 returnAmount,
50 | uint256[] memory distribution
51 | );
52 |
53 | function swap(
54 | IERC20 fromToken,
55 | IERC20 toToken,
56 | uint256 amount,
57 | uint256 minReturn,
58 | uint256[] memory distribution,
59 | uint256 disableFlags
60 | ) public payable;
61 | }
62 |
--------------------------------------------------------------------------------
/src/onesplit/index.ts:
--------------------------------------------------------------------------------
1 | import { default as contracts } from "./contracts";
2 |
3 | export = {
4 | ...contracts,
5 | };
6 |
--------------------------------------------------------------------------------
/src/synthetix/contracts/IDepot.sol:
--------------------------------------------------------------------------------
1 | pragma solidity >=0.4.24;
2 |
3 |
4 | interface IDepot {
5 | // Views
6 | function fundsWallet() external view returns (address payable);
7 |
8 | function maxEthPurchase() external view returns (uint);
9 |
10 | function minimumDepositAmount() external view returns (uint);
11 |
12 | function synthsReceivedForEther(uint amount) external view returns (uint);
13 |
14 | function totalSellableDeposits() external view returns (uint);
15 |
16 | // Mutative functions
17 | function depositSynths(uint amount) external;
18 |
19 | function exchangeEtherForSynths() external payable returns (uint);
20 |
21 | function exchangeEtherForSynthsAtRate(uint guaranteedRate) external payable returns (uint);
22 |
23 | function withdrawMyDepositedSynths() external;
24 |
25 | // Note: On mainnet no SNX has been deposited. The following functions are kept alive for testnet SNX faucets.
26 | function exchangeEtherForSNX() external payable returns (uint);
27 |
28 | function exchangeEtherForSNXAtRate(uint guaranteedRate, uint guaranteedSynthetixRate) external payable returns (uint);
29 |
30 | function exchangeSynthsForSNX(uint synthAmount) external returns (uint);
31 |
32 | function exchangeSynthsForSNXAtRate(uint synthAmount, uint guaranteedRate) external returns (uint);
33 | }
--------------------------------------------------------------------------------
/src/synthetix/contracts/ISynth.sol:
--------------------------------------------------------------------------------
1 | pragma solidity >=0.4.24;
2 |
3 |
4 | interface ISynth {
5 | // Views
6 | function currencyKey() external view returns (bytes32);
7 |
8 | function transferableSynths(address account) external view returns (uint);
9 |
10 | // Mutative functions
11 | function transferAndSettle(address to, uint value) external returns (bool);
12 |
13 | function transferFromAndSettle(
14 | address from,
15 | address to,
16 | uint value
17 | ) external returns (bool);
18 |
19 | // Restricted: used internally to Synthetix
20 | function burn(address account, uint amount) external;
21 |
22 | function issue(address account, uint amount) external;
23 | }
--------------------------------------------------------------------------------
/src/synthetix/contracts/ISynthetix.sol:
--------------------------------------------------------------------------------
1 | pragma solidity >=0.4.24;
2 |
3 | import "./ISynth.sol";
4 |
5 |
6 | interface ISynthetix {
7 | // Views
8 | function availableCurrencyKeys() external view returns (bytes32[] memory);
9 |
10 | function availableSynthCount() external view returns (uint);
11 |
12 | function collateral(address account) external view returns (uint);
13 |
14 | function collateralisationRatio(address issuer) external view returns (uint);
15 |
16 | function debtBalanceOf(address issuer, bytes32 currencyKey) external view returns (uint);
17 |
18 | function debtBalanceOfAndTotalDebt(address issuer, bytes32 currencyKey)
19 | external
20 | view
21 | returns (uint debtBalance, uint totalSystemValue);
22 |
23 | function isWaitingPeriod(bytes32 currencyKey) external view returns (bool);
24 |
25 | function maxIssuableSynths(address issuer) external view returns (uint maxIssuable);
26 |
27 | function remainingIssuableSynths(address issuer)
28 | external
29 | view
30 | returns (
31 | uint maxIssuable,
32 | uint alreadyIssued,
33 | uint totalSystemDebt
34 | );
35 |
36 | function synths(bytes32 currencyKey) external view returns (ISynth);
37 |
38 | function synthsByAddress(address synthAddress) external view returns (bytes32);
39 |
40 | function totalIssuedSynths(bytes32 currencyKey) external view returns (uint);
41 |
42 | function totalIssuedSynthsExcludeEtherCollateral(bytes32 currencyKey) external view returns (uint);
43 |
44 | function transferableSynthetix(address account) external view returns (uint);
45 |
46 | // Mutative Functions
47 | function burnSynths(uint amount) external;
48 |
49 | function burnSynthsOnBehalf(address burnForAddress, uint amount) external;
50 |
51 | function burnSynthsToTarget() external;
52 |
53 | function burnSynthsToTargetOnBehalf(address burnForAddress) external;
54 |
55 | function exchange(
56 | bytes32 sourceCurrencyKey,
57 | uint sourceAmount,
58 | bytes32 destinationCurrencyKey
59 | ) external returns (uint amountReceived);
60 |
61 | function exchangeOnBehalf(
62 | address exchangeForAddress,
63 | bytes32 sourceCurrencyKey,
64 | uint sourceAmount,
65 | bytes32 destinationCurrencyKey
66 | ) external returns (uint amountReceived);
67 |
68 | function issueMaxSynths() external;
69 |
70 | function issueMaxSynthsOnBehalf(address issueForAddress) external;
71 |
72 | function issueSynths(uint amount) external;
73 |
74 | function issueSynthsOnBehalf(address issueForAddress, uint amount) external;
75 |
76 | function mint() external returns (bool);
77 |
78 | function settle(bytes32 currencyKey)
79 | external
80 | returns (
81 | uint reclaimed,
82 | uint refunded,
83 | uint numEntries
84 | );
85 |
86 | function liquidateDelinquentAccount(address account, uint susdAmount) external returns (bool);
87 | }
--------------------------------------------------------------------------------
/src/synthetix/index.ts:
--------------------------------------------------------------------------------
1 | import { default as contracts } from "./contracts";
2 |
3 | export = {
4 | ...contracts,
5 | };
6 |
--------------------------------------------------------------------------------
/src/uma/abi/AddressWhitelist.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "anonymous": false,
4 | "inputs": [
5 | {
6 | "indexed": true,
7 | "internalType": "address",
8 | "name": "addedAddress",
9 | "type": "address"
10 | }
11 | ],
12 | "name": "AddedToWhitelist",
13 | "type": "event"
14 | },
15 | {
16 | "anonymous": false,
17 | "inputs": [
18 | {
19 | "indexed": true,
20 | "internalType": "address",
21 | "name": "previousOwner",
22 | "type": "address"
23 | },
24 | {
25 | "indexed": true,
26 | "internalType": "address",
27 | "name": "newOwner",
28 | "type": "address"
29 | }
30 | ],
31 | "name": "OwnershipTransferred",
32 | "type": "event"
33 | },
34 | {
35 | "anonymous": false,
36 | "inputs": [
37 | {
38 | "indexed": true,
39 | "internalType": "address",
40 | "name": "removedAddress",
41 | "type": "address"
42 | }
43 | ],
44 | "name": "RemovedFromWhitelist",
45 | "type": "event"
46 | },
47 | {
48 | "inputs": [],
49 | "name": "owner",
50 | "outputs": [
51 | {
52 | "internalType": "address",
53 | "name": "",
54 | "type": "address"
55 | }
56 | ],
57 | "stateMutability": "view",
58 | "type": "function",
59 | "constant": true
60 | },
61 | {
62 | "inputs": [],
63 | "name": "renounceOwnership",
64 | "outputs": [],
65 | "stateMutability": "nonpayable",
66 | "type": "function"
67 | },
68 | {
69 | "inputs": [
70 | {
71 | "internalType": "address",
72 | "name": "newOwner",
73 | "type": "address"
74 | }
75 | ],
76 | "name": "transferOwnership",
77 | "outputs": [],
78 | "stateMutability": "nonpayable",
79 | "type": "function"
80 | },
81 | {
82 | "inputs": [
83 | {
84 | "internalType": "address",
85 | "name": "",
86 | "type": "address"
87 | }
88 | ],
89 | "name": "whitelist",
90 | "outputs": [
91 | {
92 | "internalType": "enum AddressWhitelist.Status",
93 | "name": "",
94 | "type": "uint8"
95 | }
96 | ],
97 | "stateMutability": "view",
98 | "type": "function",
99 | "constant": true
100 | },
101 | {
102 | "inputs": [
103 | {
104 | "internalType": "uint256",
105 | "name": "",
106 | "type": "uint256"
107 | }
108 | ],
109 | "name": "whitelistIndices",
110 | "outputs": [
111 | {
112 | "internalType": "address",
113 | "name": "",
114 | "type": "address"
115 | }
116 | ],
117 | "stateMutability": "view",
118 | "type": "function",
119 | "constant": true
120 | },
121 | {
122 | "inputs": [
123 | {
124 | "internalType": "address",
125 | "name": "newElement",
126 | "type": "address"
127 | }
128 | ],
129 | "name": "addToWhitelist",
130 | "outputs": [],
131 | "stateMutability": "nonpayable",
132 | "type": "function"
133 | },
134 | {
135 | "inputs": [
136 | {
137 | "internalType": "address",
138 | "name": "elementToRemove",
139 | "type": "address"
140 | }
141 | ],
142 | "name": "removeFromWhitelist",
143 | "outputs": [],
144 | "stateMutability": "nonpayable",
145 | "type": "function"
146 | },
147 | {
148 | "inputs": [
149 | {
150 | "internalType": "address",
151 | "name": "elementToCheck",
152 | "type": "address"
153 | }
154 | ],
155 | "name": "isOnWhitelist",
156 | "outputs": [
157 | {
158 | "internalType": "bool",
159 | "name": "",
160 | "type": "bool"
161 | }
162 | ],
163 | "stateMutability": "view",
164 | "type": "function",
165 | "constant": true
166 | },
167 | {
168 | "inputs": [],
169 | "name": "getWhitelist",
170 | "outputs": [
171 | {
172 | "internalType": "address[]",
173 | "name": "activeWhitelist",
174 | "type": "address[]"
175 | }
176 | ],
177 | "stateMutability": "view",
178 | "type": "function",
179 | "constant": true
180 | }
181 | ]
--------------------------------------------------------------------------------
/src/uma/abi/ExpiringMultiPartyLib.json:
--------------------------------------------------------------------------------
1 | []
--------------------------------------------------------------------------------
/src/uma/abi/FinancialContractsAdmin.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "anonymous": false,
4 | "inputs": [
5 | {
6 | "indexed": true,
7 | "internalType": "address",
8 | "name": "previousOwner",
9 | "type": "address"
10 | },
11 | {
12 | "indexed": true,
13 | "internalType": "address",
14 | "name": "newOwner",
15 | "type": "address"
16 | }
17 | ],
18 | "name": "OwnershipTransferred",
19 | "type": "event"
20 | },
21 | {
22 | "inputs": [],
23 | "name": "owner",
24 | "outputs": [
25 | {
26 | "internalType": "address",
27 | "name": "",
28 | "type": "address"
29 | }
30 | ],
31 | "stateMutability": "view",
32 | "type": "function",
33 | "constant": true
34 | },
35 | {
36 | "inputs": [],
37 | "name": "renounceOwnership",
38 | "outputs": [],
39 | "stateMutability": "nonpayable",
40 | "type": "function"
41 | },
42 | {
43 | "inputs": [
44 | {
45 | "internalType": "address",
46 | "name": "newOwner",
47 | "type": "address"
48 | }
49 | ],
50 | "name": "transferOwnership",
51 | "outputs": [],
52 | "stateMutability": "nonpayable",
53 | "type": "function"
54 | },
55 | {
56 | "inputs": [
57 | {
58 | "internalType": "address",
59 | "name": "financialContract",
60 | "type": "address"
61 | }
62 | ],
63 | "name": "callEmergencyShutdown",
64 | "outputs": [],
65 | "stateMutability": "nonpayable",
66 | "type": "function"
67 | },
68 | {
69 | "inputs": [
70 | {
71 | "internalType": "address",
72 | "name": "financialContract",
73 | "type": "address"
74 | }
75 | ],
76 | "name": "callRemargin",
77 | "outputs": [],
78 | "stateMutability": "nonpayable",
79 | "type": "function"
80 | }
81 | ]
--------------------------------------------------------------------------------
/src/uma/abi/Finder.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "anonymous": false,
4 | "inputs": [
5 | {
6 | "indexed": true,
7 | "internalType": "bytes32",
8 | "name": "interfaceName",
9 | "type": "bytes32"
10 | },
11 | {
12 | "indexed": true,
13 | "internalType": "address",
14 | "name": "newImplementationAddress",
15 | "type": "address"
16 | }
17 | ],
18 | "name": "InterfaceImplementationChanged",
19 | "type": "event"
20 | },
21 | {
22 | "anonymous": false,
23 | "inputs": [
24 | {
25 | "indexed": true,
26 | "internalType": "address",
27 | "name": "previousOwner",
28 | "type": "address"
29 | },
30 | {
31 | "indexed": true,
32 | "internalType": "address",
33 | "name": "newOwner",
34 | "type": "address"
35 | }
36 | ],
37 | "name": "OwnershipTransferred",
38 | "type": "event"
39 | },
40 | {
41 | "inputs": [
42 | {
43 | "internalType": "bytes32",
44 | "name": "",
45 | "type": "bytes32"
46 | }
47 | ],
48 | "name": "interfacesImplemented",
49 | "outputs": [
50 | {
51 | "internalType": "address",
52 | "name": "",
53 | "type": "address"
54 | }
55 | ],
56 | "stateMutability": "view",
57 | "type": "function",
58 | "constant": true
59 | },
60 | {
61 | "inputs": [],
62 | "name": "owner",
63 | "outputs": [
64 | {
65 | "internalType": "address",
66 | "name": "",
67 | "type": "address"
68 | }
69 | ],
70 | "stateMutability": "view",
71 | "type": "function",
72 | "constant": true
73 | },
74 | {
75 | "inputs": [],
76 | "name": "renounceOwnership",
77 | "outputs": [],
78 | "stateMutability": "nonpayable",
79 | "type": "function"
80 | },
81 | {
82 | "inputs": [
83 | {
84 | "internalType": "address",
85 | "name": "newOwner",
86 | "type": "address"
87 | }
88 | ],
89 | "name": "transferOwnership",
90 | "outputs": [],
91 | "stateMutability": "nonpayable",
92 | "type": "function"
93 | },
94 | {
95 | "inputs": [
96 | {
97 | "internalType": "bytes32",
98 | "name": "interfaceName",
99 | "type": "bytes32"
100 | },
101 | {
102 | "internalType": "address",
103 | "name": "implementationAddress",
104 | "type": "address"
105 | }
106 | ],
107 | "name": "changeImplementationAddress",
108 | "outputs": [],
109 | "stateMutability": "nonpayable",
110 | "type": "function"
111 | },
112 | {
113 | "inputs": [
114 | {
115 | "internalType": "bytes32",
116 | "name": "interfaceName",
117 | "type": "bytes32"
118 | }
119 | ],
120 | "name": "getImplementationAddress",
121 | "outputs": [
122 | {
123 | "internalType": "address",
124 | "name": "",
125 | "type": "address"
126 | }
127 | ],
128 | "stateMutability": "view",
129 | "type": "function",
130 | "constant": true
131 | }
132 | ]
--------------------------------------------------------------------------------
/src/uma/abi/IdentifierWhitelist.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "anonymous": false,
4 | "inputs": [
5 | {
6 | "indexed": true,
7 | "internalType": "address",
8 | "name": "previousOwner",
9 | "type": "address"
10 | },
11 | {
12 | "indexed": true,
13 | "internalType": "address",
14 | "name": "newOwner",
15 | "type": "address"
16 | }
17 | ],
18 | "name": "OwnershipTransferred",
19 | "type": "event"
20 | },
21 | {
22 | "anonymous": false,
23 | "inputs": [
24 | {
25 | "indexed": true,
26 | "internalType": "bytes32",
27 | "name": "identifier",
28 | "type": "bytes32"
29 | }
30 | ],
31 | "name": "SupportedIdentifierAdded",
32 | "type": "event"
33 | },
34 | {
35 | "anonymous": false,
36 | "inputs": [
37 | {
38 | "indexed": true,
39 | "internalType": "bytes32",
40 | "name": "identifier",
41 | "type": "bytes32"
42 | }
43 | ],
44 | "name": "SupportedIdentifierRemoved",
45 | "type": "event"
46 | },
47 | {
48 | "inputs": [],
49 | "name": "owner",
50 | "outputs": [
51 | {
52 | "internalType": "address",
53 | "name": "",
54 | "type": "address"
55 | }
56 | ],
57 | "stateMutability": "view",
58 | "type": "function",
59 | "constant": true
60 | },
61 | {
62 | "inputs": [],
63 | "name": "renounceOwnership",
64 | "outputs": [],
65 | "stateMutability": "nonpayable",
66 | "type": "function"
67 | },
68 | {
69 | "inputs": [
70 | {
71 | "internalType": "address",
72 | "name": "newOwner",
73 | "type": "address"
74 | }
75 | ],
76 | "name": "transferOwnership",
77 | "outputs": [],
78 | "stateMutability": "nonpayable",
79 | "type": "function"
80 | },
81 | {
82 | "inputs": [
83 | {
84 | "internalType": "bytes32",
85 | "name": "identifier",
86 | "type": "bytes32"
87 | }
88 | ],
89 | "name": "addSupportedIdentifier",
90 | "outputs": [],
91 | "stateMutability": "nonpayable",
92 | "type": "function"
93 | },
94 | {
95 | "inputs": [
96 | {
97 | "internalType": "bytes32",
98 | "name": "identifier",
99 | "type": "bytes32"
100 | }
101 | ],
102 | "name": "removeSupportedIdentifier",
103 | "outputs": [],
104 | "stateMutability": "nonpayable",
105 | "type": "function"
106 | },
107 | {
108 | "inputs": [
109 | {
110 | "internalType": "bytes32",
111 | "name": "identifier",
112 | "type": "bytes32"
113 | }
114 | ],
115 | "name": "isIdentifierSupported",
116 | "outputs": [
117 | {
118 | "internalType": "bool",
119 | "name": "",
120 | "type": "bool"
121 | }
122 | ],
123 | "stateMutability": "view",
124 | "type": "function",
125 | "constant": true
126 | }
127 | ]
--------------------------------------------------------------------------------
/src/uma/abi/TokenFactory.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "inputs": [
4 | {
5 | "internalType": "string",
6 | "name": "tokenName",
7 | "type": "string"
8 | },
9 | {
10 | "internalType": "string",
11 | "name": "tokenSymbol",
12 | "type": "string"
13 | },
14 | {
15 | "internalType": "uint8",
16 | "name": "tokenDecimals",
17 | "type": "uint8"
18 | }
19 | ],
20 | "name": "createToken",
21 | "outputs": [
22 | {
23 | "internalType": "contract ExpandedIERC20",
24 | "name": "newToken",
25 | "type": "address"
26 | }
27 | ],
28 | "stateMutability": "nonpayable",
29 | "type": "function"
30 | }
31 | ]
--------------------------------------------------------------------------------
/src/uma/contracts.ts:
--------------------------------------------------------------------------------
1 | import addressWhitelistAbi from "./abi/AddressWhitelist.json";
2 | import designatedVotingFactoryAbi from "./abi/DesignatedVotingFactory.json";
3 | import expiringMultiPartyAbi from "./abi/ExpiringMultiParty.json";
4 | import expiringMultiPartyCreatorAbi from "./abi/ExpiringMultiPartyCreator.json";
5 | import financialContractsAdminAbi from "./abi/FinancialContractsAdmin.json";
6 | import finderAbi from "./abi/Finder.json";
7 | import governorAbi from "./abi/Governor.json";
8 | import identifierWhitelistAbi from "./abi/IdentifierWhitelist.json";
9 | import registryAbi from "./abi/Registry.json";
10 | import storeAbi from "./abi/Store.json";
11 | import tokenFactoryAbi from "./abi/TokenFactory.json";
12 | import votingAbi from "./abi/Voting.json";
13 | import votingTokenAbi from "./abi/VotingToken.json";
14 | import weth9Abi from "./abi/WETH9.json";
15 |
16 | const contracts = {
17 | addressWhitelist: {
18 | abi: addressWhitelistAbi,
19 | address: "0xdBF90434dF0B98219f87d112F37d74B1D90758c7",
20 | },
21 | designatedVotingFactory: {
22 | abi: designatedVotingFactoryAbi,
23 | address: "0xE81EeE5Da165fA6863bBc82dF66E62d18625d592",
24 | },
25 | expiringMultiParty: {
26 | abi: expiringMultiPartyAbi,
27 | },
28 | expiringMultiPartyLib: {
29 | abi: [],
30 | address: "0xCb08678e4381Be3E264E6A0037E3297Ca56a583e",
31 | },
32 | expiringMultiPartyCreator: {
33 | abi: expiringMultiPartyCreatorAbi,
34 | address: "0xad8fD1f418FB860A383c9D4647880af7f043Ef39",
35 | },
36 | financialContractsAdmin: {
37 | abi: financialContractsAdminAbi,
38 | address: "0x4E6CCB1dA3C7844887F9A5aF4e8450d9fd90317A",
39 | },
40 | finder: {
41 | abi: finderAbi,
42 | address: "0x40f941E48A552bF496B154Af6bf55725f18D77c3",
43 | },
44 | governor: {
45 | abi: governorAbi,
46 | address: "0x592349F7DeDB2b75f9d4F194d4b7C16D82E507Dc",
47 | },
48 | identifierWhitelist: {
49 | abi: identifierWhitelistAbi,
50 | address: "0xcF649d9Da4D1362C4DAEa67573430Bd6f945e570",
51 | },
52 | registry: {
53 | abi: registryAbi,
54 | address: "0x3e532e6222afe9Bcf02DCB87216802c75D5113aE",
55 | },
56 | store: {
57 | abi: storeAbi,
58 | address: "0x54f44eA3D2e7aA0ac089c4d8F7C93C27844057BF",
59 | },
60 | tokenFactory: {
61 | abi: tokenFactoryAbi,
62 | address: "0x7c96d6235CfaaCcAc5d80fCe74E6032B25dd1F03",
63 | },
64 | voting: {
65 | abi: votingAbi,
66 | address: "0x9921810C710E7c3f7A7C6831e30929f19537a545",
67 | },
68 | votingToken: {
69 | abi: votingTokenAbi,
70 | address: "0x04Fa0d235C4abf4BcF4787aF4CF447DE572eF828",
71 | },
72 | weth9: {
73 | abi: weth9Abi,
74 | address: "0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2",
75 | },
76 | };
77 |
78 | export default contracts;
79 |
--------------------------------------------------------------------------------
/src/uma/index.ts:
--------------------------------------------------------------------------------
1 | import { default as contracts } from "./contracts";
2 |
3 | export = {
4 | ...contracts,
5 | };
6 |
--------------------------------------------------------------------------------
/src/uniswap/abi/Factory.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "name": "NewExchange",
4 | "inputs": [
5 | {
6 | "type": "address",
7 | "name": "token",
8 | "indexed": true
9 | },
10 | {
11 | "type": "address",
12 | "name": "exchange",
13 | "indexed": true
14 | }
15 | ],
16 | "anonymous": false,
17 | "type": "event"
18 | },
19 | {
20 | "name": "initializeFactory",
21 | "outputs": [],
22 | "inputs": [
23 | {
24 | "type": "address",
25 | "name": "template"
26 | }
27 | ],
28 | "constant": false,
29 | "payable": false,
30 | "type": "function",
31 | "gas": 35725
32 | },
33 | {
34 | "name": "createExchange",
35 | "outputs": [
36 | {
37 | "type": "address",
38 | "name": "out"
39 | }
40 | ],
41 | "inputs": [
42 | {
43 | "type": "address",
44 | "name": "token"
45 | }
46 | ],
47 | "constant": false,
48 | "payable": false,
49 | "type": "function",
50 | "gas": 187911
51 | },
52 | {
53 | "name": "getExchange",
54 | "outputs": [
55 | {
56 | "type": "address",
57 | "name": "out"
58 | }
59 | ],
60 | "inputs": [
61 | {
62 | "type": "address",
63 | "name": "token"
64 | }
65 | ],
66 | "constant": true,
67 | "payable": false,
68 | "type": "function",
69 | "gas": 715
70 | },
71 | {
72 | "name": "getToken",
73 | "outputs": [
74 | {
75 | "type": "address",
76 | "name": "out"
77 | }
78 | ],
79 | "inputs": [
80 | {
81 | "type": "address",
82 | "name": "exchange"
83 | }
84 | ],
85 | "constant": true,
86 | "payable": false,
87 | "type": "function",
88 | "gas": 745
89 | },
90 | {
91 | "name": "getTokenWithId",
92 | "outputs": [
93 | {
94 | "type": "address",
95 | "name": "out"
96 | }
97 | ],
98 | "inputs": [
99 | {
100 | "type": "uint256",
101 | "name": "token_id"
102 | }
103 | ],
104 | "constant": true,
105 | "payable": false,
106 | "type": "function",
107 | "gas": 736
108 | },
109 | {
110 | "name": "exchangeTemplate",
111 | "outputs": [
112 | {
113 | "type": "address",
114 | "name": "out"
115 | }
116 | ],
117 | "inputs": [],
118 | "constant": true,
119 | "payable": false,
120 | "type": "function",
121 | "gas": 633
122 | },
123 | {
124 | "name": "tokenCount",
125 | "outputs": [
126 | {
127 | "type": "uint256",
128 | "name": "out"
129 | }
130 | ],
131 | "inputs": [],
132 | "constant": true,
133 | "payable": false,
134 | "type": "function",
135 | "gas": 663
136 | }
137 | ]
--------------------------------------------------------------------------------
/src/uniswap/contracts.ts:
--------------------------------------------------------------------------------
1 | import exchangeAbi from "./abi/Exchange.json";
2 | import factoryAbi from "./abi/Factory.json";
3 |
4 | const contracts = {
5 | factory: {
6 | address: "0xc0a47dFe034B400B47bDaD5FecDa2621de6c4d95",
7 | abi: factoryAbi,
8 | },
9 | exchange: {
10 | abi: exchangeAbi,
11 | },
12 | };
13 |
14 | export default contracts;
15 |
--------------------------------------------------------------------------------
/src/uniswap/contracts/IUniswapExchange.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | interface IUniswapExchange {
4 | // Address of ERC20 token sold on this exchange
5 | function tokenAddress() external view returns (address token);
6 | // Address of Uniswap Factory
7 | function factoryAddress() external view returns (address factory);
8 | // Provide Liquidity
9 | function addLiquidity(uint256 min_liquidity, uint256 max_tokens, uint256 deadline) external payable returns (uint256);
10 | function removeLiquidity(uint256 amount, uint256 min_eth, uint256 min_tokens, uint256 deadline) external returns (uint256, uint256);
11 | // Get Prices
12 | function getEthToTokenInputPrice(uint256 eth_sold) external view returns (uint256 tokens_bought);
13 | function getEthToTokenOutputPrice(uint256 tokens_bought) external view returns (uint256 eth_sold);
14 | function getTokenToEthInputPrice(uint256 tokens_sold) external view returns (uint256 eth_bought);
15 | function getTokenToEthOutputPrice(uint256 eth_bought) external view returns (uint256 tokens_sold);
16 | // Trade ETH to ERC20
17 | function ethToTokenSwapInput(uint256 min_tokens, uint256 deadline) external payable returns (uint256 tokens_bought);
18 | function ethToTokenTransferInput(uint256 min_tokens, uint256 deadline, address recipient) external payable returns (uint256 tokens_bought);
19 | function ethToTokenSwapOutput(uint256 tokens_bought, uint256 deadline) external payable returns (uint256 eth_sold);
20 | function ethToTokenTransferOutput(uint256 tokens_bought, uint256 deadline, address recipient) external payable returns (uint256 eth_sold);
21 | // Trade ERC20 to ETH
22 | function tokenToEthSwapInput(uint256 tokens_sold, uint256 min_eth, uint256 deadline) external returns (uint256 eth_bought);
23 | function tokenToEthTransferInput(uint256 tokens_sold, uint256 min_eth, uint256 deadline, address recipient) external returns (uint256 eth_bought);
24 | function tokenToEthSwapOutput(uint256 eth_bought, uint256 max_tokens, uint256 deadline) external returns (uint256 tokens_sold);
25 | function tokenToEthTransferOutput(uint256 eth_bought, uint256 max_tokens, uint256 deadline, address recipient) external returns (uint256 tokens_sold);
26 | // Trade ERC20 to ERC20
27 | function tokenToTokenSwapInput(uint256 tokens_sold, uint256 min_tokens_bought, uint256 min_eth_bought, uint256 deadline, address token_addr) external returns (uint256 tokens_bought);
28 | function tokenToTokenTransferInput(uint256 tokens_sold, uint256 min_tokens_bought, uint256 min_eth_bought, uint256 deadline, address recipient, address token_addr) external returns (uint256 tokens_bought);
29 | function tokenToTokenSwapOutput(uint256 tokens_bought, uint256 max_tokens_sold, uint256 max_eth_sold, uint256 deadline, address token_addr) external returns (uint256 tokens_sold);
30 | function tokenToTokenTransferOutput(uint256 tokens_bought, uint256 max_tokens_sold, uint256 max_eth_sold, uint256 deadline, address recipient, address token_addr) external returns (uint256 tokens_sold);
31 | // Trade ERC20 to Custom Pool
32 | function tokenToExchangeSwapInput(uint256 tokens_sold, uint256 min_tokens_bought, uint256 min_eth_bought, uint256 deadline, address exchange_addr) external returns (uint256 tokens_bought);
33 | function tokenToExchangeTransferInput(uint256 tokens_sold, uint256 min_tokens_bought, uint256 min_eth_bought, uint256 deadline, address recipient, address exchange_addr) external returns (uint256 tokens_bought);
34 | function tokenToExchangeSwapOutput(uint256 tokens_bought, uint256 max_tokens_sold, uint256 max_eth_sold, uint256 deadline, address exchange_addr) external returns (uint256 tokens_sold);
35 | function tokenToExchangeTransferOutput(uint256 tokens_bought, uint256 max_tokens_sold, uint256 max_eth_sold, uint256 deadline, address recipient, address exchange_addr) external returns (uint256 tokens_sold);
36 | // ERC20 comaptibility for liquidity tokens
37 | function name() external view returns (bytes32);
38 | function symbol() external view returns (bytes32);
39 | function decimals() external view returns (uint256);
40 | function transfer(address _to, uint256 _value) external returns (bool);
41 | function transferFrom(address _from, address _to, uint256 value) external returns (bool);
42 | function approve(address _spender, uint256 _value) external returns (bool);
43 | function allowance(address _owner, address _spender) external view returns (uint256);
44 | function balanceOf(address _owner) external view returns (uint256);
45 | function totalSupply() external view returns (uint256);
46 | // Never use
47 | function setup(address token_addr) external;
48 | }
49 |
--------------------------------------------------------------------------------
/src/uniswap/contracts/IUniswapFactory.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | interface IUniswapFactory {
4 | // Create Exchange
5 | function createExchange(address token) external returns (address exchange);
6 | // Get Exchange and Token Info
7 | function getExchange(address token) external view returns (address exchange);
8 | function getToken(address exchange) external view returns (address token);
9 | function getTokenWithId(uint256 tokenId) external view returns (address token);
10 | // Never use
11 | function initializeFactory(address template) external;
12 | }
--------------------------------------------------------------------------------
/src/uniswap/index.ts:
--------------------------------------------------------------------------------
1 | import { default as contracts } from "./contracts";
2 |
3 | export = {
4 | ...contracts,
5 | };
6 |
--------------------------------------------------------------------------------
/src/uniswapV2/abi/IUniswapV2Factory.json:
--------------------------------------------------------------------------------
1 | [
2 | {
3 | "anonymous": false,
4 | "inputs": [
5 | {
6 | "indexed": true,
7 | "internalType": "address",
8 | "name": "token0",
9 | "type": "address"
10 | },
11 | {
12 | "indexed": true,
13 | "internalType": "address",
14 | "name": "token1",
15 | "type": "address"
16 | },
17 | {
18 | "indexed": false,
19 | "internalType": "address",
20 | "name": "pair",
21 | "type": "address"
22 | },
23 | {
24 | "indexed": false,
25 | "internalType": "uint256",
26 | "name": "",
27 | "type": "uint256"
28 | }
29 | ],
30 | "name": "PairCreated",
31 | "type": "event"
32 | },
33 | {
34 | "constant": true,
35 | "inputs": [
36 | {
37 | "internalType": "uint256",
38 | "name": "",
39 | "type": "uint256"
40 | }
41 | ],
42 | "name": "allPairs",
43 | "outputs": [
44 | {
45 | "internalType": "address",
46 | "name": "pair",
47 | "type": "address"
48 | }
49 | ],
50 | "payable": false,
51 | "stateMutability": "view",
52 | "type": "function"
53 | },
54 | {
55 | "constant": true,
56 | "inputs": [],
57 | "name": "allPairsLength",
58 | "outputs": [
59 | {
60 | "internalType": "uint256",
61 | "name": "",
62 | "type": "uint256"
63 | }
64 | ],
65 | "payable": false,
66 | "stateMutability": "view",
67 | "type": "function"
68 | },
69 | {
70 | "constant": false,
71 | "inputs": [
72 | {
73 | "internalType": "address",
74 | "name": "tokenA",
75 | "type": "address"
76 | },
77 | {
78 | "internalType": "address",
79 | "name": "tokenB",
80 | "type": "address"
81 | }
82 | ],
83 | "name": "createPair",
84 | "outputs": [
85 | {
86 | "internalType": "address",
87 | "name": "pair",
88 | "type": "address"
89 | }
90 | ],
91 | "payable": false,
92 | "stateMutability": "nonpayable",
93 | "type": "function"
94 | },
95 | {
96 | "constant": true,
97 | "inputs": [],
98 | "name": "feeTo",
99 | "outputs": [
100 | {
101 | "internalType": "address",
102 | "name": "",
103 | "type": "address"
104 | }
105 | ],
106 | "payable": false,
107 | "stateMutability": "view",
108 | "type": "function"
109 | },
110 | {
111 | "constant": true,
112 | "inputs": [],
113 | "name": "feeToSetter",
114 | "outputs": [
115 | {
116 | "internalType": "address",
117 | "name": "",
118 | "type": "address"
119 | }
120 | ],
121 | "payable": false,
122 | "stateMutability": "view",
123 | "type": "function"
124 | },
125 | {
126 | "constant": true,
127 | "inputs": [
128 | {
129 | "internalType": "address",
130 | "name": "tokenA",
131 | "type": "address"
132 | },
133 | {
134 | "internalType": "address",
135 | "name": "tokenB",
136 | "type": "address"
137 | }
138 | ],
139 | "name": "getPair",
140 | "outputs": [
141 | {
142 | "internalType": "address",
143 | "name": "pair",
144 | "type": "address"
145 | }
146 | ],
147 | "payable": false,
148 | "stateMutability": "view",
149 | "type": "function"
150 | },
151 | {
152 | "constant": false,
153 | "inputs": [
154 | {
155 | "internalType": "address",
156 | "name": "",
157 | "type": "address"
158 | }
159 | ],
160 | "name": "setFeeTo",
161 | "outputs": [],
162 | "payable": false,
163 | "stateMutability": "nonpayable",
164 | "type": "function"
165 | },
166 | {
167 | "constant": false,
168 | "inputs": [
169 | {
170 | "internalType": "address",
171 | "name": "",
172 | "type": "address"
173 | }
174 | ],
175 | "name": "setFeeToSetter",
176 | "outputs": [],
177 | "payable": false,
178 | "stateMutability": "nonpayable",
179 | "type": "function"
180 | }
181 | ]
182 |
--------------------------------------------------------------------------------
/src/uniswapV2/contracts.ts:
--------------------------------------------------------------------------------
1 | import factoryAbi from "./abi/IUniswapV2Factory.json";
2 | import pairAbi from "./abi/IUniswapV2Pair.json";
3 | import router01Abi from "./abi/IUniswapV2Router01.json";
4 | import router02Abi from "./abi/IUniswapV2Router02.json";
5 |
6 | const contracts = {
7 | factory: {
8 | address: "0x5C69bEe701ef814a2B6a3EDD4B1652CB9cc5aA6f",
9 | abi: factoryAbi,
10 | },
11 | pair: {
12 | abi: pairAbi,
13 | },
14 | router01: {
15 | address: "0xf164fC0Ec4E93095b804a4795bBe1e041497b92a",
16 | abi: router01Abi,
17 | },
18 | router02: {
19 | address: "0x7a250d5630B4cF539739dF2C5dAcb4c659F2488D",
20 | abi: router02Abi,
21 | },
22 | };
23 |
24 | export default contracts;
25 |
--------------------------------------------------------------------------------
/src/uniswapV2/contracts/IUniswapV2Factory.sol:
--------------------------------------------------------------------------------
1 | pragma solidity >=0.5.0;
2 |
3 | interface IUniswapV2Factory {
4 | event PairCreated(address indexed token0, address indexed token1, address pair, uint);
5 |
6 | function getPair(address tokenA, address tokenB) external view returns (address pair);
7 | function allPairs(uint) external view returns (address pair);
8 | function allPairsLength() external view returns (uint);
9 |
10 | function feeTo() external view returns (address);
11 | function feeToSetter() external view returns (address);
12 |
13 | function createPair(address tokenA, address tokenB) external returns (address pair);
14 | }
--------------------------------------------------------------------------------
/src/uniswapV2/contracts/IUniswapV2Pair.sol:
--------------------------------------------------------------------------------
1 | pragma solidity >=0.5.0;
2 |
3 | interface IUniswapV2Pair {
4 | event Approval(address indexed owner, address indexed spender, uint value);
5 | event Transfer(address indexed from, address indexed to, uint value);
6 |
7 | function name() external pure returns (string memory);
8 | function symbol() external pure returns (string memory);
9 | function decimals() external pure returns (uint8);
10 | function totalSupply() external view returns (uint);
11 | function balanceOf(address owner) external view returns (uint);
12 | function allowance(address owner, address spender) external view returns (uint);
13 |
14 | function approve(address spender, uint value) external returns (bool);
15 | function transfer(address to, uint value) external returns (bool);
16 | function transferFrom(address from, address to, uint value) external returns (bool);
17 |
18 | function DOMAIN_SEPARATOR() external view returns (bytes32);
19 | function PERMIT_TYPEHASH() external pure returns (bytes32);
20 | function nonces(address owner) external view returns (uint);
21 |
22 | function permit(address owner, address spender, uint value, uint deadline, uint8 v, bytes32 r, bytes32 s) external;
23 |
24 | event Mint(address indexed sender, uint amount0, uint amount1);
25 | event Burn(address indexed sender, uint amount0, uint amount1, address indexed to);
26 | event Swap(
27 | address indexed sender,
28 | uint amount0In,
29 | uint amount1In,
30 | uint amount0Out,
31 | uint amount1Out,
32 | address indexed to
33 | );
34 | event Sync(uint112 reserve0, uint112 reserve1);
35 |
36 | function MINIMUM_LIQUIDITY() external pure returns (uint);
37 | function factory() external view returns (address);
38 | function token0() external view returns (address);
39 | function token1() external view returns (address);
40 | function getReserves() external view returns (uint112 reserve0, uint112 reserve1, uint32 blockTimestampLast);
41 | function price0CumulativeLast() external view returns (uint);
42 | function price1CumulativeLast() external view returns (uint);
43 | function kLast() external view returns (uint);
44 |
45 | function mint(address to) external returns (uint liquidity);
46 | function burn(address to) external returns (uint amount0, uint amount1);
47 | function swap(uint amount0Out, uint amount1Out, address to, bytes calldata data) external;
48 | function skim(address to) external;
49 | function sync() external;
50 | }
--------------------------------------------------------------------------------
/src/uniswapV2/contracts/IUniswapV2Router01.sol:
--------------------------------------------------------------------------------
1 | pragma solidity >=0.6.2;
2 |
3 | interface IUniswapV2Router01 {
4 | function factory() external pure returns (address);
5 | function WETH() external pure returns (address);
6 |
7 | function addLiquidity(
8 | address tokenA,
9 | address tokenB,
10 | uint amountADesired,
11 | uint amountBDesired,
12 | uint amountAMin,
13 | uint amountBMin,
14 | address to,
15 | uint deadline
16 | ) external returns (uint amountA, uint amountB, uint liquidity);
17 | function addLiquidityETH(
18 | address token,
19 | uint amountTokenDesired,
20 | uint amountTokenMin,
21 | uint amountETHMin,
22 | address to,
23 | uint deadline
24 | ) external payable returns (uint amountToken, uint amountETH, uint liquidity);
25 | function removeLiquidity(
26 | address tokenA,
27 | address tokenB,
28 | uint liquidity,
29 | uint amountAMin,
30 | uint amountBMin,
31 | address to,
32 | uint deadline
33 | ) external returns (uint amountA, uint amountB);
34 | function removeLiquidityETH(
35 | address token,
36 | uint liquidity,
37 | uint amountTokenMin,
38 | uint amountETHMin,
39 | address to,
40 | uint deadline
41 | ) external returns (uint amountToken, uint amountETH);
42 | function removeLiquidityWithPermit(
43 | address tokenA,
44 | address tokenB,
45 | uint liquidity,
46 | uint amountAMin,
47 | uint amountBMin,
48 | address to,
49 | uint deadline,
50 | bool approveMax, uint8 v, bytes32 r, bytes32 s
51 | ) external returns (uint amountA, uint amountB);
52 | function removeLiquidityETHWithPermit(
53 | address token,
54 | uint liquidity,
55 | uint amountTokenMin,
56 | uint amountETHMin,
57 | address to,
58 | uint deadline,
59 | bool approveMax, uint8 v, bytes32 r, bytes32 s
60 | ) external returns (uint amountToken, uint amountETH);
61 | function swapExactTokensForTokens(
62 | uint amountIn,
63 | uint amountOutMin,
64 | address[] calldata path,
65 | address to,
66 | uint deadline
67 | ) external returns (uint[] memory amounts);
68 | function swapTokensForExactTokens(
69 | uint amountOut,
70 | uint amountInMax,
71 | address[] calldata path,
72 | address to,
73 | uint deadline
74 | ) external returns (uint[] memory amounts);
75 | function swapExactETHForTokens(uint amountOutMin, address[] calldata path, address to, uint deadline)
76 | external
77 | payable
78 | returns (uint[] memory amounts);
79 | function swapTokensForExactETH(uint amountOut, uint amountInMax, address[] calldata path, address to, uint deadline)
80 | external
81 | returns (uint[] memory amounts);
82 | function swapExactTokensForETH(uint amountIn, uint amountOutMin, address[] calldata path, address to, uint deadline)
83 | external
84 | returns (uint[] memory amounts);
85 | function swapETHForExactTokens(uint amountOut, address[] calldata path, address to, uint deadline)
86 | external
87 | payable
88 | returns (uint[] memory amounts);
89 |
90 | function quote(uint amountA, uint reserveA, uint reserveB) external pure returns (uint amountB);
91 | function getAmountOut(uint amountIn, uint reserveIn, uint reserveOut) external pure returns (uint amountOut);
92 | function getAmountIn(uint amountOut, uint reserveIn, uint reserveOut) external pure returns (uint amountIn);
93 | function getAmountsOut(uint amountIn, address[] calldata path) external view returns (uint[] memory amounts);
94 | function getAmountsIn(uint amountOut, address[] calldata path) external view returns (uint[] memory amounts);
95 | }
--------------------------------------------------------------------------------
/src/uniswapV2/contracts/IUniswapV2Router02.sol:
--------------------------------------------------------------------------------
1 | pragma solidity >=0.6.2;
2 |
3 | interface IUniswapV2Router01 {
4 | function factory() external pure returns (address);
5 | function WETH() external pure returns (address);
6 |
7 | function addLiquidity(
8 | address tokenA,
9 | address tokenB,
10 | uint amountADesired,
11 | uint amountBDesired,
12 | uint amountAMin,
13 | uint amountBMin,
14 | address to,
15 | uint deadline
16 | ) external returns (uint amountA, uint amountB, uint liquidity);
17 | function addLiquidityETH(
18 | address token,
19 | uint amountTokenDesired,
20 | uint amountTokenMin,
21 | uint amountETHMin,
22 | address to,
23 | uint deadline
24 | ) external payable returns (uint amountToken, uint amountETH, uint liquidity);
25 | function removeLiquidity(
26 | address tokenA,
27 | address tokenB,
28 | uint liquidity,
29 | uint amountAMin,
30 | uint amountBMin,
31 | address to,
32 | uint deadline
33 | ) external returns (uint amountA, uint amountB);
34 | function removeLiquidityETH(
35 | address token,
36 | uint liquidity,
37 | uint amountTokenMin,
38 | uint amountETHMin,
39 | address to,
40 | uint deadline
41 | ) external returns (uint amountToken, uint amountETH);
42 | function removeLiquidityWithPermit(
43 | address tokenA,
44 | address tokenB,
45 | uint liquidity,
46 | uint amountAMin,
47 | uint amountBMin,
48 | address to,
49 | uint deadline,
50 | bool approveMax, uint8 v, bytes32 r, bytes32 s
51 | ) external returns (uint amountA, uint amountB);
52 | function removeLiquidityETHWithPermit(
53 | address token,
54 | uint liquidity,
55 | uint amountTokenMin,
56 | uint amountETHMin,
57 | address to,
58 | uint deadline,
59 | bool approveMax, uint8 v, bytes32 r, bytes32 s
60 | ) external returns (uint amountToken, uint amountETH);
61 | function swapExactTokensForTokens(
62 | uint amountIn,
63 | uint amountOutMin,
64 | address[] calldata path,
65 | address to,
66 | uint deadline
67 | ) external returns (uint[] memory amounts);
68 | function swapTokensForExactTokens(
69 | uint amountOut,
70 | uint amountInMax,
71 | address[] calldata path,
72 | address to,
73 | uint deadline
74 | ) external returns (uint[] memory amounts);
75 | function swapExactETHForTokens(uint amountOutMin, address[] calldata path, address to, uint deadline)
76 | external
77 | payable
78 | returns (uint[] memory amounts);
79 | function swapTokensForExactETH(uint amountOut, uint amountInMax, address[] calldata path, address to, uint deadline)
80 | external
81 | returns (uint[] memory amounts);
82 | function swapExactTokensForETH(uint amountIn, uint amountOutMin, address[] calldata path, address to, uint deadline)
83 | external
84 | returns (uint[] memory amounts);
85 | function swapETHForExactTokens(uint amountOut, address[] calldata path, address to, uint deadline)
86 | external
87 | payable
88 | returns (uint[] memory amounts);
89 |
90 | function quote(uint amountA, uint reserveA, uint reserveB) external pure returns (uint amountB);
91 | function getAmountOut(uint amountIn, uint reserveIn, uint reserveOut) external pure returns (uint amountOut);
92 | function getAmountIn(uint amountOut, uint reserveIn, uint reserveOut) external pure returns (uint amountIn);
93 | function getAmountsOut(uint amountIn, address[] calldata path) external view returns (uint[] memory amounts);
94 | function getAmountsIn(uint amountOut, address[] calldata path) external view returns (uint[] memory amounts);
95 | }
96 |
97 | interface IUniswapV2Router02 is IUniswapV2Router01 {
98 | function removeLiquidityETHSupportingFeeOnTransferTokens(
99 | address token,
100 | uint liquidity,
101 | uint amountTokenMin,
102 | uint amountETHMin,
103 | address to,
104 | uint deadline
105 | ) external returns (uint amountETH);
106 | function removeLiquidityETHWithPermitSupportingFeeOnTransferTokens(
107 | address token,
108 | uint liquidity,
109 | uint amountTokenMin,
110 | uint amountETHMin,
111 | address to,
112 | uint deadline,
113 | bool approveMax, uint8 v, bytes32 r, bytes32 s
114 | ) external returns (uint amountETH);
115 |
116 | function swapExactTokensForTokensSupportingFeeOnTransferTokens(
117 | uint amountIn,
118 | uint amountOutMin,
119 | address[] calldata path,
120 | address to,
121 | uint deadline
122 | ) external;
123 | function swapExactETHForTokensSupportingFeeOnTransferTokens(
124 | uint amountOutMin,
125 | address[] calldata path,
126 | address to,
127 | uint deadline
128 | ) external payable;
129 | function swapExactTokensForETHSupportingFeeOnTransferTokens(
130 | uint amountIn,
131 | uint amountOutMin,
132 | address[] calldata path,
133 | address to,
134 | uint deadline
135 | ) external;
136 | }
--------------------------------------------------------------------------------
/src/uniswapV2/index.ts:
--------------------------------------------------------------------------------
1 | import { default as contracts } from "./contracts";
2 |
3 | export = {
4 | ...contracts,
5 | };
6 |
--------------------------------------------------------------------------------
/tests/aave.test.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 | pragma experimental ABIEncoderV2;
3 |
4 | import "@studydefi/money-legos/aave/contracts/ILendingPool.sol";
5 | import "@studydefi/money-legos/aave/contracts/IFlashLoanReceiver.sol";
6 | import "@studydefi/money-legos/aave/contracts/FlashloanReceiverBase.sol";
7 |
8 | import "@openzeppelin/contracts/token/ERC20/IERC20.sol";
9 |
10 | contract ContractWithFlashLoan is FlashLoanReceiverBase {
11 | address constant AaveLendingPoolAddressProviderAddress = 0x24a42fD28C976A61Df5D00D0599C34c4f90748c8;
12 |
13 | struct MyCustomData {
14 | address a;
15 | uint b;
16 | }
17 |
18 | function executeOperation(
19 | address _reserve,
20 | uint _amount,
21 | uint _fee,
22 | bytes calldata _params
23 | ) external {
24 | // You can pass in some byte-encoded params
25 | MyCustomData memory myCustomData = abi.decode(_params, (MyCustomData));
26 | // myCustomData.a
27 |
28 | // Function is called when loan is given to contract
29 | // Do your logic here, e.g. arbitrage, liquidate compound, etc
30 | // Note that if you don't do your logic, it WILL fail
31 |
32 | // TODO: Change line below
33 | revert("Hello, you haven't implemented your flashloan logic");
34 |
35 | transferFundsBackToPoolInternal(_reserve, _amount.add(_fee));
36 | }
37 |
38 | // Entry point
39 | function initateFlashLoan(
40 | address contractWithFlashLoan,
41 | address assetToFlashLoan,
42 | uint amountToLoan,
43 | bytes calldata _params
44 | ) external {
45 | // Get Aave lending pool
46 | ILendingPool lendingPool = ILendingPool(
47 | ILendingPoolAddressesProvider(AaveLendingPoolAddressProviderAddress)
48 | .getLendingPool()
49 | );
50 |
51 | // Ask for a flashloan
52 | // LendingPool will now execute the `executeOperation` function above
53 | lendingPool.flashLoan(
54 | contractWithFlashLoan, // Which address to callback into, alternatively: address(this)
55 | assetToFlashLoan,
56 | amountToLoan,
57 | _params
58 | );
59 | }
60 | }
--------------------------------------------------------------------------------
/tests/balancer.test.ts:
--------------------------------------------------------------------------------
1 | jest.setTimeout(100000);
2 |
3 | import { Wallet, Contract, ethers } from "ethers";
4 | import erc20 from "../src/erc20";
5 | import balancer from "../src/balancer";
6 | import mstable from "../src/mstable";
7 | import { fromWei } from "./utils";
8 | import { parseUnits } from "ethers/utils";
9 |
10 | const { parseEther, bigNumberify } = ethers.utils;
11 |
12 | const MAX_UINT256 = bigNumberify("2").pow("256").sub("1");
13 |
14 | // Note:
15 | // Balancer uses Smart Order Router (SOR), an off-chain linear optimization of routing orders across pools.
16 | // SOR exists in the Bronze release as a way to aggregate liquidity across all Balancer pools.
17 | // Future releases of Balancer will accomplish this on-chain and allow aggregate contract fillable liquidity.
18 | // See more: https://docs.balancer.finance/protocol/sor
19 | const ETH_MUSD_50_50_POOL_ADDRESS =
20 | "0xe036cce08cf4e23d33bc6b18e53caf532afa8513";
21 | const MUSD_USDC_50_50_POOL_ADDRESS =
22 | "0x72Cd8f4504941Bf8c5a21d1Fd83A96499FD71d2C";
23 |
24 | describe("balancer", () => {
25 | let wallet: Wallet;
26 | let weth: Contract;
27 | let mUSD: Contract;
28 | let usdc: Contract;
29 | let exchangeProxy: Contract;
30 |
31 | beforeAll(async () => {
32 | ethers.errors.setLogLevel("error");
33 |
34 | // @ts-ignore
35 | wallet = global.wallet;
36 | weth = new ethers.Contract(erc20.weth.address, erc20.weth.abi, wallet);
37 | mUSD = new ethers.Contract(mstable.mUSD.address, mstable.mUSD.abi, wallet);
38 | usdc = new ethers.Contract(erc20.usdc.address, erc20.usdc.abi, wallet);
39 | exchangeProxy = new ethers.Contract(
40 | balancer.ExchangeProxy.address,
41 | balancer.ExchangeProxy.abi,
42 | wallet,
43 | );
44 | });
45 |
46 | test("Swap ETH -> mUSD", async () => {
47 | // given
48 | const beforeWei = await mUSD.balanceOf(wallet.address);
49 | const before = parseFloat(fromWei(beforeWei));
50 | expect(before).toEqual(0);
51 |
52 | // when
53 | const tokenInParam = parseEther("10");
54 | const tokenOutParam = 0;
55 | const maxPrice = MAX_UINT256;
56 | const swap = [
57 | ETH_MUSD_50_50_POOL_ADDRESS,
58 | tokenInParam,
59 | tokenOutParam,
60 | maxPrice,
61 | ];
62 | const swaps: any = [swap];
63 |
64 | const tokenOut = mUSD.address;
65 | const minTotalAmountOut = 1;
66 | await exchangeProxy.batchEthInSwapExactIn(
67 | swaps,
68 | tokenOut,
69 | minTotalAmountOut,
70 | {
71 | gasLimit: 500000,
72 | value: tokenInParam,
73 | },
74 | );
75 |
76 | // then
77 | const afterWei = await mUSD.balanceOf(wallet.address);
78 | const after = parseFloat(fromWei(afterWei));
79 | expect(after).toBeGreaterThan(0);
80 | });
81 |
82 | test("Swap some mUSD -> USDC", async () => {
83 | // given
84 | const beforeWei = await usdc.balanceOf(wallet.address);
85 | const before = parseFloat(fromWei(beforeWei));
86 | expect(before).toEqual(0);
87 |
88 | const mUSDToSell = parseEther("1000");
89 | await mUSD.approve(exchangeProxy.address, mUSDToSell);
90 |
91 | // when
92 | const tokenInParam = mUSDToSell;
93 | const tokenOutParam = 0;
94 | const maxPrice = MAX_UINT256;
95 | const swap = [
96 | MUSD_USDC_50_50_POOL_ADDRESS,
97 | tokenInParam,
98 | tokenOutParam,
99 | maxPrice,
100 | ];
101 | const swaps: any = [swap];
102 |
103 | const tokenIn = mUSD.addressPromise;
104 | const tokenOut = usdc.address;
105 | const totalAmountIn = mUSDToSell;
106 | const minTotalAmountOut = 1;
107 | await exchangeProxy.batchSwapExactIn(
108 | swaps,
109 | tokenIn,
110 | tokenOut,
111 | totalAmountIn,
112 | minTotalAmountOut,
113 | {
114 | gasLimit: 500000,
115 | },
116 | );
117 |
118 | // then
119 | const afterWei = await usdc.balanceOf(wallet.address);
120 | const after = parseFloat(fromWei(afterWei));
121 | expect(after).toBeGreaterThan(0);
122 | });
123 |
124 | test("Add liquidity to a pool", async () => {
125 | const pool = new ethers.Contract(
126 | MUSD_USDC_50_50_POOL_ADDRESS,
127 | balancer.BPool.abi,
128 | wallet,
129 | );
130 |
131 | // given
132 | const beforeWei = await pool.balanceOf(wallet.address);
133 | const before = parseFloat(fromWei(beforeWei));
134 | expect(before).toEqual(0);
135 |
136 | await mUSD.approve(pool.address, MAX_UINT256);
137 | await usdc.approve(pool.address, MAX_UINT256);
138 |
139 | const poolAmountOut = parseEther("5");
140 | const maxAmountsIn = [
141 | parseUnits("1000", mstable.mUSD.decimals),
142 | parseUnits("1000", erc20.usdc.decimals),
143 | ];
144 | await pool.joinPool(poolAmountOut, maxAmountsIn, { gasLimit: 500000 });
145 |
146 | const afterWei = await pool.balanceOf(wallet.address);
147 | const after = parseFloat(fromWei(afterWei));
148 | expect(after).toEqual(parseFloat(fromWei(poolAmountOut)));
149 | });
150 | });
151 |
--------------------------------------------------------------------------------
/tests/index.test.ts:
--------------------------------------------------------------------------------
1 | jest.setTimeout(100000);
2 |
3 | import { Wallet, Contract, ethers } from "ethers";
4 | import { fromWei } from "./utils";
5 |
6 | // import legos
7 | import erc20 from "../src/erc20";
8 |
9 | describe("initial conditions", () => {
10 | let wallet: Wallet, daiContract: Contract;
11 |
12 | beforeAll(async () => {
13 | ethers.errors.setLogLevel("error");
14 |
15 | // @ts-ignore
16 | wallet = global.wallet;
17 | daiContract = new ethers.Contract(
18 | erc20.dai.address,
19 | erc20.abi,
20 | wallet,
21 | );
22 | });
23 |
24 | test("initial DAI balance of 0", async () => {
25 | const daiBalance = await daiContract.balanceOf(wallet.address);
26 | expect(fromWei(daiBalance)).toBe("0.0");
27 | });
28 |
29 | test("initial ETH balance of 1000 ETH", async () => {
30 | // note: this is set in test-environment.js when we spin up the test chain
31 | const ethBalance = await wallet.getBalance();
32 | expect(fromWei(ethBalance)).toBe("1000.0");
33 | });
34 | });
35 |
--------------------------------------------------------------------------------
/tests/kyber.test.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.8.0;
2 |
3 | import "@studydefi/money-legos/kyber/contracts/KyberNetworkProxy.sol";
4 | import "@openzeppelin/contracts/token/ERC20/IERC20.sol";
5 |
6 | contract KyberLiteBase {
7 | // Uniswap Mainnet factory address
8 | address constant KyberNetworkProxyAddress = 0x818E6FECD516Ecc3849DAf6845e3EC868087B755;
9 |
10 | function _ethToToken(address tokenAddress, uint ethAmount) internal returns (uint) {
11 | return _ethToToken(tokenAddress, ethAmount, uint(1));
12 | }
13 |
14 | function _ethToToken(address tokenAddress, uint ethAmount, uint minConversionRate) internal returns (uint) {
15 | IERC20 token = IERC20(tokenAddress);
16 | return KyberNetworkProxy(KyberNetworkProxyAddress).swapEtherToToken.value(ethAmount)(token, minConversionRate);
17 | }
18 |
19 | function _tokenToEth(address tokenAddress, uint tokenAmount) internal returns (uint) {
20 | return _tokenToEth(tokenAddress, tokenAmount, uint(1));
21 | }
22 |
23 | function _tokenToEth(address tokenAddress, uint tokenAmount, uint minConversionRate) internal returns (uint) {
24 | KyberNetworkProxy kyber = KyberNetworkProxy(KyberNetworkProxyAddress);
25 |
26 | IERC20 token = IERC20(tokenAddress);
27 |
28 | token.approve(address(kyber), tokenAmount);
29 |
30 | return kyber.swapTokenToEther(token, tokenAmount, minConversionRate);
31 | }
32 |
33 | function _tokenToToken(address from, address to, uint tokenAmount, uint minConversionRate) internal returns (uint) {
34 | KyberNetworkProxy kyber = KyberNetworkProxy(KyberNetworkProxyAddress);
35 |
36 | IERC20(from).approve(address(kyber), tokenAmount);
37 |
38 | return kyber.swapTokenToToken(IERC20(from), tokenAmount, IERC20(to), minConversionRate);
39 | }
40 |
41 | function _tokenToToken(address from, address to, uint tokenAmount) internal returns (uint) {
42 | return _tokenToToken(from, to, tokenAmount, uint(1));
43 | }
44 |
45 | function ethToToken(address tokenAddress) public payable {
46 | IERC20 token = IERC20(tokenAddress);
47 | uint256 tokensAmount = _ethToToken(tokenAddress, msg.value, uint(1));
48 | token.transfer(msg.sender, tokensAmount);
49 | }
50 | }
--------------------------------------------------------------------------------
/tests/kyber.test.ts:
--------------------------------------------------------------------------------
1 | jest.setTimeout(500000);
2 |
3 | import { Wallet, Contract, ethers } from "ethers";
4 | import { fromWei } from "./utils";
5 |
6 | // import legos
7 | import erc20 from "../src/erc20";
8 | import kyber from "../src/kyber";
9 |
10 | const { parseEther, bigNumberify } = ethers.utils;
11 |
12 | describe("kyber", () => {
13 | let wallet: Wallet, daiContract: Contract;
14 |
15 | beforeAll(async () => {
16 | ethers.errors.setLogLevel("error");
17 |
18 | // @ts-ignore
19 | wallet = global.wallet;
20 | daiContract = new ethers.Contract(erc20.dai.address, erc20.abi, wallet);
21 | });
22 |
23 | test("buy DAI from Kyber.Network", async () => {
24 | const kyberNetworkContract = new ethers.Contract(
25 | kyber.network.address,
26 | kyber.network.abi,
27 | wallet,
28 | );
29 |
30 | const ethToSwap = 5;
31 | const ethBeforeWei = await wallet.getBalance();
32 | const daiBeforeWei = await daiContract.balanceOf(wallet.address);
33 |
34 | const {
35 | expectedRate,
36 | slippageRate,
37 | } = await kyberNetworkContract.getExpectedRate(
38 | erc20.eth.address,
39 | erc20.dai.address,
40 | parseEther(`${ethToSwap}`),
41 | );
42 |
43 | const expectedDaiWei = expectedRate.mul(bigNumberify(`${ethToSwap}`));
44 | const expectedDai = parseFloat(fromWei(expectedDaiWei));
45 |
46 | // do the actual swapping
47 | const minConversionRate = slippageRate;
48 | await kyberNetworkContract.swapEtherToToken(
49 | erc20.dai.address,
50 | minConversionRate,
51 | {
52 | gasLimit: 4000000,
53 | value: parseEther(`${ethToSwap}`),
54 | },
55 | );
56 |
57 | const ethAfterWei = await wallet.getBalance();
58 | const daiAfterWei = await daiContract.balanceOf(wallet.address);
59 |
60 | const daiAfter = parseFloat(fromWei(daiAfterWei));
61 | const ethLost = parseFloat(fromWei(ethBeforeWei.sub(ethAfterWei)));
62 |
63 | expect(fromWei(daiBeforeWei)).toBe("0.0");
64 | expect(daiAfter).toBeCloseTo(expectedDai);
65 | expect(ethLost).toBeCloseTo(ethToSwap);
66 | });
67 | });
68 |
--------------------------------------------------------------------------------
/tests/maker.test.ts:
--------------------------------------------------------------------------------
1 | jest.setTimeout(100000);
2 |
3 | import { Wallet, Contract, ethers } from "ethers";
4 | import { fromWei } from "./utils";
5 |
6 | // import legos
7 | import erc20 from "../src/erc20";
8 | import maker from "../src/maker";
9 | import dappsys from "../src/dappsys";
10 |
11 | describe("maker", () => {
12 | let wallet: Wallet, daiContract: Contract;
13 |
14 | beforeAll(async () => {
15 | ethers.errors.setLogLevel("error");
16 |
17 | // @ts-ignore
18 | wallet = global.wallet;
19 | daiContract = new ethers.Contract(erc20.dai.address, erc20.abi, wallet);
20 | });
21 |
22 | test("create a proxy on Maker", async () => {
23 | const proxyRegistry = new ethers.Contract(
24 | maker.proxyRegistry.address,
25 | maker.proxyRegistry.abi,
26 | wallet,
27 | );
28 |
29 | const before = await proxyRegistry.proxies(wallet.address);
30 |
31 | await proxyRegistry.build({ gasLimit: 1500000 });
32 |
33 | const after = await proxyRegistry.proxies(wallet.address);
34 |
35 | expect(before).toBe("0x0000000000000000000000000000000000000000");
36 | expect(after).not.toBe("0x0000000000000000000000000000000000000000");
37 | });
38 |
39 | test("open Vault on Maker", async () => {
40 | const proxyRegistry = new ethers.Contract(
41 | maker.proxyRegistry.address,
42 | maker.proxyRegistry.abi,
43 | wallet,
44 | );
45 |
46 | // Build proxy if we don't have one
47 | let proxyAddress = await proxyRegistry.proxies(wallet.address);
48 | if (proxyAddress === "0x0000000000000000000000000000000000000000") {
49 | await proxyRegistry.build({ gasLimit: 1500000 });
50 | proxyAddress = await proxyRegistry.proxies(wallet.address);
51 | }
52 |
53 | // Note: MakerDAO uses dappsys's DSProxy
54 | const proxyContract = new ethers.Contract(
55 | proxyAddress,
56 | dappsys.dsProxy.abi,
57 | wallet,
58 | );
59 |
60 | // Prepare data for delegate call
61 | const IDssProxyActions = new ethers.utils.Interface(
62 | maker.dssProxyActions.abi,
63 | );
64 |
65 | const _data = IDssProxyActions.functions.openLockETHAndDraw.encode([
66 | maker.dssCdpManager.address,
67 | maker.jug.address,
68 | maker.ethAJoin.address,
69 | maker.daiJoin.address,
70 | ethers.utils.formatBytes32String(maker.ethA.symbol),
71 | ethers.utils.parseUnits("20", erc20.dai.decimals),
72 | ]);
73 |
74 | const ethBefore = await await wallet.getBalance();
75 | const daiBefore = await daiContract.balanceOf(wallet.address);
76 |
77 | // Open vault through proxy
78 | await proxyContract.execute(maker.dssProxyActions.address, _data, {
79 | gasLimit: 2500000,
80 | value: ethers.utils.parseEther("1"),
81 | });
82 |
83 | const ethAfter = await await wallet.getBalance();
84 | const daiAfter = await daiContract.balanceOf(wallet.address);
85 |
86 | const ethSpent = parseFloat(fromWei(ethBefore.sub(ethAfter)));
87 | const daiGained = parseFloat(fromWei(daiAfter.sub(daiBefore)));
88 |
89 | expect(ethSpent).toBeCloseTo(1, 1);
90 | expect(daiGained).toBeCloseTo(20);
91 | });
92 | });
93 |
--------------------------------------------------------------------------------
/tests/medianizer.test.ts:
--------------------------------------------------------------------------------
1 | jest.setTimeout(100000);
2 |
3 | import { Wallet, ethers } from "ethers";
4 |
5 | // import legos
6 | import maker from "../src/maker";
7 | import { fromWei } from "./utils";
8 |
9 | describe("maker medianizer", () => {
10 | let wallet: Wallet;
11 |
12 | beforeAll(async () => {
13 | ethers.errors.setLogLevel("error");
14 |
15 | // @ts-ignore
16 | wallet = global.wallet;
17 | });
18 |
19 | test("read ETH price from medianizer", async () => {
20 | const makerMedianizer = new ethers.Contract(
21 | maker.ethUsdPriceFeed.address,
22 | maker.ethUsdPriceFeed.abi,
23 | wallet,
24 | );
25 |
26 | const ethPriceUsdWei = await makerMedianizer.read();
27 | const ethPriceUsd = parseFloat(fromWei(ethPriceUsdWei));
28 |
29 | expect(ethPriceUsd).toBeGreaterThan(0);
30 | expect(ethPriceUsd).toBeLessThan(1000);
31 | });
32 | });
33 |
--------------------------------------------------------------------------------
/tests/test-environment.js:
--------------------------------------------------------------------------------
1 | const dotenv = require("dotenv");
2 | dotenv.config();
3 |
4 | const { ethers } = require("ethers");
5 | const Ganache = require("ganache-core");
6 | const NodeEnvironment = require("jest-environment-node");
7 |
8 | const startChain = async () => {
9 | if (!process.env.PRIV_KEY || !process.env.MAINNET_NODE_URL) {
10 | throw Error("PRIV_KEY and MAINNET_NODE_URL not found in .env");
11 | }
12 | const ganache = Ganache.provider({
13 | fork: process.env.MAINNET_NODE_URL,
14 | network_id: 1,
15 | accounts: [
16 | {
17 | secretKey: process.env.PRIV_KEY,
18 | balance: ethers.utils.hexlify(ethers.utils.parseEther("1000")),
19 | },
20 | ],
21 | });
22 |
23 | const provider = new ethers.providers.Web3Provider(ganache);
24 | const wallet = new ethers.Wallet(process.env.PRIV_KEY, provider);
25 |
26 | return { wallet, provider };
27 | };
28 |
29 | class CustomEnvironment extends NodeEnvironment {
30 | testPath;
31 | docblockPragmas;
32 |
33 | // Our own vars
34 | wallet;
35 | provider;
36 |
37 | constructor(config, context) {
38 | super(config);
39 | this.testPath = context.testPath;
40 | this.docblockPragmas = context.docblockPragmas;
41 | }
42 |
43 | async setup() {
44 | await super.setup();
45 | const { wallet, provider } = await startChain();
46 | this.wallet = wallet;
47 | this.provider = provider;
48 | this.global.wallet = wallet;
49 | this.global.provider = provider;
50 | }
51 |
52 | async teardown() {
53 | await super.teardown();
54 | }
55 |
56 | //@ts-ignore
57 | runScript(script) {
58 | return super.runScript(script);
59 | }
60 | }
61 |
62 | module.exports = CustomEnvironment;
63 |
--------------------------------------------------------------------------------
/tests/uniswap.test.ts:
--------------------------------------------------------------------------------
1 | jest.setTimeout(100000);
2 |
3 | import { Wallet, Contract, ethers } from "ethers";
4 | import { fromWei } from "./utils";
5 |
6 | // import legos
7 | import erc20 from "../src/erc20";
8 | import uniswap from "../src/uniswap";
9 |
10 | describe("uniswap", () => {
11 | let wallet: Wallet, daiContract: Contract;
12 |
13 | beforeAll(async () => {
14 | ethers.errors.setLogLevel("error");
15 |
16 | // @ts-ignore
17 | wallet = global.wallet;
18 | daiContract = new ethers.Contract(erc20.dai.address, erc20.abi, wallet);
19 | });
20 |
21 | test("buy DAI from Uniswap", async () => {
22 | const uniswapFactoryContract = new ethers.Contract(
23 | uniswap.factory.address,
24 | uniswap.factory.abi,
25 | wallet,
26 | );
27 |
28 | const daiExchangeAddress = await uniswapFactoryContract.getExchange(
29 | erc20.dai.address,
30 | );
31 |
32 | const daiExchangeContract = new ethers.Contract(
33 | daiExchangeAddress,
34 | uniswap.exchange.abi,
35 | wallet,
36 | );
37 |
38 | const ethBefore = await wallet.getBalance();
39 | const daiBefore = await daiContract.balanceOf(wallet.address);
40 |
41 | const expectedDai = await daiExchangeContract.getEthToTokenInputPrice(
42 | ethers.utils.parseEther("5"),
43 | );
44 |
45 | // do the actual swapping
46 | await daiExchangeContract.ethToTokenSwapInput(
47 | 1, // min amount of token retrieved
48 | 2525644800, // random timestamp in the future (year 2050)
49 | {
50 | gasLimit: 4000000,
51 | value: ethers.utils.parseEther("5"),
52 | },
53 | );
54 |
55 | const ethAfter = await wallet.getBalance();
56 | const daiAfter = await daiContract.balanceOf(wallet.address);
57 |
58 | const ethLost = parseFloat(fromWei(ethBefore.sub(ethAfter)));
59 |
60 | expect(fromWei(daiBefore)).toBe("0.0");
61 | expect(fromWei(daiAfter)).toBe(fromWei(expectedDai));
62 | expect(ethLost).toBeCloseTo(5);
63 | });
64 | });
65 |
--------------------------------------------------------------------------------
/tests/uniswapV2.test.ts:
--------------------------------------------------------------------------------
1 | jest.setTimeout(100000);
2 |
3 | import { Wallet, Contract, ethers } from "ethers";
4 | import { fromWei } from "./utils";
5 |
6 | const { parseEther } = ethers.utils;
7 |
8 | // import legos
9 | import erc20 from "../src/erc20";
10 | import uniswapV2 from "../src/uniswapV2";
11 |
12 | describe("uniswapV2", () => {
13 | let wallet: Wallet;
14 | let dai: Contract;
15 |
16 | beforeAll(async () => {
17 | ethers.errors.setLogLevel("error");
18 |
19 | // @ts-ignore
20 | wallet = global.wallet;
21 | dai = new ethers.Contract(erc20.dai.address, erc20.abi, wallet);
22 | });
23 |
24 | test("buy DAI from UniswapV2", async () => {
25 | const uniswapRouter02 = new ethers.Contract(
26 | uniswapV2.router02.address,
27 | uniswapV2.router02.abi,
28 | wallet,
29 | );
30 | const path = [erc20.weth.address, erc20.dai.address];
31 |
32 | const ethBefore = await wallet.getBalance();
33 | const daiBefore = await dai.balanceOf(wallet.address);
34 |
35 | const amountIn = parseEther("5");
36 | const [, expectedDai] = await uniswapRouter02.getAmountsOut(amountIn, path);
37 |
38 | // do the actual swapping
39 | await uniswapRouter02.swapExactETHForTokens(
40 | 1, // amountOutMin
41 | path,
42 | wallet.address, // to
43 | ethers.constants.MaxUint256, // deadline
44 | {
45 | gasLimit: 4000000,
46 | value: amountIn,
47 | },
48 | );
49 |
50 | const ethAfter = await wallet.getBalance();
51 | const daiAfter = await dai.balanceOf(wallet.address);
52 |
53 | const ethLost = parseFloat(fromWei(ethBefore.sub(ethAfter)));
54 |
55 | expect(fromWei(daiBefore)).toBe("0.0");
56 | expect(fromWei(daiAfter)).toBe(fromWei(expectedDai));
57 | expect(ethLost).toBeCloseTo(5);
58 | });
59 | });
60 |
--------------------------------------------------------------------------------
/tests/utils.ts:
--------------------------------------------------------------------------------
1 | import { ethers } from "ethers";
2 | import { BigNumber } from "ethers/utils";
3 |
4 | export const fromWei = (x: BigNumber, u = 18) => ethers.utils.formatUnits(x, u);
5 |
6 | export const mineBlock = async (provider: any, timestamp: number) =>
7 | await provider.send("evm_mine", [timestamp]);
8 |
9 | export const increaseTime = async (provider: any, secsToIncrease: number) => {
10 | const blockNumber = await provider.getBlockNumber();
11 | const { timestamp: currentTimestamp } = await provider.getBlock(blockNumber);
12 | const newTime = Number(currentTimestamp) + Number(secsToIncrease);
13 | await mineBlock(provider, newTime);
14 | };
15 |
--------------------------------------------------------------------------------