From fe3cd203c34f564568c2dfc0e44278d610e78855 Mon Sep 17 00:00:00 2001 From: shkfnly Date: Wed, 11 Dec 2019 15:23:31 -0500 Subject: [PATCH 1/8] begin check implementation --- .../src/MigrationService.js | 7 +++++-- .../dai-plugin-migrations/src/constants.js | 3 ++- .../src/migrations/ChiefMigrate.js | 18 ++++++++++++++++++ 3 files changed, 25 insertions(+), 3 deletions(-) create mode 100644 packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js diff --git a/packages/dai-plugin-migrations/src/MigrationService.js b/packages/dai-plugin-migrations/src/MigrationService.js index ddd5c245a..80237633a 100644 --- a/packages/dai-plugin-migrations/src/MigrationService.js +++ b/packages/dai-plugin-migrations/src/MigrationService.js @@ -7,12 +7,14 @@ import GlobalSettlementDaiRedeemer from './migrations/GlobalSettlementDaiRedeeme import SaiToDai from './migrations/SaiToDai'; import MkrRedeemer from './migrations/MkrRedeemer'; import DaiToSai from './migrations/DaiToSai'; -const { SINGLE_TO_MULTI_CDP, SAI_TO_DAI, DAI_TO_SAI, MKR_REDEEMER } = Migrations; +import ChiefMigrate from './migrations/ChiefMigrate'; +const { SINGLE_TO_MULTI_CDP, SAI_TO_DAI, DAI_TO_SAI, MKR_REDEEMER, CHIEF_MIGRATE } = Migrations; const migrations = { [SINGLE_TO_MULTI_CDP]: SingleToMultiCdp, [SAI_TO_DAI]: SaiToDai, [DAI_TO_SAI]: DaiToSai, + [CHIEF_MIGRATE]: ChiefMigrate, [Migrations.GLOBAL_SETTLEMENT_SAVINGS_DAI]: GlobalSettlementSavingsDai, [Migrations.GLOBAL_SETTLEMENT_COLLATERAL_CLAIMS]: GlobalSettlementCollateralClaims, [Migrations.GLOBAL_SETTLEMENT_DAI_REDEEMER]: GlobalSettlementDaiRedeemer, @@ -48,7 +50,8 @@ export default class MigrationService extends PublicService { SINGLE_TO_MULTI_CDP ).check(), [SAI_TO_DAI]: await this.getMigration(SAI_TO_DAI).check(), - [DAI_TO_SAI]: await this.getMigration(DAI_TO_SAI).check() + [DAI_TO_SAI]: await this.getMigration(DAI_TO_SAI).check(), + [CHIEF_MIGRATE]: await this.getMigration(CHIEF_MIGRATE).check() // removed until fixed on mainnet: // [MKR_REDEEMER]: await this.getMigration(MKR_REDEEMER).check() }; diff --git a/packages/dai-plugin-migrations/src/constants.js b/packages/dai-plugin-migrations/src/constants.js index 338a85034..8b7520716 100644 --- a/packages/dai-plugin-migrations/src/constants.js +++ b/packages/dai-plugin-migrations/src/constants.js @@ -11,7 +11,8 @@ export const Migrations = { GLOBAL_SETTLEMENT_SAVINGS_DAI: 'global-settlement-savings-dai', GLOBAL_SETTLEMENT_COLLATERAL_CLAIMS: 'global-settlement-collateral-claims', GLOBAL_SETTLEMENT_DAI_REDEEMER: 'global-settlement-dai-redeemer', - MKR_REDEEMER: 'mkr-redeemer' + MKR_REDEEMER: 'mkr-redeemer', + CHIEF_MIGRATE: 'chief-migrate' }; export const WAD = new BigNumber('1e18'); diff --git a/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js b/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js new file mode 100644 index 000000000..a799d9faf --- /dev/null +++ b/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js @@ -0,0 +1,18 @@ + + +export default class ChiefMigrate { + constructor(manager) { + this._manager = manager; + this._oldChief = manager + .get('smartContract') + .getContract('OLD_CHIEF'); + return this; + } + // + async check() { + const address = this._manager.get('accounts').currentAddress(); + const balance = this._oldChief.deposits(address) + return balance.toNumber() > 0; + } + +} From 31168a7edd33c872f4091b2de1b55d3e42a61aa7 Mon Sep 17 00:00:00 2001 From: shkfnly Date: Thu, 12 Dec 2019 16:52:53 -0500 Subject: [PATCH 2/8] scaffold references and defaults --- .../dai-plugin-migrations/src/MigrationService.js | 8 +++++++- packages/dai-plugin-migrations/src/constants.js | 3 ++- .../src/migrations/ChiefMigrate.js | 11 +++-------- 3 files changed, 12 insertions(+), 10 deletions(-) diff --git a/packages/dai-plugin-migrations/src/MigrationService.js b/packages/dai-plugin-migrations/src/MigrationService.js index 80237633a..88f0a592e 100644 --- a/packages/dai-plugin-migrations/src/MigrationService.js +++ b/packages/dai-plugin-migrations/src/MigrationService.js @@ -8,7 +8,13 @@ import SaiToDai from './migrations/SaiToDai'; import MkrRedeemer from './migrations/MkrRedeemer'; import DaiToSai from './migrations/DaiToSai'; import ChiefMigrate from './migrations/ChiefMigrate'; -const { SINGLE_TO_MULTI_CDP, SAI_TO_DAI, DAI_TO_SAI, MKR_REDEEMER, CHIEF_MIGRATE } = Migrations; +const { + SINGLE_TO_MULTI_CDP, + SAI_TO_DAI, + DAI_TO_SAI, + MKR_REDEEMER, + CHIEF_MIGRATE +} = Migrations; const migrations = { [SINGLE_TO_MULTI_CDP]: SingleToMultiCdp, diff --git a/packages/dai-plugin-migrations/src/constants.js b/packages/dai-plugin-migrations/src/constants.js index 8b7520716..d0e869cef 100644 --- a/packages/dai-plugin-migrations/src/constants.js +++ b/packages/dai-plugin-migrations/src/constants.js @@ -12,7 +12,8 @@ export const Migrations = { GLOBAL_SETTLEMENT_COLLATERAL_CLAIMS: 'global-settlement-collateral-claims', GLOBAL_SETTLEMENT_DAI_REDEEMER: 'global-settlement-dai-redeemer', MKR_REDEEMER: 'mkr-redeemer', - CHIEF_MIGRATE: 'chief-migrate' + CHIEF_MIGRATE: 'chief-migrate', + VOTE_PROXY: 'vote-proxy' }; export const WAD = new BigNumber('1e18'); diff --git a/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js b/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js index a799d9faf..7fbd16b58 100644 --- a/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js +++ b/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js @@ -1,18 +1,13 @@ - - export default class ChiefMigrate { constructor(manager) { this._manager = manager; - this._oldChief = manager - .get('smartContract') - .getContract('OLD_CHIEF'); + this._oldChief = manager.get('smartContract').getContract('OLD_CHIEF'); return this; } // async check() { const address = this._manager.get('accounts').currentAddress(); - const balance = this._oldChief.deposits(address) - return balance.toNumber() > 0; + const balance = this._oldChief.deposits(address); + return balance.toNumber(); } - } From ee72f63a6cce2d2b069c5f05e450fb351819ffde Mon Sep 17 00:00:00 2001 From: shkfnly Date: Fri, 13 Dec 2019 16:49:47 -0500 Subject: [PATCH 3/8] First implementation of Chief Migrate --- .../contracts/abiMap.json | 3 +- .../contracts/addresses/testnet.json | 3 +- .../src/migrations/ChiefMigrate.js | 33 ++++++++++++++----- 3 files changed, 28 insertions(+), 11 deletions(-) diff --git a/packages/dai-plugin-migrations/contracts/abiMap.json b/packages/dai-plugin-migrations/contracts/abiMap.json index 4129cd1df..c93589f08 100644 --- a/packages/dai-plugin-migrations/contracts/abiMap.json +++ b/packages/dai-plugin-migrations/contracts/abiMap.json @@ -9,5 +9,6 @@ "REDEEMER": "Redeemer", "MIGRATION": "ScdMcdMigration", "MIGRATION_PROXY_ACTIONS": "MigrationProxyActions", - "OLD_CHIEF": "DSChief" + "OLD_CHIEF": "DSChief", + "VOTE_PROXY_FACTORY": "VoteProxyFactory" } diff --git a/packages/dai-plugin-migrations/contracts/addresses/testnet.json b/packages/dai-plugin-migrations/contracts/addresses/testnet.json index 30c0332d0..1a9bd3e44 100644 --- a/packages/dai-plugin-migrations/contracts/addresses/testnet.json +++ b/packages/dai-plugin-migrations/contracts/addresses/testnet.json @@ -10,5 +10,6 @@ "OLD_MKR": "0x661dc0bbe25ddedbe5a8cd68fa8117002d9a373c", "MIGRATION": "0x313450288048d2294649a86127066d462fe16dc4", "MIGRATION_PROXY_ACTIONS": "0xfdb977224348da0da32fc153bc808bef1c92bd1e", - "OLD_CHIEF": "0xaeb199d9984c1da63d9529e03bf57691f426a492" + "OLD_CHIEF": "0xaeb199d9984c1da63d9529e03bf57691f426a492", + "VOTE_PROXY_FACTORY": "0xc0b037c4206b5faa9a6dff03117089da3833a85e" } diff --git a/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js b/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js index 7fbd16b58..0272ebd1f 100644 --- a/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js +++ b/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js @@ -1,13 +1,28 @@ +import BigNumber from 'bignumber.js' + +/* Addresses */ +export const ZERO_ADDRESS = '0x0000000000000000000000000000000000000000' + export default class ChiefMigrate { - constructor(manager) { - this._manager = manager; - this._oldChief = manager.get('smartContract').getContract('OLD_CHIEF'); - return this; + constructor (manager) { + this._manager = manager + this._oldChief = manager.get('smartContract').getContract('OLD_CHIEF') + this._proxyFactoryContract = manager.get('smartContract').getContractByName('VOTE_PROXY_FACTORY') + return this } - // - async check() { - const address = this._manager.get('accounts').currentAddress(); - const balance = this._oldChief.deposits(address); - return balance.toNumber(); + + async check () { + const address = this._manager.get('accounts').currentAddress() + const balance = this._oldChief.deposits(address) + const [proxyAddressCold, proxyAddressHot] = await Promise.all([ + this._proxyFactoryContract.coldMap(address), + this._proxyFactoryContract.hotMap(address) + ]) + const proxyBalance = proxyAddressCold !== ZERO_ADDRESS + ? this._oldChief.deposits(proxyAddressCold) + : proxyAddressHot !== ZERO_ADDRESS + ? this._oldChief.deposits(proxyAddressHot) + : BigNumber(0) + return [balance, proxyBalance] } } From cf28bf76d9f05a1c53420cccad86acc70cfa0bd1 Mon Sep 17 00:00:00 2001 From: shkfnly Date: Fri, 13 Dec 2019 16:50:05 -0500 Subject: [PATCH 4/8] linting update --- .../contracts/abis/VoteProxyFactory.json | 1 + .../src/migrations/ChiefMigrate.js | 35 ++++++++++--------- 2 files changed, 20 insertions(+), 16 deletions(-) create mode 100644 packages/dai-plugin-migrations/contracts/abis/VoteProxyFactory.json diff --git a/packages/dai-plugin-migrations/contracts/abis/VoteProxyFactory.json b/packages/dai-plugin-migrations/contracts/abis/VoteProxyFactory.json new file mode 100644 index 000000000..7159deaf1 --- /dev/null +++ b/packages/dai-plugin-migrations/contracts/abis/VoteProxyFactory.json @@ -0,0 +1 @@ +[{"inputs":[{"internalType":"contract DSChief","name":"chief_","type":"address"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"cold","type":"address"},{"indexed":true,"internalType":"address","name":"hot","type":"address"},{"indexed":true,"internalType":"address","name":"voteProxy","type":"address"}],"name":"LinkConfirmed","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"cold","type":"address"},{"indexed":true,"internalType":"address","name":"hot","type":"address"}],"name":"LinkRequested","type":"event"},{"constant":false,"inputs":[{"internalType":"address","name":"cold","type":"address"}],"name":"approveLink","outputs":[{"internalType":"contract VoteProxy","name":"voteProxy","type":"address"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[],"name":"breakLink","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"chief","outputs":[{"internalType":"contract DSChief","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"coldMap","outputs":[{"internalType":"contract VoteProxy","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"internalType":"address","name":"guy","type":"address"}],"name":"hasProxy","outputs":[{"internalType":"bool","name":"","type":"bool"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"hotMap","outputs":[{"internalType":"contract VoteProxy","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"hot","type":"address"}],"name":"initiateLink","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"linkRequests","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[],"name":"linkSelf","outputs":[{"internalType":"contract VoteProxy","name":"voteProxy","type":"address"}],"payable":false,"stateMutability":"nonpayable","type":"function"}] \ No newline at end of file diff --git a/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js b/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js index 0272ebd1f..c901934ce 100644 --- a/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js +++ b/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js @@ -1,28 +1,31 @@ -import BigNumber from 'bignumber.js' +import BigNumber from 'bignumber.js'; /* Addresses */ -export const ZERO_ADDRESS = '0x0000000000000000000000000000000000000000' +export const ZERO_ADDRESS = '0x0000000000000000000000000000000000000000'; export default class ChiefMigrate { - constructor (manager) { - this._manager = manager - this._oldChief = manager.get('smartContract').getContract('OLD_CHIEF') - this._proxyFactoryContract = manager.get('smartContract').getContractByName('VOTE_PROXY_FACTORY') - return this + constructor(manager) { + this._manager = manager; + this._oldChief = manager.get('smartContract').getContract('OLD_CHIEF'); + this._proxyFactoryContract = manager + .get('smartContract') + .getContractByName('VOTE_PROXY_FACTORY'); + return this; } - async check () { - const address = this._manager.get('accounts').currentAddress() - const balance = this._oldChief.deposits(address) + async check() { + const address = this._manager.get('accounts').currentAddress(); + const balance = this._oldChief.deposits(address); const [proxyAddressCold, proxyAddressHot] = await Promise.all([ this._proxyFactoryContract.coldMap(address), this._proxyFactoryContract.hotMap(address) - ]) - const proxyBalance = proxyAddressCold !== ZERO_ADDRESS - ? this._oldChief.deposits(proxyAddressCold) - : proxyAddressHot !== ZERO_ADDRESS + ]); + const proxyBalance = + proxyAddressCold !== ZERO_ADDRESS + ? this._oldChief.deposits(proxyAddressCold) + : proxyAddressHot !== ZERO_ADDRESS ? this._oldChief.deposits(proxyAddressHot) - : BigNumber(0) - return [balance, proxyBalance] + : BigNumber(0); + return [balance, proxyBalance]; } } From 2cbfd88ddd5ef166a6b8c5f9ea37b81bdbf1c43e Mon Sep 17 00:00:00 2001 From: Josh Levine Date: Mon, 16 Dec 2019 17:01:32 -0500 Subject: [PATCH 5/8] return object from chief mig check + tests tests: 1) a sanity chief mig check test and 2) a test for mkr locked directly in chief --- .../contracts/abis/VoteProxy.json | 102 ++++++++++++++++++ .../src/migrations/ChiefMigrate.js | 35 +++--- .../test/migrations/ChiefMigrate.spec.js | 73 +++++++++++++ 3 files changed, 197 insertions(+), 13 deletions(-) create mode 100644 packages/dai-plugin-migrations/contracts/abis/VoteProxy.json create mode 100644 packages/dai-plugin-migrations/test/migrations/ChiefMigrate.spec.js diff --git a/packages/dai-plugin-migrations/contracts/abis/VoteProxy.json b/packages/dai-plugin-migrations/contracts/abis/VoteProxy.json new file mode 100644 index 000000000..d4038d4be --- /dev/null +++ b/packages/dai-plugin-migrations/contracts/abis/VoteProxy.json @@ -0,0 +1,102 @@ +[ + { + "constant": true, + "inputs": [], + "name": "gov", + "outputs": [{ "name": "", "type": "address" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "cold", + "outputs": [{ "name": "", "type": "address" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [], + "name": "freeAll", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "iou", + "outputs": [{ "name": "", "type": "address" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [{ "name": "slate", "type": "bytes32" }], + "name": "vote", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [{ "name": "wad", "type": "uint256" }], + "name": "free", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": false, + "inputs": [{ "name": "wad", "type": "uint256" }], + "name": "lock", + "outputs": [], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "hot", + "outputs": [{ "name": "", "type": "address" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "constant": false, + "inputs": [{ "name": "yays", "type": "address[]" }], + "name": "vote", + "outputs": [{ "name": "", "type": "bytes32" }], + "payable": false, + "stateMutability": "nonpayable", + "type": "function" + }, + { + "constant": true, + "inputs": [], + "name": "chief", + "outputs": [{ "name": "", "type": "address" }], + "payable": false, + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { "name": "_chief", "type": "address" }, + { "name": "_cold", "type": "address" }, + { "name": "_hot", "type": "address" } + ], + "payable": false, + "stateMutability": "nonpayable", + "type": "constructor" + } +] diff --git a/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js b/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js index c901934ce..7a2108202 100644 --- a/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js +++ b/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js @@ -1,7 +1,6 @@ -import BigNumber from 'bignumber.js'; +import { MKR } from '..'; -/* Addresses */ -export const ZERO_ADDRESS = '0x0000000000000000000000000000000000000000'; +const ZERO_ADDRESS = '0x0000000000000000000000000000000000000000'; export default class ChiefMigrate { constructor(manager) { @@ -15,17 +14,27 @@ export default class ChiefMigrate { async check() { const address = this._manager.get('accounts').currentAddress(); - const balance = this._oldChief.deposits(address); + + const voteProxyAddress = await this._getVoteProxyAddress(address); + + const mkrLockedDirectly = MKR.wei(await this._oldChief.deposits(address)); + const mkrLockedViaProxy = MKR.wei( + voteProxyAddress ? await this._oldChief.deposits(voteProxyAddress) : 0 + ); + + return { mkrLockedDirectly, mkrLockedViaProxy }; + } + + async execute() {} + + async _getVoteProxyAddress(walletAddress) { const [proxyAddressCold, proxyAddressHot] = await Promise.all([ - this._proxyFactoryContract.coldMap(address), - this._proxyFactoryContract.hotMap(address) + this._proxyFactoryContract.coldMap(walletAddress), + this._proxyFactoryContract.hotMap(walletAddress) ]); - const proxyBalance = - proxyAddressCold !== ZERO_ADDRESS - ? this._oldChief.deposits(proxyAddressCold) - : proxyAddressHot !== ZERO_ADDRESS - ? this._oldChief.deposits(proxyAddressHot) - : BigNumber(0); - return [balance, proxyBalance]; + + if (proxyAddressCold !== ZERO_ADDRESS) return proxyAddressCold; + if (proxyAddressHot !== ZERO_ADDRESS) return proxyAddressHot; + return null; } } diff --git a/packages/dai-plugin-migrations/test/migrations/ChiefMigrate.spec.js b/packages/dai-plugin-migrations/test/migrations/ChiefMigrate.spec.js new file mode 100644 index 000000000..87c6e0710 --- /dev/null +++ b/packages/dai-plugin-migrations/test/migrations/ChiefMigrate.spec.js @@ -0,0 +1,73 @@ +import { migrationMaker } from '../helpers'; +import { ServiceRoles, Migrations } from '../../src/constants'; +import { takeSnapshot, restoreSnapshot } from '@makerdao/test-helpers'; +import { MKR } from '../../src'; +// import voteProxyAbi from '../../contracts/abis/VoteProxy.json'; + +let maker, migration, snapshot; + +describe('Chief Migration', () => { + beforeAll(async () => { + maker = await migrationMaker(); + const service = maker.service(ServiceRoles.MIGRATION); + migration = service.getMigration(Migrations.CHIEF_MIGRATE); + snapshot = await takeSnapshot(maker); + }); + + afterAll(async () => { + restoreSnapshot(snapshot, maker); + }); + + test('if the account has no MKR in old chief, return 0', async () => { + const { mkrLockedDirectly, mkrLockedViaProxy } = await migration.check(); + expect(mkrLockedDirectly.toNumber()).toBe(0); + expect(mkrLockedViaProxy.toNumber()).toBe(0); + }); + + test('if the account has some MKR locked directly in old chief, return the amount', async () => { + const oldChief = maker + .service('smartContract') + .getContractByName('OLD_CHIEF'); + + await maker + .service('token') + .getToken(MKR) + .approveUnlimited(oldChief.address); + + const LOCK_AMOUNT = MKR('5.123456789123456789'); + await oldChief.lock(LOCK_AMOUNT.toFixed('wei')); + + const { mkrLockedDirectly, mkrLockedViaProxy } = await migration.check(); + expect(mkrLockedDirectly.isEqual(LOCK_AMOUNT)).toBeTruthy(); + expect(mkrLockedViaProxy.toNumber()).toBe(0); + }); + + // TODO + test.skip('if the account has some MKR locked via proxy in old chief, return the amount', async () => { + // const oldChief = maker + // .service('smartContract') + // .getContractByName('OLD_CHIEF'); + // const voteProxyFactory = maker + // .service('smartContract') + // .getContractByName('VOTE_PROXY_FACTORY'); + // cold + // voteProxyFactory.initiateLink(hot); + // hot + // voteProxyFactory.approveLink(cold); + // back to cold + // const voteProxyAddress = migration._getVoteProxyAddress(cold); + // console.log('voteProxyAbi', voteProxyAbi); + // const voteProxy = maker + // .service('smartContract') + // .getContractByAddressAndAbi(voteProxyAddress, voteProxyAbi); + // await maker + // .service('token') + // .getToken(MKR) + // .approveUnlimited(voteProxyAddress); + // const LOCK_AMOUNT = MKR('5.123456789123456789'); + // await voteProxy.lock(LOCK_AMOUNT.toFixed('wei')); + // const { mkrLockedDirectly, mkrLockedViaProxy } = await migration.check(); + // expect(mkrLockedDirectly.toNumber()).toBe(0); + // expect(mkrLockedViaProxy.isEqual(LOCK_AMOUNT)).toBeTruthy(); + }); +}); From ff00507910e824440c22f937e9dfaf120a3e68df Mon Sep 17 00:00:00 2001 From: Josh Levine Date: Mon, 16 Dec 2019 17:15:41 -0500 Subject: [PATCH 6/8] account for chief mig in mig service spec --- packages/dai-plugin-migrations/src/constants.js | 3 +-- .../dai-plugin-migrations/test/MigrationService.spec.js | 8 +++++--- 2 files changed, 6 insertions(+), 5 deletions(-) diff --git a/packages/dai-plugin-migrations/src/constants.js b/packages/dai-plugin-migrations/src/constants.js index d0e869cef..8b7520716 100644 --- a/packages/dai-plugin-migrations/src/constants.js +++ b/packages/dai-plugin-migrations/src/constants.js @@ -12,8 +12,7 @@ export const Migrations = { GLOBAL_SETTLEMENT_COLLATERAL_CLAIMS: 'global-settlement-collateral-claims', GLOBAL_SETTLEMENT_DAI_REDEEMER: 'global-settlement-dai-redeemer', MKR_REDEEMER: 'mkr-redeemer', - CHIEF_MIGRATE: 'chief-migrate', - VOTE_PROXY: 'vote-proxy' + CHIEF_MIGRATE: 'chief-migrate' }; export const WAD = new BigNumber('1e18'); diff --git a/packages/dai-plugin-migrations/test/MigrationService.spec.js b/packages/dai-plugin-migrations/test/MigrationService.spec.js index 38841095f..b0b3b6af4 100644 --- a/packages/dai-plugin-migrations/test/MigrationService.spec.js +++ b/packages/dai-plugin-migrations/test/MigrationService.spec.js @@ -40,10 +40,11 @@ test('can fetch a list of all migrations', () => { Migrations.GLOBAL_SETTLEMENT_SAVINGS_DAI, Migrations.GLOBAL_SETTLEMENT_COLLATERAL_CLAIMS, Migrations.GLOBAL_SETTLEMENT_DAI_REDEEMER, - Migrations.MKR_REDEEMER + Migrations.MKR_REDEEMER, + Migrations.CHIEF_MIGRATE ]) ); - expect(ids.length).toEqual(7); + expect(ids.length).toEqual(8); }); test('getting each migration returns a valid migration', () => { @@ -77,7 +78,8 @@ test('runAllChecks', async () => { [Migrations.DAI_TO_SAI]: expect.anything(), // removed until fixed on mainnet: // [Migrations.MKR_REDEEMER]: expect.anything(), - [Migrations.SINGLE_TO_MULTI_CDP]: {} + [Migrations.SINGLE_TO_MULTI_CDP]: {}, + [Migrations.CHIEF_MIGRATE]: expect.anything() }); expect(result[Migrations.SAI_TO_DAI].eq(0)).toBeTruthy(); }); From b04c61e2dd48b66c389f5f3d9d63a63b1f21618a Mon Sep 17 00:00:00 2001 From: Josh Levine Date: Tue, 17 Dec 2019 02:53:09 -0500 Subject: [PATCH 7/8] update mig plugin addresses, VOTE_PROXY_FACTORY -> OLD_VOTE_PROXY_FACTORY --- packages/dai-plugin-migrations/contracts/abiMap.json | 2 +- .../dai-plugin-migrations/contracts/addresses/kovan.json | 4 +++- .../dai-plugin-migrations/contracts/addresses/mainnet.json | 6 ++++-- .../dai-plugin-migrations/contracts/addresses/testnet.json | 3 ++- .../dai-plugin-migrations/src/migrations/ChiefMigrate.js | 2 +- 5 files changed, 11 insertions(+), 6 deletions(-) diff --git a/packages/dai-plugin-migrations/contracts/abiMap.json b/packages/dai-plugin-migrations/contracts/abiMap.json index c93589f08..e313a5799 100644 --- a/packages/dai-plugin-migrations/contracts/abiMap.json +++ b/packages/dai-plugin-migrations/contracts/abiMap.json @@ -10,5 +10,5 @@ "MIGRATION": "ScdMcdMigration", "MIGRATION_PROXY_ACTIONS": "MigrationProxyActions", "OLD_CHIEF": "DSChief", - "VOTE_PROXY_FACTORY": "VoteProxyFactory" + "OLD_VOTE_PROXY_FACTORY": "VoteProxyFactory" } diff --git a/packages/dai-plugin-migrations/contracts/addresses/kovan.json b/packages/dai-plugin-migrations/contracts/addresses/kovan.json index f1e7e96ad..42094e3c9 100644 --- a/packages/dai-plugin-migrations/contracts/addresses/kovan.json +++ b/packages/dai-plugin-migrations/contracts/addresses/kovan.json @@ -9,5 +9,7 @@ "REDEEMER": "0x2c0f31271673cc29927be725104642aad65a253e", "OLD_MKR": "0x4bb514a7f83fbb13c2b41448208e89fabbcfe2fb", "MIGRATION": "0x411b2faa662c8e3e5cf8f01dfdae0aee482ca7b0", - "MIGRATION_PROXY_ACTIONS": "0xf56765d255463139d3aff1613705a5520764ab93" + "MIGRATION_PROXY_ACTIONS": "0xf56765d255463139d3aff1613705a5520764ab93", + "OLD_CHIEF": "0xbbffc76e94b34f72d96d054b31f6424249c1337d", + "OLD_VOTE_PROXY_FACTORY": "0x3E08741A68c2d964d172793cD0Ad14292F658cd8" } diff --git a/packages/dai-plugin-migrations/contracts/addresses/mainnet.json b/packages/dai-plugin-migrations/contracts/addresses/mainnet.json index 1ddbff3ec..266aba8ca 100644 --- a/packages/dai-plugin-migrations/contracts/addresses/mainnet.json +++ b/packages/dai-plugin-migrations/contracts/addresses/mainnet.json @@ -6,6 +6,8 @@ "CDP_MANAGER_1": "0x5ef30b9986345249bc32d8928b7ee64de9435e39", "MCD_END_1": "0xab14d3ce3f733cacb76ec2abe7d2fcb00c99f3d5", "MCD_VAT_1": "0x35d1b3f3d7966a1dfe207aa4514c12a259a0492b", - "MCD_DAI_1" : "0x6b175474e89094c44da98b954eedeac495271d0f", - "MCD_POT_1": "0x197e90f9fad81970ba7976f33cbd77088e5d7cf7" + "MCD_DAI_1": "0x6b175474e89094c44da98b954eedeac495271d0f", + "MCD_POT_1": "0x197e90f9fad81970ba7976f33cbd77088e5d7cf7", + "OLD_CHIEF": "0x8e2a84d6ade1e7fffee039a35ef5f19f13057152", + "OLD_VOTE_PROXY_FACTORY": "0xa63E145309cadaa6A903a19993868Ef7E85058BE" } diff --git a/packages/dai-plugin-migrations/contracts/addresses/testnet.json b/packages/dai-plugin-migrations/contracts/addresses/testnet.json index 285f2b6bc..9982d9107 100644 --- a/packages/dai-plugin-migrations/contracts/addresses/testnet.json +++ b/packages/dai-plugin-migrations/contracts/addresses/testnet.json @@ -10,5 +10,6 @@ "OLD_MKR": "0x1e1e0cb82b75fda8d3653bef925bf1babd160067", "MIGRATION": "0x1f8d3148c725de9d31751c9f8cb764c8ee6d9719", "MIGRATION_PROXY_ACTIONS": "0x5f295c5589118d2f8eab6488c366d42c0f54882c", - "OLD_CHIEF": "0xe50ff8544b50e2e0f25cab27bc85a7a905d5671a" + "OLD_CHIEF": "0xe50ff8544b50e2e0f25cab27bc85a7a905d5671a", + "OLD_VOTE_PROXY_FACTORY": "0x17d4edea99fad126ce0b3ed46646587d067f4f8c" } diff --git a/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js b/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js index 7a2108202..758ca2d0c 100644 --- a/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js +++ b/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js @@ -8,7 +8,7 @@ export default class ChiefMigrate { this._oldChief = manager.get('smartContract').getContract('OLD_CHIEF'); this._proxyFactoryContract = manager .get('smartContract') - .getContractByName('VOTE_PROXY_FACTORY'); + .getContractByName('OLD_VOTE_PROXY_FACTORY'); return this; } From 4c6c259d82b8486ef1f2447daba71faf18b35bb7 Mon Sep 17 00:00:00 2001 From: Josh Levine Date: Tue, 17 Dec 2019 03:31:52 -0500 Subject: [PATCH 8/8] add test for vote proxy mkr deposit check --- .../src/migrations/ChiefMigrate.js | 9 +-- .../test/migrations/ChiefMigrate.spec.js | 80 ++++++++++++------- 2 files changed, 52 insertions(+), 37 deletions(-) diff --git a/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js b/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js index 758ca2d0c..e4b209241 100644 --- a/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js +++ b/packages/dai-plugin-migrations/src/migrations/ChiefMigrate.js @@ -6,7 +6,7 @@ export default class ChiefMigrate { constructor(manager) { this._manager = manager; this._oldChief = manager.get('smartContract').getContract('OLD_CHIEF'); - this._proxyFactoryContract = manager + this._oldProxyFactoryContract = manager .get('smartContract') .getContractByName('OLD_VOTE_PROXY_FACTORY'); return this; @@ -14,7 +14,6 @@ export default class ChiefMigrate { async check() { const address = this._manager.get('accounts').currentAddress(); - const voteProxyAddress = await this._getVoteProxyAddress(address); const mkrLockedDirectly = MKR.wei(await this._oldChief.deposits(address)); @@ -25,12 +24,10 @@ export default class ChiefMigrate { return { mkrLockedDirectly, mkrLockedViaProxy }; } - async execute() {} - async _getVoteProxyAddress(walletAddress) { const [proxyAddressCold, proxyAddressHot] = await Promise.all([ - this._proxyFactoryContract.coldMap(walletAddress), - this._proxyFactoryContract.hotMap(walletAddress) + this._oldProxyFactoryContract.coldMap(walletAddress), + this._oldProxyFactoryContract.hotMap(walletAddress) ]); if (proxyAddressCold !== ZERO_ADDRESS) return proxyAddressCold; diff --git a/packages/dai-plugin-migrations/test/migrations/ChiefMigrate.spec.js b/packages/dai-plugin-migrations/test/migrations/ChiefMigrate.spec.js index 87c6e0710..81c56fdf1 100644 --- a/packages/dai-plugin-migrations/test/migrations/ChiefMigrate.spec.js +++ b/packages/dai-plugin-migrations/test/migrations/ChiefMigrate.spec.js @@ -1,8 +1,12 @@ import { migrationMaker } from '../helpers'; import { ServiceRoles, Migrations } from '../../src/constants'; -import { takeSnapshot, restoreSnapshot } from '@makerdao/test-helpers'; +import { + takeSnapshot, + restoreSnapshot, + TestAccountProvider +} from '@makerdao/test-helpers'; import { MKR } from '../../src'; -// import voteProxyAbi from '../../contracts/abis/VoteProxy.json'; +import voteProxyAbi from '../../contracts/abis/VoteProxy.json'; let maker, migration, snapshot; @@ -11,14 +15,17 @@ describe('Chief Migration', () => { maker = await migrationMaker(); const service = maker.service(ServiceRoles.MIGRATION); migration = service.getMigration(Migrations.CHIEF_MIGRATE); + }); + + beforeEach(async () => { snapshot = await takeSnapshot(maker); }); - afterAll(async () => { + afterEach(() => { restoreSnapshot(snapshot, maker); }); - test('if the account has no MKR in old chief, return 0', async () => { + test('if the account has no MKR locked in old chief, return 0', async () => { const { mkrLockedDirectly, mkrLockedViaProxy } = await migration.check(); expect(mkrLockedDirectly.toNumber()).toBe(0); expect(mkrLockedViaProxy.toNumber()).toBe(0); @@ -42,32 +49,43 @@ describe('Chief Migration', () => { expect(mkrLockedViaProxy.toNumber()).toBe(0); }); - // TODO - test.skip('if the account has some MKR locked via proxy in old chief, return the amount', async () => { - // const oldChief = maker - // .service('smartContract') - // .getContractByName('OLD_CHIEF'); - // const voteProxyFactory = maker - // .service('smartContract') - // .getContractByName('VOTE_PROXY_FACTORY'); - // cold - // voteProxyFactory.initiateLink(hot); - // hot - // voteProxyFactory.approveLink(cold); - // back to cold - // const voteProxyAddress = migration._getVoteProxyAddress(cold); - // console.log('voteProxyAbi', voteProxyAbi); - // const voteProxy = maker - // .service('smartContract') - // .getContractByAddressAndAbi(voteProxyAddress, voteProxyAbi); - // await maker - // .service('token') - // .getToken(MKR) - // .approveUnlimited(voteProxyAddress); - // const LOCK_AMOUNT = MKR('5.123456789123456789'); - // await voteProxy.lock(LOCK_AMOUNT.toFixed('wei')); - // const { mkrLockedDirectly, mkrLockedViaProxy } = await migration.check(); - // expect(mkrLockedDirectly.toNumber()).toBe(0); - // expect(mkrLockedViaProxy.isEqual(LOCK_AMOUNT)).toBeTruthy(); + test('if the account has some MKR locked via proxy in old chief, return the amount', async () => { + const oldVoteProxyFactory = maker + .service('smartContract') + .getContractByName('OLD_VOTE_PROXY_FACTORY'); + + const coldAccount = maker.currentAccount(); + const hotAccount = TestAccountProvider.nextAccount(); + await maker.addAccount({ ...hotAccount, type: 'privateKey' }); + + // initiate from cold + maker.useAccount('default'); + await oldVoteProxyFactory.initiateLink(hotAccount.address); + + // switch to hot + maker.useAccount(hotAccount.address); + await oldVoteProxyFactory.approveLink(coldAccount.address); + + // and back to cold + maker.useAccount('default'); + const voteProxyAddress = await migration._getVoteProxyAddress( + coldAccount.address + ); + + const voteProxy = maker + .service('smartContract') + .getContractByAddressAndAbi(voteProxyAddress, voteProxyAbi); + + await maker + .service('token') + .getToken(MKR) + .approveUnlimited(voteProxyAddress); + + const LOCK_AMOUNT = MKR('5.123456789123456789'); + await voteProxy.lock(LOCK_AMOUNT.toFixed('wei')); + + const { mkrLockedDirectly, mkrLockedViaProxy } = await migration.check(); + expect(mkrLockedDirectly.toNumber()).toBe(0); + expect(mkrLockedViaProxy.isEqual(LOCK_AMOUNT)).toBeTruthy(); }); });