From 472bf2c6bb5b28f0b4dee99c28d51fbcb7bdf9e5 Mon Sep 17 00:00:00 2001 From: smitrajput Date: Wed, 3 Mar 2021 00:24:47 +0530 Subject: [PATCH 1/4] feature: integrate stake-dao assets to zerion --- .../stake-dao/StakeDAOTokenAdapter.sol | 75 +++++++++++++++++++ .../stake-dao/StakeDAOVaultAdapter.sol | 32 ++++++++ test/adapters/StakeDaoTokenAdapter.js | 62 +++++++++++++++ 3 files changed, 169 insertions(+) create mode 100644 contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol create mode 100644 contracts/adapters/stake-dao/StakeDAOVaultAdapter.sol create mode 100644 test/adapters/StakeDaoTokenAdapter.js diff --git a/contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol b/contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol new file mode 100644 index 00000000..45c69028 --- /dev/null +++ b/contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol @@ -0,0 +1,75 @@ +// SPDX-License-Identifier: None + +pragma solidity 0.6.5; +pragma experimental ABIEncoderV2; + +import {ERC20} from "../../ERC20.sol"; +import {TokenMetadata, Component} from "../../Structs.sol"; +import {TokenAdapter} from "../TokenAdapter.sol"; + +interface Vault { + function token() external view returns (address); + + function getPricePerFullShare() external view returns (uint256); +} + +/** + * @title Token adapter for Stake DAO Vaults. + * @dev Implementation of TokenAdapter abstract contract. + * @author Elephant memory/strength + */ +contract StakeDaoTokenAdapter is TokenAdapter { + address public sdveCrv = 0x478bBC744811eE8310B461514BDc29D03739084D; + + function setSdveCrv(address newSdveCrv) external { + sdveCrv = newSdveCrv; + } + + /** + * @return TokenMetadata struct with ERC20-style token info. + * @dev Implementation of TokenAdapter interface function. + */ + function getMetadata(address token) + external + view + override + returns (TokenMetadata memory) + { + return + TokenMetadata({ + token: token, + name: ERC20(token).name(), + symbol: ERC20(token).symbol(), + decimals: ERC20(token).decimals() + }); + } + + /** + * @return Array of Component structs with underlying tokens rates for the given token. + * @dev Implementation of TokenAdapter abstract contract function. + */ + function getComponents(address token) + external + view + override + returns (Component[] memory) + { + Component[] memory components = new Component[](1); + + if (token == sdveCrv) { + components[0] = Component({ + token: sdveCrv, + tokenType: "ERC20", + rate: 1e18 + }); + } else { + components[0] = Component({ + token: Vault(token).token(), + tokenType: "ERC20", + rate: Vault(token).getPricePerFullShare() + }); + } + + return components; + } +} diff --git a/contracts/adapters/stake-dao/StakeDAOVaultAdapter.sol b/contracts/adapters/stake-dao/StakeDAOVaultAdapter.sol new file mode 100644 index 00000000..5920b4d4 --- /dev/null +++ b/contracts/adapters/stake-dao/StakeDAOVaultAdapter.sol @@ -0,0 +1,32 @@ +// SPDX-License-Identifier: None + +pragma solidity 0.6.5; +pragma experimental ABIEncoderV2; + +import {ERC20} from "../../ERC20.sol"; +import {ProtocolAdapter} from "../ProtocolAdapter.sol"; + +/** + * @title Adapter for Yearn Token Vaults. + * @dev Implementation of ProtocolAdapter interface. + * @author Igor Sobolev + */ +contract StakeDAOVaultAdapter is ProtocolAdapter { + string public constant override adapterType = "Asset"; + + string public constant override tokenType = "Stake DAO Vault"; + + /** + * @return Amount of Stake DAO Vault Tokens owned by the given account. + * @param token Address of the vault token. + * @dev Implementation of ProtocolAdapter interface function. + */ + function getBalance(address token, address account) + external + view + override + returns (uint256) + { + return ERC20(token).balanceOf(account); + } +} diff --git a/test/adapters/StakeDaoTokenAdapter.js b/test/adapters/StakeDaoTokenAdapter.js new file mode 100644 index 00000000..0b6666f5 --- /dev/null +++ b/test/adapters/StakeDaoTokenAdapter.js @@ -0,0 +1,62 @@ +const TokenAdapter = artifacts.require("StakeDaoTokenAdapter"); + +contract("StakeDaoTokenAdapter", () => { + const sbtcVaultAddress = "0x24129B935AfF071c4f0554882C0D9573F4975fEd"; + const sbtcCrv = "0x075b1bb99792c9E1041bA13afEf80C91a1e70fB3"; + + const sdveCrvAddress = "0x478bBC744811eE8310B461514BDc29D03739084D"; + + let accounts; + let tokenAdapter; + const sbtcVault = [ + sbtcVaultAddress, + "stake dao Curve.fi renBTC/wBTC/sBTC", + "sdcrvRenWSBTC", + "18", + ]; + + const sdveCrvVault = [sdveCrvAddress, "veCRV Stake DAO", "sdveCRV-DAO", "18"]; + + beforeEach(async () => { + accounts = await web3.eth.getAccounts(); + + await TokenAdapter.new({ from: accounts[0] }).then((result) => { + tokenAdapter = result.contract; + }); + }); + + it("should return correct components for sBTC, 3Pool, Eurs vaults", async () => { + await tokenAdapter.methods["getComponents(address)"](sbtcVaultAddress) + .call() + .then((result) => { + assert.equal(result[0][0], sbtcCrv); + assert.equal(result[0][1], "ERC20"); + }); + }); + + it("should return correct metadata for sBTC, 3Pool, Eurs vaults", async () => { + await tokenAdapter.methods["getMetadata(address)"](sbtcVaultAddress) + .call() + .then((result) => { + assert.deepEqual(result, sbtcVault); + }); + }); + + it("should return correct components for perpetual passive strategy vault", async () => { + await tokenAdapter.methods["getComponents(address)"](sdveCrvAddress) + .call() + .then((result) => { + assert.equal(result[0][0], sdveCrvAddress); + assert.equal(result[0][1], "ERC20"); + assert.equal(result[0][2], "1000000000000000000"); + }); + }); + + it("should return correct metadata for perpetual passive strategy vaults", async () => { + await tokenAdapter.methods["getMetadata(address)"](sdveCrvAddress) + .call() + .then((result) => { + assert.deepEqual(result, sdveCrvVault); + }); + }); +}); From 003c265b198368fa428425bb0f369cda0436a60e Mon Sep 17 00:00:00 2001 From: smitrajput Date: Fri, 5 Mar 2021 13:00:54 +0530 Subject: [PATCH 2/4] fix: put CRV as component token for sdveCrv --- contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol | 3 ++- test/adapters/StakeDaoTokenAdapter.js | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol b/contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol index 45c69028..7a2ac1d7 100644 --- a/contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol +++ b/contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol @@ -20,6 +20,7 @@ interface Vault { */ contract StakeDaoTokenAdapter is TokenAdapter { address public sdveCrv = 0x478bBC744811eE8310B461514BDc29D03739084D; + address internal constant CRV = 0xD533a949740bb3306d119CC777fa900bA034cd52; function setSdveCrv(address newSdveCrv) external { sdveCrv = newSdveCrv; @@ -58,7 +59,7 @@ contract StakeDaoTokenAdapter is TokenAdapter { if (token == sdveCrv) { components[0] = Component({ - token: sdveCrv, + token: CRV, tokenType: "ERC20", rate: 1e18 }); diff --git a/test/adapters/StakeDaoTokenAdapter.js b/test/adapters/StakeDaoTokenAdapter.js index 0b6666f5..fa405c2b 100644 --- a/test/adapters/StakeDaoTokenAdapter.js +++ b/test/adapters/StakeDaoTokenAdapter.js @@ -5,6 +5,7 @@ contract("StakeDaoTokenAdapter", () => { const sbtcCrv = "0x075b1bb99792c9E1041bA13afEf80C91a1e70fB3"; const sdveCrvAddress = "0x478bBC744811eE8310B461514BDc29D03739084D"; + const CRV = '0xD533a949740bb3306d119CC777fa900bA034cd52'; let accounts; let tokenAdapter; @@ -46,7 +47,7 @@ contract("StakeDaoTokenAdapter", () => { await tokenAdapter.methods["getComponents(address)"](sdveCrvAddress) .call() .then((result) => { - assert.equal(result[0][0], sdveCrvAddress); + assert.equal(result[0][0], CRV); assert.equal(result[0][1], "ERC20"); assert.equal(result[0][2], "1000000000000000000"); }); From 18386dbb7ee6ddf85e5f24b211e4a2544b5ab445 Mon Sep 17 00:00:00 2001 From: smitrajput Date: Fri, 5 Mar 2021 16:42:57 +0530 Subject: [PATCH 3/4] refactor: remove setSdveCrv() --- contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol b/contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol index 7a2ac1d7..5a705ee7 100644 --- a/contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol +++ b/contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol @@ -19,13 +19,9 @@ interface Vault { * @author Elephant memory/strength */ contract StakeDaoTokenAdapter is TokenAdapter { - address public sdveCrv = 0x478bBC744811eE8310B461514BDc29D03739084D; + address internal constant sdveCrv = 0x478bBC744811eE8310B461514BDc29D03739084D; address internal constant CRV = 0xD533a949740bb3306d119CC777fa900bA034cd52; - function setSdveCrv(address newSdveCrv) external { - sdveCrv = newSdveCrv; - } - /** * @return TokenMetadata struct with ERC20-style token info. * @dev Implementation of TokenAdapter interface function. From a57fa6ed8db55638dc7bd07ebb8a6879aa049055 Mon Sep 17 00:00:00 2001 From: smitrajput Date: Fri, 5 Mar 2021 16:52:16 +0530 Subject: [PATCH 4/4] refactor: rename sdveCrv to SD_VECRV --- contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol b/contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol index 5a705ee7..15f038ff 100644 --- a/contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol +++ b/contracts/adapters/stake-dao/StakeDAOTokenAdapter.sol @@ -19,7 +19,7 @@ interface Vault { * @author Elephant memory/strength */ contract StakeDaoTokenAdapter is TokenAdapter { - address internal constant sdveCrv = 0x478bBC744811eE8310B461514BDc29D03739084D; + address internal constant SD_VECRV = 0x478bBC744811eE8310B461514BDc29D03739084D; address internal constant CRV = 0xD533a949740bb3306d119CC777fa900bA034cd52; /** @@ -53,7 +53,7 @@ contract StakeDaoTokenAdapter is TokenAdapter { { Component[] memory components = new Component[](1); - if (token == sdveCrv) { + if (token == SD_VECRV) { components[0] = Component({ token: CRV, tokenType: "ERC20",