Blockhash.test.js 2.7 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576
  1. const { ethers } = require('hardhat');
  2. const { expect } = require('chai');
  3. const { loadFixture, mine, mineUpTo, setCode } = require('@nomicfoundation/hardhat-network-helpers');
  4. const { impersonate } = require('../helpers/account');
  5. async function fixture() {
  6. const mock = await ethers.deployContract('$Blockhash');
  7. return { mock };
  8. }
  9. const HISTORY_STORAGE_ADDRESS = '0x0000F90827F1C53a10cb7A02335B175320002935';
  10. const SYSTEM_ADDRESS = '0xfffffffffffffffffffffffffffffffffffffffe';
  11. const HISTORY_SERVE_WINDOW = 8191;
  12. const BLOCKHASH_SERVE_WINDOW = 256;
  13. describe('Blockhash', function () {
  14. before(async function () {
  15. Object.assign(this, await loadFixture(fixture));
  16. impersonate(SYSTEM_ADDRESS);
  17. this.systemSigner = await ethers.getSigner(SYSTEM_ADDRESS);
  18. });
  19. it('recent block', async function () {
  20. await mine();
  21. const mostRecentBlock = (await ethers.provider.getBlock('latest')).number;
  22. const blockToCheck = mostRecentBlock - 1;
  23. const fetchedHash = (await ethers.provider.getBlock(blockToCheck)).hash;
  24. await expect(this.mock.$blockHash(blockToCheck)).to.eventually.equal(fetchedHash);
  25. });
  26. it('old block', async function () {
  27. await mine();
  28. const mostRecentBlock = await ethers.provider.getBlock('latest');
  29. // Call the history address with the most recent block hash
  30. await this.systemSigner.sendTransaction({
  31. to: HISTORY_STORAGE_ADDRESS,
  32. data: mostRecentBlock.hash,
  33. });
  34. await mineUpTo(mostRecentBlock.number + BLOCKHASH_SERVE_WINDOW + 10);
  35. // Verify blockhash after setting history
  36. await expect(this.mock.$blockHash(mostRecentBlock.number)).to.eventually.equal(mostRecentBlock.hash);
  37. });
  38. it('very old block', async function () {
  39. await mine();
  40. const mostRecentBlock = await ethers.provider.getBlock('latest');
  41. await mineUpTo(mostRecentBlock.number + HISTORY_SERVE_WINDOW + 10);
  42. await expect(this.mock.$blockHash(mostRecentBlock.number)).to.eventually.equal(ethers.ZeroHash);
  43. });
  44. it('future block', async function () {
  45. await mine();
  46. const mostRecentBlock = await ethers.provider.getBlock('latest');
  47. const blockToCheck = mostRecentBlock.number + 10;
  48. await expect(this.mock.$blockHash(blockToCheck)).to.eventually.equal(ethers.ZeroHash);
  49. });
  50. it('unsupported chain', async function () {
  51. await setCode(HISTORY_STORAGE_ADDRESS, '0x00');
  52. const mostRecentBlock = await ethers.provider.getBlock('latest');
  53. await mineUpTo(mostRecentBlock.number + BLOCKHASH_SERVE_WINDOW + 10);
  54. await expect(this.mock.$blockHash(mostRecentBlock.number)).to.eventually.equal(ethers.ZeroHash);
  55. await expect(this.mock.$blockHash(mostRecentBlock.number + 20)).to.eventually.not.equal(ethers.ZeroHash);
  56. });
  57. });