mirror of
https://github.com/cerc-io/watcher-ts
synced 2024-11-19 20:36:19 +00:00
Assert proof data when running against GQL endpoint (#86)
* Assert proof data for intial test cases of value type variables. * Assert proof data for value type variables integers and bytes. * Assert proof for dynamic byte arrays and strings. * Assert proof for fixed array types. * Assert proof for dynamic array types. * Assert proofs for nested arrays. * Assert proof for struct type variables. * Assert proof for mapping type variables. Co-authored-by: nikugogoi <95nikass@gmail.com>
This commit is contained in:
parent
2adc5e9c34
commit
fc30290685
File diff suppressed because it is too large
Load Diff
@ -298,7 +298,7 @@ const getStructureValue = async (getStorageAt: GetStorageAt, blockHash: string,
|
|||||||
return members.reduce((acc, member, index) => {
|
return members.reduce((acc, member, index) => {
|
||||||
acc.value[member.label] = results[index].value;
|
acc.value[member.label] = results[index].value;
|
||||||
const proofData = JSON.parse(acc.proof.data);
|
const proofData = JSON.parse(acc.proof.data);
|
||||||
proofData[member.label] = results[index].proof;
|
proofData[member.label] = JSON.parse(results[index].proof.data);
|
||||||
acc.proof.data = JSON.stringify(proofData);
|
acc.proof.data = JSON.stringify(proofData);
|
||||||
return acc;
|
return acc;
|
||||||
}, initialValue);
|
}, initialValue);
|
||||||
@ -336,6 +336,7 @@ const getInplaceValue = async (getStorageAt: GetStorageAt, blockHash: string, ad
|
|||||||
const getBytesValue = async (getStorageAt: GetStorageAt, blockHash: string, address: string, slot: string) => {
|
const getBytesValue = async (getStorageAt: GetStorageAt, blockHash: string, address: string, slot: string) => {
|
||||||
const { value, proof } = await getStorageAt({ blockHash, contract: address, slot });
|
const { value, proof } = await getStorageAt({ blockHash, contract: address, slot });
|
||||||
let length = 0;
|
let length = 0;
|
||||||
|
const proofs = [JSON.parse(proof.data)];
|
||||||
|
|
||||||
// Get length of bytes stored.
|
// Get length of bytes stored.
|
||||||
if (BigNumber.from(utils.hexDataSlice(value, 0, 1)).isZero()) {
|
if (BigNumber.from(utils.hexDataSlice(value, 0, 1)).isZero()) {
|
||||||
@ -353,14 +354,13 @@ const getBytesValue = async (getStorageAt: GetStorageAt, blockHash: string, addr
|
|||||||
if (length < 32) {
|
if (length < 32) {
|
||||||
return {
|
return {
|
||||||
value: utils.hexDataSlice(value, 0, length),
|
value: utils.hexDataSlice(value, 0, length),
|
||||||
proof
|
proof: {
|
||||||
|
data: JSON.stringify(proofs)
|
||||||
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
// Array to hold multiple bytes32 data.
|
// Array to hold multiple bytes32 data.
|
||||||
const proofs = [
|
|
||||||
JSON.parse(proof.data)
|
|
||||||
];
|
|
||||||
const hexStringArray = [];
|
const hexStringArray = [];
|
||||||
|
|
||||||
// Compute zero padded hexstring to calculate hashed position of storage.
|
// Compute zero padded hexstring to calculate hashed position of storage.
|
||||||
|
@ -1,7 +1,11 @@
|
|||||||
|
/* eslint-disable no-unused-expressions */
|
||||||
|
/* eslint-disable @typescript-eslint/no-explicit-any */
|
||||||
import { ContractInterface } from '@ethersproject/contracts';
|
import { ContractInterface } from '@ethersproject/contracts';
|
||||||
import '@nomiclabs/hardhat-ethers';
|
import '@nomiclabs/hardhat-ethers';
|
||||||
import { artifacts, ethers } from 'hardhat';
|
import { artifacts, ethers } from 'hardhat';
|
||||||
import { CompilerOutput, CompilerOutputBytecode } from 'hardhat/types';
|
import { CompilerOutput, CompilerOutputBytecode } from 'hardhat/types';
|
||||||
|
import { expect } from 'chai';
|
||||||
|
import isArray from 'lodash/isArray';
|
||||||
|
|
||||||
import { StorageLayout, GetStorageAt } from '../src';
|
import { StorageLayout, GetStorageAt } from '../src';
|
||||||
|
|
||||||
@ -25,6 +29,17 @@ interface StorageCompilerOutput extends CompilerOutput {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
interface ProofData {
|
||||||
|
blockHash: string;
|
||||||
|
account: {
|
||||||
|
address: string;
|
||||||
|
storage: {
|
||||||
|
ipldBlock: string;
|
||||||
|
cid: string;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get storage layout of specified contract.
|
* Get storage layout of specified contract.
|
||||||
* @param contractName
|
* @param contractName
|
||||||
@ -79,3 +94,77 @@ export const generateDummyAddresses = (length: number): Array<string> => {
|
|||||||
return ethers.utils.hexlify(ethers.utils.randomBytes(20));
|
return ethers.utils.hexlify(ethers.utils.randomBytes(20));
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get latest blockHash.
|
||||||
|
*/
|
||||||
|
export const getBlockHash = async (): Promise<string> => {
|
||||||
|
const blockNumber = await ethers.provider.getBlockNumber();
|
||||||
|
const { hash } = await ethers.provider.getBlock(blockNumber);
|
||||||
|
return hash;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Assert proof data returned from ipld graphql server.
|
||||||
|
* @param blockHash
|
||||||
|
* @param address
|
||||||
|
* @param proofData
|
||||||
|
*/
|
||||||
|
export const assertProofData = (blockHash: string, address: string, proofData: ProofData): void => {
|
||||||
|
const {
|
||||||
|
blockHash: proofBlockHash,
|
||||||
|
account: {
|
||||||
|
address: proofAddress,
|
||||||
|
storage
|
||||||
|
}
|
||||||
|
} = proofData;
|
||||||
|
|
||||||
|
expect(proofBlockHash).to.equal(blockHash);
|
||||||
|
expect(proofAddress).to.equal(address);
|
||||||
|
expect(storage.cid).to.not.be.empty;
|
||||||
|
expect(storage.ipldBlock).to.not.be.empty;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Assert array of proof data.
|
||||||
|
* @param blockHash
|
||||||
|
* @param address
|
||||||
|
* @param proofArray
|
||||||
|
*/
|
||||||
|
export const assertProofArray = (blockHash: string, address: string, proofArray: Array<any>): void => {
|
||||||
|
proofArray.forEach(proofData => {
|
||||||
|
if (isArray(proofData)) {
|
||||||
|
assertProofArray(blockHash, address, proofData);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (['blockHash', 'account'].every(key => key in proofData)) {
|
||||||
|
assertProofData(blockHash, address, proofData);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
assertProofStruct(blockHash, address, proofData);
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Assert array of proof data from structure type.
|
||||||
|
* @param blockHash
|
||||||
|
* @param address
|
||||||
|
* @param proofStruct
|
||||||
|
*/
|
||||||
|
export const assertProofStruct = (blockHash: string, address: string, proofStruct: {[key: string]: any}): void => {
|
||||||
|
Object.values(proofStruct).forEach(proofData => {
|
||||||
|
if (isArray(proofData)) {
|
||||||
|
assertProofArray(blockHash, address, proofData);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (['blockHash', 'account'].every(key => key in proofData)) {
|
||||||
|
assertProofData(blockHash, address, proofData);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
assertProofStruct(blockHash, address, proofData);
|
||||||
|
});
|
||||||
|
};
|
||||||
|
Loading…
Reference in New Issue
Block a user