Skip to content

Commit

Permalink
estimateGas supports blocktag
Browse files Browse the repository at this point in the history
  • Loading branch information
shunjizhan committed Dec 4, 2023
1 parent da83d1f commit 0955bb9
Show file tree
Hide file tree
Showing 5 changed files with 26 additions and 9 deletions.
18 changes: 13 additions & 5 deletions packages/eth-providers/src/base-provider.ts
Original file line number Diff line number Diff line change
Expand Up @@ -928,8 +928,11 @@ export abstract class BaseProvider extends AbstractProvider {
* @param transaction The transaction to estimate the gas of
* @returns The estimated gas used by this transaction
*/
estimateGas = async (transaction: Deferrable<TransactionRequest>): Promise<BigNumber> => {
const { usedGas, gasLimit, usedStorage } = await this.estimateResources(transaction);
estimateGas = async (
transaction: Deferrable<TransactionRequest>,
blockTag?: BlockTag | Promise<BlockTag>
): Promise<BigNumber> => {
const { usedGas, gasLimit, usedStorage } = await this.estimateResources(transaction, blockTag);

const tx = await resolveProperties(transaction);
const data = tx.data?.toString() ?? '0x';
Expand Down Expand Up @@ -1098,7 +1101,8 @@ export abstract class BaseProvider extends AbstractProvider {
* @returns The estimated resources used by this transaction
*/
estimateResources = async (
transaction: Deferrable<TransactionRequest>
transaction: Deferrable<TransactionRequest>,
blockTag?: BlockTag | Promise<BlockTag>,
): Promise<{
usedGas: BigNumber;
gasLimit: BigNumber;
Expand All @@ -1116,7 +1120,11 @@ export abstract class BaseProvider extends AbstractProvider {
storageLimit: STORAGE_LIMIT,
};

const gasInfo = await this._ethCall(txRequest);
const blockHash = blockTag && blockTag !== 'latest'
? await this._getBlockHash(blockTag)
: undefined; // if blockTag is latest, avoid explicit blockhash for better performance

const gasInfo = await this._ethCall(txRequest, blockHash);
const usedGas = BigNumber.from(gasInfo.used_gas).toNumber();
const usedStorage = gasInfo.used_storage;

Expand Down Expand Up @@ -1523,7 +1531,7 @@ export abstract class BaseProvider extends AbstractProvider {

switch (blockTag) {
case 'pending': {
return logger.throwError('pending tag not implemented', Logger.errors.UNSUPPORTED_OPERATION);
return logger.throwError('pending tag not supported', Logger.errors.UNSUPPORTED_OPERATION);
}
case 'latest': {
return this.safeMode ? this.finalizedBlockHash : this.bestBlockHash;
Expand Down
3 changes: 3 additions & 0 deletions packages/eth-rpc-adapter/src/__tests__/e2e/endpoint.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1940,6 +1940,9 @@ describe('endpoint', () => {
const { gasLimit } = await estimateGas(tx);
const bbb = (gasLimit.toNumber() % 100000) / 100;

const { gasLimit: gasLimitWithBlockTag } = await estimateGas(tx, 'latest');
expect(gasLimitWithBlockTag).to.equal(gasLimit);

// should be passing gasLimit instead of usedGas
expect(bbb).to.gt(GAS_MONSTER_GAS_REQUIRED / 30000);

Expand Down
5 changes: 3 additions & 2 deletions packages/eth-rpc-adapter/src/__tests__/e2e/utils.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { BigNumber, ContractFactory, Signer } from 'ethers';
import { BlockTagish } from '@acala-network/eth-providers';
import { Log, TransactionRequest } from '@ethersproject/abstract-provider';
import { expect } from 'vitest';
import { hexValue } from '@ethersproject/bytes';
Expand Down Expand Up @@ -71,9 +72,9 @@ export const eth_getTransactionByHash_karura = rpcGet('eth_getTransactionByHash'
export const eth_getBlockByNumber_karura = rpcGet('eth_getBlockByNumber', KARURA_ETH_RPC_URL);
export const eth_getStorageAt_karura = rpcGet('eth_getStorageAt', KARURA_ETH_RPC_URL);

export const estimateGas = async (tx: TransactionRequest) => {
export const estimateGas = async (tx: TransactionRequest, blockTag?: BlockTagish) => {
const gasPrice = (await eth_gasPrice([])).data.result;
const res = await eth_estimateGas([{ ...tx, gasPrice }]);
const res = await eth_estimateGas([{ ...tx, gasPrice }, blockTag]);
if (res.data.error) {
throw new Error(res.data.error.message);
}
Expand Down
4 changes: 2 additions & 2 deletions packages/eth-rpc-adapter/src/eip1193-bridge.ts
Original file line number Diff line number Diff line change
Expand Up @@ -293,8 +293,8 @@ class Eip1193BridgeImpl {
* @returns GAS USED - the amount of gas used.
*/
async eth_estimateGas(params: any[]): Promise<string> {
validate([{ type: 'transaction' }], params);
const val = await this.#provider.estimateGas(params[0]);
validate([{ type: 'transaction' }, { type: 'block?' }], params);
const val = await this.#provider.estimateGas(params[0], params[1]);
return hexValue(val);
}

Expand Down
5 changes: 5 additions & 0 deletions packages/eth-rpc-adapter/src/validate.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ export type Schema = {
type:
| 'address'
| 'block'
| 'block?'
| 'transaction'
| 'blockHash'
| 'trasactionHash'
Expand Down Expand Up @@ -148,6 +149,10 @@ export const validate = (schema: Schema, data: unknown[]) => {
validateBlock(data[i]);
break;
}
case 'block?': {
data[i] && validateBlock(data[i]);
break;
}
case 'transaction': {
validateTransaction(data[i]);
break;
Expand Down

0 comments on commit 0955bb9

Please sign in to comment.