In the blockchain, when a block is being prepared to be mined, the timestamp is adjusted by the chain's internal offset:
if (timestamp == null) {
timestamp = this.#adjustedTime(previousHeader.timestamp);
}
return new RuntimeBlock(
Quantity.from(previousNumber + 1n),
previousBlock.hash(),
this.coinbase,
minerOptions.blockGasLimit.toBuffer(),
BUFFER_ZERO,
Quantity.from(timestamp),
minerOptions.difficulty,
previousHeader.totalDifficulty,
Block.calcNextBaseFee(previousBlock)
);
However, eth_estimateGas
just uses the parent block's timestamp:
const block = new RuntimeBlock(
Quantity.from((parentHeader.number.toBigInt() || 0n) + 1n),
parentHeader.parentHash,
parentHeader.miner,
tx.gas.toBuffer(),
parentHeader.gasUsed.toBuffer(),
parentHeader.timestamp,
options.miner.difficulty,
parentHeader.totalDifficulty,
0n // no baseFeePerGas for estimates
);
This is particularly annoying if you are using Truffle to test a contract that is time dependent because truffle calls an eth_estimateGas
before sending your actual transaction. If you use evm_setTime
to the time needed for your contract to do what it needs to do, the actual transaction would pass, but Truffle doesn't let you get that far because the eth_estimateGas
fails beforehand.