mirror of
https://github.com/cerc-io/watcher-ts
synced 2024-11-19 20:36:19 +00:00
Add test package (#164)
* Add test package * Add a separate command to perform an eth-call * Add snapshot test suite * Add eth-calls for UniswapV2 Pair, USDC, Compound, Dai contracts * Add args for Uniswap and USDC contracts * Add args for Compound and Dai contracts * Add getStorageAt calls to the test suite * Refactor code and add documentation * Loop over test slots for getStorageAt calls * Add support for individual calls * Use debug for logging
This commit is contained in:
parent
7238f614c0
commit
a5b3c7942d
5
packages/test/.eslintignore
Normal file
5
packages/test/.eslintignore
Normal file
@ -0,0 +1,5 @@
|
||||
# Don't lint node_modules.
|
||||
node_modules
|
||||
|
||||
# Don't lint build output.
|
||||
dist
|
23
packages/test/.eslintrc.json
Normal file
23
packages/test/.eslintrc.json
Normal file
@ -0,0 +1,23 @@
|
||||
{
|
||||
"env": {
|
||||
"browser": true,
|
||||
"es2021": true
|
||||
},
|
||||
"extends": [
|
||||
"eslint:recommended",
|
||||
"plugin:@typescript-eslint/recommended"
|
||||
],
|
||||
"overrides": [
|
||||
],
|
||||
"parser": "@typescript-eslint/parser",
|
||||
"parserOptions": {
|
||||
"ecmaVersion": "latest",
|
||||
"sourceType": "module"
|
||||
},
|
||||
"plugins": [
|
||||
"@typescript-eslint"
|
||||
],
|
||||
"rules": {
|
||||
"@typescript-eslint/no-explicit-any": "off"
|
||||
}
|
||||
}
|
4
packages/test/.mocharc.yml
Normal file
4
packages/test/.mocharc.yml
Normal file
@ -0,0 +1,4 @@
|
||||
timeout: '0' # No timeout since RPC calls may take longer
|
||||
bail: true
|
||||
exit: true
|
||||
require: 'ts-node/register'
|
76
packages/test/README.md
Normal file
76
packages/test/README.md
Normal file
@ -0,0 +1,76 @@
|
||||
# test
|
||||
|
||||
## Setup
|
||||
|
||||
* Run the following command to install required packages:
|
||||
|
||||
```bash
|
||||
yarn
|
||||
```
|
||||
|
||||
## Test Snapshot
|
||||
|
||||
* The snapshot test suite compares results for eth-calls and `getStorageAt` calls to the provided endpoints.
|
||||
|
||||
* Contracts considered:
|
||||
* UniswapV2 Factory
|
||||
* UniswapV2 Pair
|
||||
* USDC
|
||||
* Compound
|
||||
* Dai / Maker
|
||||
|
||||
* Edit the [config file](./environments/local.toml):
|
||||
|
||||
Eg:
|
||||
|
||||
```toml
|
||||
blockTag = "0xB5FFFF" # block tag to perform eth-call and getStorageAt call with (eg. block number in hex)
|
||||
|
||||
[endpoints]
|
||||
endpoint1 = "http://127.0.0.1:8545" # endpoint1 URL
|
||||
endpoint2 = "http://127.0.0.1:8082" # endpoint2 URL
|
||||
```
|
||||
|
||||
* Run the following command to run the snapshot test suite:
|
||||
|
||||
```bash
|
||||
yarn test:snapshot
|
||||
```
|
||||
|
||||
## Individual Calls
|
||||
|
||||
* Run the following to make an eth-call:
|
||||
|
||||
```bash
|
||||
yarn eth-call -e <endpoint> -c <contract> -a <abi> -m <method-name> --method-args [method-args] -b [block-tag]
|
||||
```
|
||||
|
||||
* `endpoint` (`e`): Endpoint to perform eth-call against
|
||||
* `contract` (`c`): Contract address
|
||||
* `abi` (`a`): Contract ABI path
|
||||
* `method-name` (`m`): Contract method to call
|
||||
* `method-args`: Contract method arguments
|
||||
* `block-tag` (`b`): Block tag to make eth-call with (block number (hex) / block hash)
|
||||
|
||||
Eg.
|
||||
|
||||
```bash
|
||||
yarn eth-call -e http://127.0.0.1:8545 -c 0x5C69bEe701ef814a2B6a3EDD4B1652CB9cc5aA6f -a abis/UniswapV2Factory.json -m allPairs --method-args 100 -b 0xB5FFFF
|
||||
```
|
||||
|
||||
* Run the following to make a `getStorageAt` call:
|
||||
|
||||
```bash
|
||||
yarn get-storage-at -e <endpoint> -c <contract> -s <slot> -b [block-tag]
|
||||
```
|
||||
|
||||
* `endpoint` (`e`): Endpoint to perform getStorageAt call against
|
||||
* `contract` (`c`): Contract address
|
||||
* `slot` (`s`): Storge slot
|
||||
* `block-tag` (`b`): Block tag to make getStorageAt call with (block number (hex) / block hash)
|
||||
|
||||
Eg.
|
||||
|
||||
```bash
|
||||
yarn get-storage-at -e http://127.0.0.1:8545 -c 0x5C69bEe701ef814a2B6a3EDD4B1652CB9cc5aA6f -s 0x1 -b 0xB5FFFF
|
||||
```
|
1
packages/test/abis/Comp.json
Normal file
1
packages/test/abis/Comp.json
Normal file
File diff suppressed because one or more lines are too long
1
packages/test/abis/Dai.json
Normal file
1
packages/test/abis/Dai.json
Normal file
File diff suppressed because one or more lines are too long
1
packages/test/abis/FiatTokenV2_1.json
Normal file
1
packages/test/abis/FiatTokenV2_1.json
Normal file
File diff suppressed because one or more lines are too long
1
packages/test/abis/UniswapV2Factory.json
Normal file
1
packages/test/abis/UniswapV2Factory.json
Normal file
@ -0,0 +1 @@
|
||||
[{"inputs":[{"internalType":"address","name":"_feeToSetter","type":"address"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"token0","type":"address"},{"indexed":true,"internalType":"address","name":"token1","type":"address"},{"indexed":false,"internalType":"address","name":"pair","type":"address"},{"indexed":false,"internalType":"uint256","name":"","type":"uint256"}],"name":"PairCreated","type":"event"},{"constant":true,"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"allPairs","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"allPairsLength","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"tokenA","type":"address"},{"internalType":"address","name":"tokenB","type":"address"}],"name":"createPair","outputs":[{"internalType":"address","name":"pair","type":"address"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"feeTo","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"feeToSetter","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"internalType":"address","name":"","type":"address"},{"internalType":"address","name":"","type":"address"}],"name":"getPair","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"_feeTo","type":"address"}],"name":"setFeeTo","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"_feeToSetter","type":"address"}],"name":"setFeeToSetter","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"}]
|
1
packages/test/abis/UniswapV2Pair.json
Normal file
1
packages/test/abis/UniswapV2Pair.json
Normal file
File diff suppressed because one or more lines are too long
5
packages/test/environments/local.toml
Normal file
5
packages/test/environments/local.toml
Normal file
@ -0,0 +1,5 @@
|
||||
blockTag = "" # block tag to perform eth-call and getStorageAt call with (eg. block number in hex)
|
||||
|
||||
[endpoints]
|
||||
endpoint1 = "" # endpoint1 URL
|
||||
endpoint2 = "" # endpoint2 URL
|
32
packages/test/package.json
Normal file
32
packages/test/package.json
Normal file
@ -0,0 +1,32 @@
|
||||
{
|
||||
"name": "@vulcanize/test",
|
||||
"version": "0.1.0",
|
||||
"main": "dist/index.js",
|
||||
"license": "AGPL-3.0",
|
||||
"scripts": {
|
||||
"lint": "eslint .",
|
||||
"build": "tsc",
|
||||
"eth-call": "DEBUG=vulcanize:* ts-node src/eth-call.ts",
|
||||
"get-storage-at": "DEBUG=vulcanize:* ts-node src/get-storage-at.ts",
|
||||
"test:snapshot": "DEBUG=vulcanize:* mocha src/snapshot.test.ts"
|
||||
},
|
||||
"dependencies": {
|
||||
"chai": "^4.3.4",
|
||||
"ethers": "^5.4.4",
|
||||
"fs-extra": "^10.0.0",
|
||||
"lodash": "^4.17.21",
|
||||
"mocha": "^8.4.0",
|
||||
"toml": "^3.0.0",
|
||||
"debug": "^4.3.1",
|
||||
"yargs": "^17.0.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/chai": "^4.2.19",
|
||||
"@types/mocha": "^8.2.2",
|
||||
"@typescript-eslint/eslint-plugin": "^4.25.0",
|
||||
"@typescript-eslint/parser": "^4.25.0",
|
||||
"eslint": "^7.27.0",
|
||||
"ts-node": "^10.0.0",
|
||||
"typescript": "^4.3.2"
|
||||
}
|
||||
}
|
46
packages/test/src/common.ts
Normal file
46
packages/test/src/common.ts
Normal file
@ -0,0 +1,46 @@
|
||||
//
|
||||
// Copyright 2022 Vulcanize, Inc.
|
||||
//
|
||||
|
||||
import fs from 'fs-extra';
|
||||
import path from 'path';
|
||||
import assert from 'assert';
|
||||
import toml from 'toml';
|
||||
|
||||
export interface Config {
|
||||
endpoint1URL: string,
|
||||
endpoint2URL: string,
|
||||
blockTag: string
|
||||
}
|
||||
|
||||
export const getConfig = async (configFile: string): Promise<Config> => {
|
||||
const configFilePath = path.resolve(configFile);
|
||||
const fileExists = await fs.pathExists(configFilePath);
|
||||
if (!fileExists) {
|
||||
throw new Error(`Config file not found: ${configFilePath}`);
|
||||
}
|
||||
|
||||
const configString = await fs.readFile(configFilePath, 'utf8');
|
||||
const config = toml.parse(configString);
|
||||
|
||||
const { endpoints: endpointConfig, blockTag } = config;
|
||||
assert(endpointConfig, 'Missing endpoints config');
|
||||
|
||||
const {endpoint1: endpoint1URL, endpoint2: endpoint2URL} = endpointConfig;
|
||||
assert(endpoint1URL, 'Missing endpoint1 URL');
|
||||
assert(endpoint2URL, 'Missing endpoint2 URL');
|
||||
|
||||
assert(blockTag);
|
||||
|
||||
return {
|
||||
endpoint1URL,
|
||||
endpoint2URL,
|
||||
blockTag
|
||||
};
|
||||
}
|
||||
|
||||
export const readAbi = (abiPath: string): any => {
|
||||
const fullAbiPath = path.resolve(abiPath);
|
||||
|
||||
return JSON.parse(fs.readFileSync(fullAbiPath).toString());
|
||||
}
|
70
packages/test/src/eth-call.ts
Normal file
70
packages/test/src/eth-call.ts
Normal file
@ -0,0 +1,70 @@
|
||||
//
|
||||
// Copyright 2022 Vulcanize, Inc.
|
||||
//
|
||||
|
||||
import yargs from 'yargs';
|
||||
import { ethers, providers } from 'ethers';
|
||||
import debug from 'debug';
|
||||
|
||||
import { readAbi } from './common';
|
||||
|
||||
const log = debug('vulcanize:test');
|
||||
|
||||
const main = async (): Promise<void> => {
|
||||
const argv = await yargs.parserConfiguration({
|
||||
'parse-numbers': false
|
||||
}).options({
|
||||
endpoint: {
|
||||
alias: 'e',
|
||||
demandOption: true,
|
||||
describe: 'Endpoint to perform eth-call against',
|
||||
type: 'string'
|
||||
},
|
||||
contract: {
|
||||
alias: 'c',
|
||||
demandOption: true,
|
||||
describe: 'Contract address',
|
||||
type: 'string'
|
||||
},
|
||||
abi: {
|
||||
alias: 'a',
|
||||
demandOption: true,
|
||||
describe: 'Contract ABI path',
|
||||
type: 'string'
|
||||
},
|
||||
methodName: {
|
||||
alias: 'm',
|
||||
demandOption: true,
|
||||
describe: 'Contract method to call',
|
||||
type: 'string'
|
||||
},
|
||||
methodArgs: {
|
||||
describe: 'Contract method arguments',
|
||||
type: 'array'
|
||||
},
|
||||
blockTag: {
|
||||
alias: 'b',
|
||||
describe: 'Block tag to make eth-call with (block number (hex) / block hash)',
|
||||
type: 'string'
|
||||
}
|
||||
}).argv;
|
||||
|
||||
const abi = readAbi(argv.abi);
|
||||
const provider = new providers.JsonRpcProvider(argv.endpoint);
|
||||
const contract = new ethers.Contract(argv.contract, abi, provider);
|
||||
|
||||
let args: (string | number)[] = []
|
||||
if(argv.methodArgs !== undefined) {
|
||||
args = argv.methodArgs
|
||||
}
|
||||
|
||||
log(`Making an eth-call (${argv.methodName}) to endpoint ${argv.endpoint}`);
|
||||
const result = await contract[argv.methodName](...args, {blockTag: argv.blockTag});
|
||||
|
||||
log("Result:");
|
||||
log(result);
|
||||
}
|
||||
|
||||
main().catch(err => {
|
||||
log(err);
|
||||
});
|
53
packages/test/src/get-storage-at.ts
Normal file
53
packages/test/src/get-storage-at.ts
Normal file
@ -0,0 +1,53 @@
|
||||
//
|
||||
// Copyright 2022 Vulcanize, Inc.
|
||||
//
|
||||
|
||||
import yargs from 'yargs';
|
||||
import { ethers, providers } from 'ethers';
|
||||
import debug from 'debug';
|
||||
|
||||
import { readAbi } from './common';
|
||||
|
||||
const log = debug('vulcanize:test');
|
||||
|
||||
const main = async (): Promise<void> => {
|
||||
const argv = await yargs.parserConfiguration({
|
||||
'parse-numbers': false
|
||||
}).options({
|
||||
endpoint: {
|
||||
alias: 'e',
|
||||
demandOption: true,
|
||||
describe: 'Endpoint to perform getStorageAt against',
|
||||
type: 'string'
|
||||
},
|
||||
contract: {
|
||||
alias: 'c',
|
||||
demandOption: true,
|
||||
describe: 'Contract address',
|
||||
type: 'string'
|
||||
},
|
||||
slot: {
|
||||
alias: 's',
|
||||
demandOption: true,
|
||||
describe: 'Storge slot',
|
||||
type: 'string'
|
||||
},
|
||||
blockTag: {
|
||||
alias: 'b',
|
||||
describe: 'Block tag to make eth-call with (block number (hex) / block hash)',
|
||||
type: 'string'
|
||||
},
|
||||
}).argv;
|
||||
|
||||
const provider = new providers.JsonRpcProvider(argv.endpoint);
|
||||
|
||||
log(`Making a getStorageAt call for slot ${argv.slot} to endpoint ${argv.endpoint}`);
|
||||
const result = await provider.getStorageAt(argv.contract, argv.slot, argv.blockTag);
|
||||
|
||||
log("Result:");
|
||||
log(result);
|
||||
}
|
||||
|
||||
main().catch(err => {
|
||||
log(err);
|
||||
});
|
741
packages/test/src/snapshot.test.ts
Normal file
741
packages/test/src/snapshot.test.ts
Normal file
@ -0,0 +1,741 @@
|
||||
//
|
||||
// Copyright 2022 Vulcanize, Inc.
|
||||
//
|
||||
|
||||
import { expect } from 'chai';
|
||||
import { providers, Contract } from 'ethers';
|
||||
import 'mocha';
|
||||
|
||||
import { Config, getConfig } from './common';
|
||||
import {
|
||||
uniswapV2FactoryABI,
|
||||
uniswapV2FactoryAddress,
|
||||
uniswapV2PairABI,
|
||||
uniswapV2PairAddress,
|
||||
usdcABI,
|
||||
usdcAddress,
|
||||
compoundABI,
|
||||
compoundAddress,
|
||||
daiABI,
|
||||
daiAddress
|
||||
} from './test-data';
|
||||
|
||||
const DEFAULT_CONFIG_FILE = './environments/local.toml';
|
||||
|
||||
describe('snapshot-test', () => {
|
||||
let config: Config;
|
||||
|
||||
let provider1: providers.JsonRpcProvider;
|
||||
let provider2: providers.JsonRpcProvider;
|
||||
|
||||
before("initialize providers", async () => {
|
||||
config = await getConfig(DEFAULT_CONFIG_FILE);
|
||||
|
||||
provider1 = new providers.JsonRpcProvider(config.endpoint1URL);
|
||||
provider2 = new providers.JsonRpcProvider(config.endpoint2URL);
|
||||
});
|
||||
|
||||
// Compare eth-call results
|
||||
describe('match results for eth-calls', async () => {
|
||||
let contract1: Contract;
|
||||
let contract2: Contract;
|
||||
|
||||
describe('match results for eth-calls to UniswapV2 Factory', async () => {
|
||||
before("initialize contracts", async () => {
|
||||
contract1 = new Contract(uniswapV2FactoryAddress, uniswapV2FactoryABI, provider1);
|
||||
contract2 = new Contract(uniswapV2FactoryAddress, uniswapV2FactoryABI, provider2);
|
||||
});
|
||||
|
||||
it('should match results for allPairs', async () => {
|
||||
const args = [100]
|
||||
|
||||
const result1 = await contract1.allPairs(...args, {blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.allPairs(...args, {blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for allPairsLength', async () => {
|
||||
const result1 = await contract1.allPairsLength({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.allPairsLength({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for feeTo', async () => {
|
||||
const result1 = await contract1.feeTo({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.feeTo({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for feeToSetter', async () => {
|
||||
const result1 = await contract1.feeToSetter({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.feeToSetter({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for getPair', async () => {
|
||||
const args = ["0x8e870d67f660d95d5be530380d0ec0bd388289e1", "0xa0b86991c6218b36c1d19d4a2e9eb0ce3606eb48"]
|
||||
|
||||
const result1 = await contract1.getPair(...args, {blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.getPair(...args, {blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
});
|
||||
|
||||
describe('match results for eth-calls to UniswapV2 Pair', async () => {
|
||||
before("initialize contracts", async () => {
|
||||
contract1 = new Contract(uniswapV2PairAddress, uniswapV2PairABI, provider1);
|
||||
contract2 = new Contract(uniswapV2PairAddress, uniswapV2PairABI, provider2);
|
||||
});
|
||||
|
||||
it('should match results for DOMAIN_SEPARATOR', async () => {
|
||||
const result1 = await contract1.DOMAIN_SEPARATOR({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.DOMAIN_SEPARATOR({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for MINIMUM_LIQUIDITY', async () => {
|
||||
const result1 = await contract1.MINIMUM_LIQUIDITY({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.MINIMUM_LIQUIDITY({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for PERMIT_TYPEHASH', async () => {
|
||||
const result1 = await contract1.PERMIT_TYPEHASH({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.PERMIT_TYPEHASH({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for allowance', async () => {
|
||||
const args = ["0x9c77233bbd235a3ed219daa051e0a3de5ce03c3e", "0x7a250d5630B4cF539739dF2C5dAcb4c659F2488D"]
|
||||
|
||||
const result1 = await contract1.allowance(...args, {blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.allowance(...args, {blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for balanceOf', async () => {
|
||||
const args = ["0x052ba6f57c9184a89c34196ee4f3adacaeb58e8d"]
|
||||
|
||||
const result1 = await contract1.balanceOf(...args, {blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.balanceOf(...args, {blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for decimals', async () => {
|
||||
const result1 = await contract1.decimals({blockTag: config.blockTag});
|
||||
const result2 = await contract2.decimals({blockTag: config.blockTag});
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for factory', async () => {
|
||||
const result1 = await contract1.factory({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.factory({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for getReserves', async () => {
|
||||
const result1 = await contract1.getReserves({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.getReserves({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for kLast', async () => {
|
||||
const result1 = await contract1.kLast({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.kLast({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for name', async () => {
|
||||
const result1 = await contract1.name({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.name({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for nonces', async () => {
|
||||
const args = ["0xE0e8C1D735698060477e79a8e4C20276Fc2Ec7A7"]
|
||||
|
||||
const result1 = await contract1.nonces(...args, {blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.nonces(...args, {blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for price0CumulativeLast', async () => {
|
||||
const result1 = await contract1.price0CumulativeLast({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.price0CumulativeLast({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for price1CumulativeLast', async () => {
|
||||
const result1 = await contract1.price1CumulativeLast({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.price1CumulativeLast({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for symbol', async () => {
|
||||
const result1 = await contract1.symbol({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.symbol({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for token0', async () => {
|
||||
const result1 = await contract1.token0({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.token0({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for token1', async () => {
|
||||
const result1 = await contract1.token1({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.token1({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for totalSupply', async () => {
|
||||
const result1 = await contract1.totalSupply({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.totalSupply({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
});
|
||||
|
||||
describe('match results for eth-calls to USDC', async () => {
|
||||
before("initialize contracts", async () => {
|
||||
contract1 = new Contract(usdcAddress, usdcABI, provider1);
|
||||
contract2 = new Contract(usdcAddress, usdcABI, provider2);
|
||||
});
|
||||
|
||||
it('should match results for CANCEL_AUTHORIZATION_TYPEHASH', async () => {
|
||||
const result1 = await contract1.CANCEL_AUTHORIZATION_TYPEHASH({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.CANCEL_AUTHORIZATION_TYPEHASH({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for DOMAIN_SEPARATOR', async () => {
|
||||
const result1 = await contract1.DOMAIN_SEPARATOR({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.DOMAIN_SEPARATOR({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for PERMIT_TYPEHASH', async () => {
|
||||
const result1 = await contract1.PERMIT_TYPEHASH({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.PERMIT_TYPEHASH({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for TRANSFER_WITH_AUTHORIZATION_TYPEHASH', async () => {
|
||||
const result1 = await contract1.TRANSFER_WITH_AUTHORIZATION_TYPEHASH({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.TRANSFER_WITH_AUTHORIZATION_TYPEHASH({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for allowance', async () => {
|
||||
const args = ["0xa064c5d674b0de5ac8d1d1ade3fba7569525ac44", "0x7a250d5630B4cF539739dF2C5dAcb4c659F2488D"];
|
||||
|
||||
const result1 = await contract1.allowance(...args, {blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.allowance(...args, {blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for balanceOf', async () => {
|
||||
const args = ["0x95ba4cf87d6723ad9c0db21737d862be80e93911"]
|
||||
|
||||
const result1 = await contract1.balanceOf(...args, {blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.balanceOf(...args, {blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for blacklister', async () => {
|
||||
const result1 = await contract1.blacklister({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.blacklister({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for currency', async () => {
|
||||
const result1 = await contract1.currency({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.currency({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for decimals', async () => {
|
||||
const result1 = await contract1.decimals({blockTag: config.blockTag});
|
||||
const result2 = await contract2.decimals({blockTag: config.blockTag});
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for masterMinter', async () => {
|
||||
const result1 = await contract1.masterMinter({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.masterMinter({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for name', async () => {
|
||||
const result1 = await contract1.name({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.name({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for owner', async () => {
|
||||
const result1 = await contract1.owner({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.owner({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for paused', async () => {
|
||||
const result1 = await contract1.paused({blockTag: config.blockTag});
|
||||
const result2 = await contract2.paused({blockTag: config.blockTag});
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for pauser', async () => {
|
||||
const result1 = await contract1.pauser({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.pauser({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for rescuer', async () => {
|
||||
const result1 = await contract1.rescuer({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.rescuer({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for symbol', async () => {
|
||||
const result1 = await contract1.symbol({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.symbol({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for totalSupply', async () => {
|
||||
const result1 = await contract1.totalSupply({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.totalSupply({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
});
|
||||
|
||||
describe('match results for eth-calls to Compound', async () => {
|
||||
before("initialize contracts", async () => {
|
||||
contract1 = new Contract(compoundAddress, compoundABI, provider1);
|
||||
contract2 = new Contract(compoundAddress, compoundABI, provider2);
|
||||
});
|
||||
|
||||
it('should match results for DELEGATION_TYPEHASH', async () => {
|
||||
const result1 = await contract1.DELEGATION_TYPEHASH({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.DELEGATION_TYPEHASH({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for DOMAIN_TYPEHASH', async () => {
|
||||
const result1 = await contract1.DOMAIN_TYPEHASH({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.DOMAIN_TYPEHASH({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for allowance', async () => {
|
||||
const args = ["0xa5ffc832b23606f82005688d734c099dfabd5313", "0x70e36f6bf80a52b3b46b3af8e106cc0ed743e8e4"]
|
||||
|
||||
const result1 = await contract1.allowance(...args, {blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.allowance(...args, {blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for balanceOf', async () => {
|
||||
const args = ["0x2FAF487A4414Fe77e2327F0bf4AE2a264a776AD2"]
|
||||
|
||||
const result1 = await contract1.balanceOf(...args, {blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.balanceOf(...args, {blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for decimals', async () => {
|
||||
const result1 = await contract1.decimals({blockTag: config.blockTag});
|
||||
const result2 = await contract2.decimals({blockTag: config.blockTag});
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for delegates', async () => {
|
||||
const args = ["0xdaaf40dae51ad67f1eeb8c8bded831f7ab150830"]
|
||||
|
||||
const result1 = await contract1.delegates(...args, {blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.delegates(...args, {blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for name', async () => {
|
||||
const result1 = await contract1.name({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.name({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for numCheckpoints', async () => {
|
||||
const args = ["0xc00e94Cb662C3520282E6f5717214004A7f26888"]
|
||||
|
||||
const result1 = await contract1.numCheckpoints(...args, {blockTag: config.blockTag});
|
||||
const result2 = await contract2.numCheckpoints(...args, {blockTag: config.blockTag});
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for symbol', async () => {
|
||||
const result1 = await contract1.symbol({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.symbol({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for totalSupply', async () => {
|
||||
const result1 = await contract1.totalSupply({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.totalSupply({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
});
|
||||
|
||||
describe('match results for eth-calls to Dai', async () => {
|
||||
before("initialize contracts", async () => {
|
||||
contract1 = new Contract(daiAddress, daiABI, provider1);
|
||||
contract2 = new Contract(daiAddress, daiABI, provider2);
|
||||
});
|
||||
|
||||
it('should match results for DOMAIN_SEPARATOR', async () => {
|
||||
const result1 = await contract1.DOMAIN_SEPARATOR({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.DOMAIN_SEPARATOR({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for PERMIT_TYPEHASH', async () => {
|
||||
const result1 = await contract1.PERMIT_TYPEHASH({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.PERMIT_TYPEHASH({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for allowance', async () => {
|
||||
const args = ["0x74ae284dd6044db63dc268f52131571a3b80ad33", "0xa91902085405CE0F648a7Eb82045Aefc1B7BAC01"]
|
||||
|
||||
const result1 = await contract1.allowance(...args, {blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.allowance(...args, {blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for balanceOf', async () => {
|
||||
const args = ["0xab78b4c4a28f6e449e0bf2d6eb4f4f0316343d2a"]
|
||||
|
||||
const result1 = await contract1.balanceOf(...args, {blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.balanceOf(...args, {blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for decimals', async () => {
|
||||
const result1 = await contract1.decimals({blockTag: config.blockTag});
|
||||
const result2 = await contract2.decimals({blockTag: config.blockTag});
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for name', async () => {
|
||||
const result1 = await contract1.name({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.name({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for symbol', async () => {
|
||||
const result1 = await contract1.symbol({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.symbol({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for totalSupply', async () => {
|
||||
const result1 = await contract1.totalSupply({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.totalSupply({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
|
||||
it('should match results for version', async () => {
|
||||
const result1 = await contract1.version({blockTag: config.blockTag});
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await contract2.version({blockTag: config.blockTag});
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
// Compare getStorageAt results
|
||||
describe('match results for getStorageAt calls', async () => {
|
||||
const testSlots = ['0x0', '0x1', '0x2', '0x3', '0x4', '0x5', '0x6', '0x7', '0x8', '0x9', '0xa', '0xb', '0xc', '0xd', '0xe', '0xf']
|
||||
|
||||
describe('match results for getStorageAt for UniswapV2 Factory', async () => {
|
||||
testSlots.forEach((testSlot: string) => {
|
||||
it(`should match results for slot ${testSlot}`, async () => {
|
||||
const result1 = await provider1.getStorageAt(uniswapV2FactoryAddress, testSlot, config.blockTag)
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await provider2.getStorageAt(uniswapV2FactoryAddress, testSlot, config.blockTag)
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
describe('match results for getStorageAt for UniswapV2 Pair', async () => {
|
||||
testSlots.forEach((testSlot: string) => {
|
||||
it(`should match results for slot ${testSlot}`, async () => {
|
||||
const result1 = await provider1.getStorageAt(uniswapV2PairAddress, testSlot, config.blockTag)
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await provider2.getStorageAt(uniswapV2PairAddress, testSlot, config.blockTag)
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
describe('match results for getStorageAt for USDC', async () => {
|
||||
testSlots.forEach((testSlot: string) => {
|
||||
it(`should match results for slot ${testSlot}`, async () => {
|
||||
const result1 = await provider1.getStorageAt(usdcAddress, testSlot, config.blockTag)
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await provider2.getStorageAt(usdcAddress, testSlot, config.blockTag)
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
describe('match results for getStorageAt for Compound', async () => {
|
||||
testSlots.forEach((testSlot: string) => {
|
||||
it(`should match results for slot ${testSlot}`, async () => {
|
||||
const result1 = await provider1.getStorageAt(compoundAddress, testSlot, config.blockTag)
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await provider2.getStorageAt(compoundAddress, testSlot, config.blockTag)
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
describe('match results for getStorageAt for Dai', async () => {
|
||||
testSlots.forEach((testSlot: string) => {
|
||||
it(`should match results for slot ${testSlot}`, async () => {
|
||||
const result1 = await provider1.getStorageAt(daiAddress, testSlot, config.blockTag)
|
||||
expect(result1).to.not.be.empty;
|
||||
|
||||
const result2 = await provider2.getStorageAt(daiAddress, testSlot, config.blockTag)
|
||||
expect(result2).to.not.be.empty;
|
||||
|
||||
expect(result1).to.deep.equal(result2);
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
25
packages/test/src/test-data.ts
Normal file
25
packages/test/src/test-data.ts
Normal file
@ -0,0 +1,25 @@
|
||||
//
|
||||
// Copyright 2022 Vulcanize, Inc.
|
||||
//
|
||||
|
||||
import { readAbi } from "./common";
|
||||
|
||||
// UniswapV2 Factory contract
|
||||
export const uniswapV2FactoryAddress = "0x5C69bEe701ef814a2B6a3EDD4B1652CB9cc5aA6f";
|
||||
export const uniswapV2FactoryABI = readAbi("abis/UniswapV2Factory.json");
|
||||
|
||||
// UniswapV2 Pair contract
|
||||
export const uniswapV2PairAddress = "0xB4e16d0168e52d35CaCD2c6185b44281Ec28C9Dc";
|
||||
export const uniswapV2PairABI = readAbi("abis/UniswapV2Pair.json");
|
||||
|
||||
// USDC contract
|
||||
export const usdcAddress = "0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48";
|
||||
export const usdcABI = readAbi("abis/FiatTokenV2_1.json");
|
||||
|
||||
// Compound contract
|
||||
export const compoundAddress = "0xc00e94Cb662C3520282E6f5717214004A7f26888";
|
||||
export const compoundABI = readAbi("abis/Comp.json");
|
||||
|
||||
// Dai/Maker contract
|
||||
export const daiAddress = "0x6B175474E89094C44Da98b954EedeAC495271d0F";
|
||||
export const daiABI = readAbi("abis/Dai.json");
|
104
packages/test/tsconfig.json
Normal file
104
packages/test/tsconfig.json
Normal file
@ -0,0 +1,104 @@
|
||||
{
|
||||
"compilerOptions": {
|
||||
/* Visit https://aka.ms/tsconfig to read more about this file */
|
||||
|
||||
/* Projects */
|
||||
// "incremental": true, /* Save .tsbuildinfo files to allow for incremental compilation of projects. */
|
||||
// "composite": true, /* Enable constraints that allow a TypeScript project to be used with project references. */
|
||||
// "tsBuildInfoFile": "./.tsbuildinfo", /* Specify the path to .tsbuildinfo incremental compilation file. */
|
||||
// "disableSourceOfProjectReferenceRedirect": true, /* Disable preferring source files instead of declaration files when referencing composite projects. */
|
||||
// "disableSolutionSearching": true, /* Opt a project out of multi-project reference checking when editing. */
|
||||
// "disableReferencedProjectLoad": true, /* Reduce the number of projects loaded automatically by TypeScript. */
|
||||
|
||||
/* Language and Environment */
|
||||
"target": "es5", /* Set the JavaScript language version for emitted JavaScript and include compatible library declarations. */
|
||||
// "lib": [], /* Specify a set of bundled library declaration files that describe the target runtime environment. */
|
||||
// "jsx": "preserve", /* Specify what JSX code is generated. */
|
||||
// "experimentalDecorators": true, /* Enable experimental support for TC39 stage 2 draft decorators. */
|
||||
// "emitDecoratorMetadata": true, /* Emit design-type metadata for decorated declarations in source files. */
|
||||
// "jsxFactory": "", /* Specify the JSX factory function used when targeting React JSX emit, e.g. 'React.createElement' or 'h'. */
|
||||
// "jsxFragmentFactory": "", /* Specify the JSX Fragment reference used for fragments when targeting React JSX emit e.g. 'React.Fragment' or 'Fragment'. */
|
||||
// "jsxImportSource": "", /* Specify module specifier used to import the JSX factory functions when using 'jsx: react-jsx*'. */
|
||||
// "reactNamespace": "", /* Specify the object invoked for 'createElement'. This only applies when targeting 'react' JSX emit. */
|
||||
// "noLib": true, /* Disable including any library files, including the default lib.d.ts. */
|
||||
// "useDefineForClassFields": true, /* Emit ECMAScript-standard-compliant class fields. */
|
||||
// "moduleDetection": "auto", /* Control what method is used to detect module-format JS files. */
|
||||
|
||||
/* Modules */
|
||||
"module": "commonjs", /* Specify what module code is generated. */
|
||||
// "rootDir": "./", /* Specify the root folder within your source files. */
|
||||
// "moduleResolution": "node", /* Specify how TypeScript looks up a file from a given module specifier. */
|
||||
// "baseUrl": "./", /* Specify the base directory to resolve non-relative module names. */
|
||||
// "paths": {}, /* Specify a set of entries that re-map imports to additional lookup locations. */
|
||||
// "rootDirs": [], /* Allow multiple folders to be treated as one when resolving modules. */
|
||||
// "typeRoots": [], /* Specify multiple folders that act like './node_modules/@types'. */
|
||||
// "types": [], /* Specify type package names to be included without being referenced in a source file. */
|
||||
// "allowUmdGlobalAccess": true, /* Allow accessing UMD globals from modules. */
|
||||
// "moduleSuffixes": [], /* List of file name suffixes to search when resolving a module. */
|
||||
// "resolveJsonModule": true, /* Enable importing .json files. */
|
||||
// "noResolve": true, /* Disallow 'import's, 'require's or '<reference>'s from expanding the number of files TypeScript should add to a project. */
|
||||
|
||||
/* JavaScript Support */
|
||||
// "allowJs": true, /* Allow JavaScript files to be a part of your program. Use the 'checkJS' option to get errors from these files. */
|
||||
// "checkJs": true, /* Enable error reporting in type-checked JavaScript files. */
|
||||
// "maxNodeModuleJsDepth": 1, /* Specify the maximum folder depth used for checking JavaScript files from 'node_modules'. Only applicable with 'allowJs'. */
|
||||
|
||||
/* Emit */
|
||||
// "declaration": true, /* Generate .d.ts files from TypeScript and JavaScript files in your project. */
|
||||
// "declarationMap": true, /* Create sourcemaps for d.ts files. */
|
||||
// "emitDeclarationOnly": true, /* Only output d.ts files and not JavaScript files. */
|
||||
// "sourceMap": true, /* Create source map files for emitted JavaScript files. */
|
||||
// "outFile": "./", /* Specify a file that bundles all outputs into one JavaScript file. If 'declaration' is true, also designates a file that bundles all .d.ts output. */
|
||||
"outDir": "dist", /* Specify an output folder for all emitted files. */
|
||||
// "removeComments": true, /* Disable emitting comments. */
|
||||
// "noEmit": true, /* Disable emitting files from a compilation. */
|
||||
// "importHelpers": true, /* Allow importing helper functions from tslib once per project, instead of including them per-file. */
|
||||
// "importsNotUsedAsValues": "remove", /* Specify emit/checking behavior for imports that are only used for types. */
|
||||
// "downlevelIteration": true, /* Emit more compliant, but verbose and less performant JavaScript for iteration. */
|
||||
// "sourceRoot": "", /* Specify the root path for debuggers to find the reference source code. */
|
||||
// "mapRoot": "", /* Specify the location where debugger should locate map files instead of generated locations. */
|
||||
// "inlineSourceMap": true, /* Include sourcemap files inside the emitted JavaScript. */
|
||||
// "inlineSources": true, /* Include source code in the sourcemaps inside the emitted JavaScript. */
|
||||
// "emitBOM": true, /* Emit a UTF-8 Byte Order Mark (BOM) in the beginning of output files. */
|
||||
// "newLine": "crlf", /* Set the newline character for emitting files. */
|
||||
// "stripInternal": true, /* Disable emitting declarations that have '@internal' in their JSDoc comments. */
|
||||
// "noEmitHelpers": true, /* Disable generating custom helper functions like '__extends' in compiled output. */
|
||||
// "noEmitOnError": true, /* Disable emitting files if any type checking errors are reported. */
|
||||
// "preserveConstEnums": true, /* Disable erasing 'const enum' declarations in generated code. */
|
||||
// "declarationDir": "./", /* Specify the output directory for generated declaration files. */
|
||||
// "preserveValueImports": true, /* Preserve unused imported values in the JavaScript output that would otherwise be removed. */
|
||||
|
||||
/* Interop Constraints */
|
||||
// "isolatedModules": true, /* Ensure that each file can be safely transpiled without relying on other imports. */
|
||||
// "allowSyntheticDefaultImports": true, /* Allow 'import x from y' when a module doesn't have a default export. */
|
||||
"esModuleInterop": true, /* Emit additional JavaScript to ease support for importing CommonJS modules. This enables 'allowSyntheticDefaultImports' for type compatibility. */
|
||||
// "preserveSymlinks": true, /* Disable resolving symlinks to their realpath. This correlates to the same flag in node. */
|
||||
"forceConsistentCasingInFileNames": true, /* Ensure that casing is correct in imports. */
|
||||
|
||||
/* Type Checking */
|
||||
"strict": true, /* Enable all strict type-checking options. */
|
||||
// "noImplicitAny": true, /* Enable error reporting for expressions and declarations with an implied 'any' type. */
|
||||
// "strictNullChecks": true, /* When type checking, take into account 'null' and 'undefined'. */
|
||||
// "strictFunctionTypes": true, /* When assigning functions, check to ensure parameters and the return values are subtype-compatible. */
|
||||
// "strictBindCallApply": true, /* Check that the arguments for 'bind', 'call', and 'apply' methods match the original function. */
|
||||
// "strictPropertyInitialization": true, /* Check for class properties that are declared but not set in the constructor. */
|
||||
// "noImplicitThis": true, /* Enable error reporting when 'this' is given the type 'any'. */
|
||||
// "useUnknownInCatchVariables": true, /* Default catch clause variables as 'unknown' instead of 'any'. */
|
||||
// "alwaysStrict": true, /* Ensure 'use strict' is always emitted. */
|
||||
// "noUnusedLocals": true, /* Enable error reporting when local variables aren't read. */
|
||||
// "noUnusedParameters": true, /* Raise an error when a function parameter isn't read. */
|
||||
// "exactOptionalPropertyTypes": true, /* Interpret optional property types as written, rather than adding 'undefined'. */
|
||||
// "noImplicitReturns": true, /* Enable error reporting for codepaths that do not explicitly return in a function. */
|
||||
// "noFallthroughCasesInSwitch": true, /* Enable error reporting for fallthrough cases in switch statements. */
|
||||
// "noUncheckedIndexedAccess": true, /* Add 'undefined' to a type when accessed using an index. */
|
||||
// "noImplicitOverride": true, /* Ensure overriding members in derived classes are marked with an override modifier. */
|
||||
// "noPropertyAccessFromIndexSignature": true, /* Enforces using indexed accessors for keys declared using an indexed type. */
|
||||
// "allowUnusedLabels": true, /* Disable error reporting for unused labels. */
|
||||
// "allowUnreachableCode": true, /* Disable error reporting for unreachable code. */
|
||||
|
||||
/* Completeness */
|
||||
// "skipDefaultLibCheck": true, /* Skip type checking .d.ts files that are included with TypeScript. */
|
||||
"skipLibCheck": true /* Skip type checking all .d.ts files. */
|
||||
},
|
||||
"exclude": ["dist", "artifacts"]
|
||||
}
|
Loading…
Reference in New Issue
Block a user