From 2eac1991941275a825bbb84d7f44ecee205935c5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Emanuel=20Tesa=C5=99?= Date: Tue, 20 May 2025 10:30:00 +0200 Subject: [PATCH 01/19] Prepare contracts for deployment --- contracts/IWstETH.sol | 9 ++++++++ contracts/WstETHApi3ReaderProxyV1.sol | 33 +++++++++++++++++++++++++++ scripts/deploy-morpho.ts | 22 ++++++++++++++++++ 3 files changed, 64 insertions(+) create mode 100644 contracts/IWstETH.sol create mode 100644 contracts/WstETHApi3ReaderProxyV1.sol create mode 100644 scripts/deploy-morpho.ts diff --git a/contracts/IWstETH.sol b/contracts/IWstETH.sol new file mode 100644 index 0000000..a037db8 --- /dev/null +++ b/contracts/IWstETH.sol @@ -0,0 +1,9 @@ +// SPDX-License-Identifier: MIT +pragma solidity ^0.8.27; + +/// @title A minimal interface for the wstETH contract indended to read the +/// stETH value per token value of 1 unit of wstETH. +interface IWstETH { + /// @notice Returns the stETH value per token value of 1 unit of wstETH. + function stEthPerToken() external view returns (uint256); +} diff --git a/contracts/WstETHApi3ReaderProxyV1.sol b/contracts/WstETHApi3ReaderProxyV1.sol new file mode 100644 index 0000000..7af97c1 --- /dev/null +++ b/contracts/WstETHApi3ReaderProxyV1.sol @@ -0,0 +1,33 @@ +// SPDX-License-Identifier: MIT +pragma solidity ^0.8.27; + +import "@api3/contracts/interfaces/IApi3ReaderProxy.sol"; +import "./IWstETH.sol"; + +/// @title An immutable proxy contract that reads the price of wstETH directly +/// from the WstETH contract on Ethereum. +/// @dev This contract implements only the IApi3ReaderProxy and not the +/// AggregatorV2V3Interface which is usually implemented with Api3 proxies. The +/// user of this contract needs to be aware of this and only use this contract +/// where the IApi3ReaderProxy interface is expected. +contract WstETHApi3ReaderProxyV1 is IApi3ReaderProxy { + address public constant WST_ETH = + 0x7f39C581F595B53c5cb19bD0b3f8dA6c935E2Ca0; + + constructor() {} + + /// @inheritdoc IApi3ReaderProxy + /// @dev The value returned by this function is the stETH value scaled to 18 + /// decimals. The timestamp returned is the current block timestamp. + function read() + public + view + override + returns (int224 value, uint32 timestamp) + { + uint256 stEthPerToken = IWstETH(WST_ETH).stEthPerToken(); + + value = int224(int256(stEthPerToken)); // stEthPerToken value has 18 decimals. + timestamp = uint32(block.timestamp); + } +} diff --git a/scripts/deploy-morpho.ts b/scripts/deploy-morpho.ts new file mode 100644 index 0000000..dd93ae5 --- /dev/null +++ b/scripts/deploy-morpho.ts @@ -0,0 +1,22 @@ +import { ethers } from 'ethers'; + +import { ProductApi3ReaderProxyV1__factory } from '../typechain-types'; + +const deployPriceFeedProxy = async () => { + const provider = new ethers.JsonRpcProvider(process.env.PROVIDER); + const signer = new ethers.Wallet(process.env.PK!, provider); + const productApi3ReaderProxyV1Factory = new ProductApi3ReaderProxyV1__factory(signer); + console.info('Deploying product proxy...'); + const tx = await productApi3ReaderProxyV1Factory.deploy( + '', // TODO: Deploy WstETHApi3ReaderProxyV1.sol + '0x37422cC8e1487a0452cc0D0BF75877d86c63c88A' // https://market.api3.org/ethereum/eth-usd/integrate?dappAlias=morpho-wsteth-usdc-860-lltv + ); + const productApi3ReaderProxyV1 = await tx.waitForDeployment(); + console.info('Deployed ProductApi3ReaderProxyV1:', await productApi3ReaderProxyV1.getAddress()); + console.info('ProductApi3ReaderProxyV1.read():', await productApi3ReaderProxyV1.read()); + // Deployed on Base: 0x707991d5533021021cC360dF093f1B396340Ef3E +}; + +deployPriceFeedProxy(); + +// NOTE: https://market.api3.org/ethereum/usdc-usd/integrate?dappAlias=morpho-wsteth-usdc-860-lltv From ba2eac8bc9bca8d15bd5419b1b80db003d7fcc5c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Emanuel=20Tesa=C5=99?= Date: Tue, 20 May 2025 10:32:14 +0200 Subject: [PATCH 02/19] Small docs updates --- contracts/IWstETH.sol | 4 ++-- contracts/WstETHApi3ReaderProxyV1.sol | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/contracts/IWstETH.sol b/contracts/IWstETH.sol index a037db8..a57b419 100644 --- a/contracts/IWstETH.sol +++ b/contracts/IWstETH.sol @@ -1,8 +1,8 @@ // SPDX-License-Identifier: MIT pragma solidity ^0.8.27; -/// @title A minimal interface for the wstETH contract indended to read the -/// stETH value per token value of 1 unit of wstETH. +/// @title A minimal interface for the wstETH contract on Ethereum, used to read +/// the stETH value per token value of 1 unit of wstETH. interface IWstETH { /// @notice Returns the stETH value per token value of 1 unit of wstETH. function stEthPerToken() external view returns (uint256); diff --git a/contracts/WstETHApi3ReaderProxyV1.sol b/contracts/WstETHApi3ReaderProxyV1.sol index 7af97c1..c2b1be0 100644 --- a/contracts/WstETHApi3ReaderProxyV1.sol +++ b/contracts/WstETHApi3ReaderProxyV1.sol @@ -4,8 +4,8 @@ pragma solidity ^0.8.27; import "@api3/contracts/interfaces/IApi3ReaderProxy.sol"; import "./IWstETH.sol"; -/// @title An immutable proxy contract that reads the price of wstETH directly -/// from the WstETH contract on Ethereum. +/// @title An immutable proxy contract that reads the price of wstETH/stETH +/// directly from the WstETH contract on Ethereum. /// @dev This contract implements only the IApi3ReaderProxy and not the /// AggregatorV2V3Interface which is usually implemented with Api3 proxies. The /// user of this contract needs to be aware of this and only use this contract From 6d4bf338b0b4eaf37f29a3dc63913adb525e852e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Emanuel=20Tesa=C5=99?= Date: Wed, 21 May 2025 16:41:04 +0200 Subject: [PATCH 03/19] Address review comments --- contracts/WstETHApi3ReaderProxyV1.sol | 5 ++--- contracts/{ => interfaces}/IWstETH.sol | 3 ++- 2 files changed, 4 insertions(+), 4 deletions(-) rename contracts/{ => interfaces}/IWstETH.sol (65%) diff --git a/contracts/WstETHApi3ReaderProxyV1.sol b/contracts/WstETHApi3ReaderProxyV1.sol index c2b1be0..79e3822 100644 --- a/contracts/WstETHApi3ReaderProxyV1.sol +++ b/contracts/WstETHApi3ReaderProxyV1.sol @@ -2,7 +2,7 @@ pragma solidity ^0.8.27; import "@api3/contracts/interfaces/IApi3ReaderProxy.sol"; -import "./IWstETH.sol"; +import "./interfaces/IWstETH.sol"; /// @title An immutable proxy contract that reads the price of wstETH/stETH /// directly from the WstETH contract on Ethereum. @@ -11,11 +11,10 @@ import "./IWstETH.sol"; /// user of this contract needs to be aware of this and only use this contract /// where the IApi3ReaderProxy interface is expected. contract WstETHApi3ReaderProxyV1 is IApi3ReaderProxy { + /// @notice The address of the wstETH contract on Ethereum mainnet. address public constant WST_ETH = 0x7f39C581F595B53c5cb19bD0b3f8dA6c935E2Ca0; - constructor() {} - /// @inheritdoc IApi3ReaderProxy /// @dev The value returned by this function is the stETH value scaled to 18 /// decimals. The timestamp returned is the current block timestamp. diff --git a/contracts/IWstETH.sol b/contracts/interfaces/IWstETH.sol similarity index 65% rename from contracts/IWstETH.sol rename to contracts/interfaces/IWstETH.sol index a57b419..eebe4d8 100644 --- a/contracts/IWstETH.sol +++ b/contracts/interfaces/IWstETH.sol @@ -3,7 +3,8 @@ pragma solidity ^0.8.27; /// @title A minimal interface for the wstETH contract on Ethereum, used to read /// the stETH value per token value of 1 unit of wstETH. +/// @dev The returned value is scaled to 18 decimals. interface IWstETH { - /// @notice Returns the stETH value per token value of 1 unit of wstETH. + /// @return The stETH value per token value of 1 unit of wstETH, scaled to 18 decimals. function stEthPerToken() external view returns (uint256); } From 223a4c0750d8236c76ce51037c0d0e40da784293 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Emanuel=20Tesa=C5=99?= Date: Wed, 21 May 2025 16:50:38 +0200 Subject: [PATCH 04/19] Improve docs --- contracts/WstETHApi3ReaderProxyV1.sol | 14 +++++++------- contracts/interfaces/IWstETH.sol | 9 +++++---- 2 files changed, 12 insertions(+), 11 deletions(-) diff --git a/contracts/WstETHApi3ReaderProxyV1.sol b/contracts/WstETHApi3ReaderProxyV1.sol index 79e3822..7e5eb1d 100644 --- a/contracts/WstETHApi3ReaderProxyV1.sol +++ b/contracts/WstETHApi3ReaderProxyV1.sol @@ -4,20 +4,20 @@ pragma solidity ^0.8.27; import "@api3/contracts/interfaces/IApi3ReaderProxy.sol"; import "./interfaces/IWstETH.sol"; -/// @title An immutable proxy contract that reads the price of wstETH/stETH +/// @title An immutable proxy contract that reads the stETH per wstETH ratio /// directly from the WstETH contract on Ethereum. -/// @dev This contract implements only the IApi3ReaderProxy and not the -/// AggregatorV2V3Interface which is usually implemented with Api3 proxies. The -/// user of this contract needs to be aware of this and only use this contract -/// where the IApi3ReaderProxy interface is expected. +/// @dev This contract implements only the IApi3ReaderProxy interface and not the +/// AggregatorV2V3Interface which is usually implemented by Api3 proxies. The +/// user of this contract needs to be aware of this limitation and only use this +/// contract where the IApi3ReaderProxy interface is expected. contract WstETHApi3ReaderProxyV1 is IApi3ReaderProxy { /// @notice The address of the wstETH contract on Ethereum mainnet. address public constant WST_ETH = 0x7f39C581F595B53c5cb19bD0b3f8dA6c935E2Ca0; /// @inheritdoc IApi3ReaderProxy - /// @dev The value returned by this function is the stETH value scaled to 18 - /// decimals. The timestamp returned is the current block timestamp. + /// @dev Returns the stETH/wstETH exchange rate with 18 decimals precision. + /// The timestamp returned is the current block timestamp. function read() public view diff --git a/contracts/interfaces/IWstETH.sol b/contracts/interfaces/IWstETH.sol index eebe4d8..019e4b6 100644 --- a/contracts/interfaces/IWstETH.sol +++ b/contracts/interfaces/IWstETH.sol @@ -1,10 +1,11 @@ // SPDX-License-Identifier: MIT pragma solidity ^0.8.27; -/// @title A minimal interface for the wstETH contract on Ethereum, used to read -/// the stETH value per token value of 1 unit of wstETH. -/// @dev The returned value is scaled to 18 decimals. +/// @title A minimal interface for the wstETH contract on Ethereum +/// @dev This interface only includes the stEthPerToken function needed to read +/// the exchange rate between stETH and wstETH. interface IWstETH { - /// @return The stETH value per token value of 1 unit of wstETH, scaled to 18 decimals. + /// @notice Returns the amount of stETH that corresponds to 1 wstETH + /// @return The stETH/wstETH exchange rate with 18 decimals precision function stEthPerToken() external view returns (uint256); } From 0a179e2a8d24da5098f251f1ea6c3a303dbd2daa Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Santiago=20Ace=C3=B1olaza?= Date: Wed, 21 May 2025 14:10:03 -0300 Subject: [PATCH 05/19] Adds hardhat-deploy scripts for proxy contracts --- deploy/001_deploy_InverseApi3ReaderProxyV1.ts | 35 ++++++++ .../002_deploy_NormalizedApi3ReaderProxyV1.ts | 48 ++++++++++ deploy/003_deploy_ProductApi3ReaderProxyV1.ts | 44 ++++++++++ deploy/004_deploy_ScaledApi3FeedProxyV1.ts | 51 +++++++++++ hardhat.config.ts | 1 + package.json | 5 ++ pnpm-lock.yaml | 88 +++++++++++++++++++ 7 files changed, 272 insertions(+) create mode 100644 deploy/001_deploy_InverseApi3ReaderProxyV1.ts create mode 100644 deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts create mode 100644 deploy/003_deploy_ProductApi3ReaderProxyV1.ts create mode 100644 deploy/004_deploy_ScaledApi3FeedProxyV1.ts diff --git a/deploy/001_deploy_InverseApi3ReaderProxyV1.ts b/deploy/001_deploy_InverseApi3ReaderProxyV1.ts new file mode 100644 index 0000000..dc3fb5d --- /dev/null +++ b/deploy/001_deploy_InverseApi3ReaderProxyV1.ts @@ -0,0 +1,35 @@ +import { DeployFunction } from 'hardhat-deploy/types'; +import { HardhatRuntimeEnvironment } from 'hardhat/types'; + +const func: DeployFunction = async function (hre: HardhatRuntimeEnvironment) { + const { deployments, getUnnamedAccounts } = hre; + const { deploy, log } = deployments; + + const [deployerAddress] = await getUnnamedAccounts(); + if (!deployerAddress) { + throw new Error("No deployer address found."); + } + log(`Deployer address: ${deployerAddress}`); + + const proxyAddress = process.env.PROXY; + if (!proxyAddress) { + throw new Error("PROXY environment variable not set. Please provide the address of the proxy contract."); + } + if (!hre.ethers.isAddress(proxyAddress)) { + throw new Error(`Invalid address provided for PROXY: ${proxyAddress}`); + } + log(`Proxy address: ${proxyAddress}`); + + await deployments + .get("InverseApi3ReaderProxyV1") + .catch(async () => { + return deploy("InverseApi3ReaderProxyV1", { + from: deployerAddress, + args: [proxyAddress], + log: true, + }); + }); +}; + +export default func; +func.tags = ['InverseApi3ReaderProxyV1']; \ No newline at end of file diff --git a/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts b/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts new file mode 100644 index 0000000..3e36ee4 --- /dev/null +++ b/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts @@ -0,0 +1,48 @@ +import { DeployFunction, DeploymentsExtension } from 'hardhat-deploy/types'; +import { HardhatRuntimeEnvironment } from 'hardhat/types'; + +const deployTestFeed = async (deployments: DeploymentsExtension, deployerAddress: string) => { + const { address: scaledApi3FeedProxyV1Address } = await deployments + .get("ScaledApi3FeedProxyV1") + .catch(async () => { + return deployments.deploy("ScaledApi3FeedProxyV1", { + from: deployerAddress, + args: ["0x5b0cf2b36a65a6BB085D501B971e4c102B9Cd473", 8], + log: true, + }); + }); + return scaledApi3FeedProxyV1Address; +} + +const func: DeployFunction = async function (hre: HardhatRuntimeEnvironment) { + const { deployments, getUnnamedAccounts, network } = hre; + const { deploy, log } = deployments; + + const [deployerAddress] = await getUnnamedAccounts(); + if (!deployerAddress) { + throw new Error("No deployer address found."); + } + log(`Deployer address: ${deployerAddress}`); + + const feedAddress = network.name !== "hardhat" ? process.env.FEED : await deployTestFeed(deployments, deployerAddress); + if (!feedAddress) { + throw new Error("FEED environment variable not set. Please provide the address of the AggregatorV2V3Interface contract."); + } + if (!hre.ethers.isAddress(feedAddress)) { + throw new Error(`Invalid address provided for FEED: ${feedAddress}`); + } + log(`Feed address: ${feedAddress}`); + + await deployments + .get("NormalizedApi3ReaderProxyV1") + .catch(async () => { + return deploy("NormalizedApi3ReaderProxyV1", { + from: deployerAddress, + args: [feedAddress], + log: true, + }); + }); +}; + +export default func; +func.tags = ['NormalizedApi3ReaderProxyV1']; \ No newline at end of file diff --git a/deploy/003_deploy_ProductApi3ReaderProxyV1.ts b/deploy/003_deploy_ProductApi3ReaderProxyV1.ts new file mode 100644 index 0000000..9f3ab94 --- /dev/null +++ b/deploy/003_deploy_ProductApi3ReaderProxyV1.ts @@ -0,0 +1,44 @@ +import { DeployFunction } from 'hardhat-deploy/types'; +import { HardhatRuntimeEnvironment } from 'hardhat/types'; + +const func: DeployFunction = async function (hre: HardhatRuntimeEnvironment) { + const { deployments, getUnnamedAccounts } = hre; + const { deploy, log } = deployments; + + const [deployerAddress] = await getUnnamedAccounts(); + if (!deployerAddress) { + throw new Error("No deployer address found."); + } + log(`Deployer address: ${deployerAddress}`); + + const proxy1Address = process.env.PROXY1; + if (!proxy1Address) { + throw new Error("PROXY1 environment variable not set. Please provide the address of the first proxy contract."); + } + if (!hre.ethers.isAddress(proxy1Address)) { + throw new Error(`Invalid address provided for PROXY1: ${proxy1Address}`); + } + log(`Proxy 1 address: ${proxy1Address}`); + + const proxy2Address = process.env.PROXY2; + if (!proxy2Address) { + throw new Error("PROXY2 environment variable not set. Please provide the address of the second proxy contract."); + } + if (!hre.ethers.isAddress(proxy2Address)) { + throw new Error(`Invalid address provided for PROXY2: ${proxy2Address}`); + } + log(`Proxy 2 address: ${proxy2Address}`); + + await deployments + .get("ProductApi3ReaderProxyV1") + .catch(async () => { + return deploy("ProductApi3ReaderProxyV1", { + from: deployerAddress, + args: [proxy1Address, proxy2Address], + log: true, + }); + }); +}; + +export default func; +func.tags = ['ProductApi3ReaderProxyV1']; \ No newline at end of file diff --git a/deploy/004_deploy_ScaledApi3FeedProxyV1.ts b/deploy/004_deploy_ScaledApi3FeedProxyV1.ts new file mode 100644 index 0000000..0730137 --- /dev/null +++ b/deploy/004_deploy_ScaledApi3FeedProxyV1.ts @@ -0,0 +1,51 @@ +import { DeployFunction, DeploymentsExtension } from 'hardhat-deploy/types'; +import { HardhatRuntimeEnvironment } from 'hardhat/types'; + +const deployTestProxy = async (deployments: DeploymentsExtension, deployerAddress: string) => { + const { address: inverseApi3ReaderProxyV1Address } = await deployments + .get("InverseApi3ReaderProxyV1") + .catch(async () => { + return deployments.deploy("InverseApi3ReaderProxyV1", { + from: deployerAddress, + args: ["0x5b0cf2b36a65a6BB085D501B971e4c102B9Cd473"], + log: true, + }); + }); + return inverseApi3ReaderProxyV1Address; +} + +const func: DeployFunction = async function (hre: HardhatRuntimeEnvironment) { + const { deployments, getUnnamedAccounts, network } = hre; + const { deploy, log } = deployments; + + const [deployerAddress] = await getUnnamedAccounts(); + if (!deployerAddress) { + throw new Error("No deployer address found."); + } + log(`Deployer address: ${deployerAddress}`); + + const proxyAddress = network.name !== "hardhat" ? process.env.PROXY : await deployTestProxy(deployments, deployerAddress); + if (!proxyAddress) { + throw new Error("PROXY environment variable not set. Please provide the address of the Api3ReaderProxy contract."); + } + if (!hre.ethers.isAddress(proxyAddress)) { + throw new Error(`Invalid address provided for PROXY: ${proxyAddress}`); + } + log(`Proxy address: ${proxyAddress}`); + + const decimals = process.env.DECIMALS ? parseInt(process.env.DECIMALS) : 18; + log(`Decimals: ${decimals}`); + + await deployments + .get("ScaledApi3FeedProxyV1") + .catch(async () => { + return deploy("ScaledApi3FeedProxyV1", { + from: deployerAddress, + args: [proxyAddress, decimals], + log: true, + }); + }); +}; + +export default func; +func.tags = ['ScaledApi3FeedProxyV1']; \ No newline at end of file diff --git a/hardhat.config.ts b/hardhat.config.ts index e50001a..21f0325 100644 --- a/hardhat.config.ts +++ b/hardhat.config.ts @@ -1,5 +1,6 @@ import { hardhatConfig } from '@api3/contracts'; import '@nomicfoundation/hardhat-toolbox'; +import 'hardhat-deploy'; import type { HardhatUserConfig } from 'hardhat/config'; const config: HardhatUserConfig = { diff --git a/package.json b/package.json index 3db3b4d..64acfa1 100644 --- a/package.json +++ b/package.json @@ -23,6 +23,10 @@ "scripts": { "build": "pnpm build:hardhat && tsc -p tsconfig.build.json", "build:hardhat": "hardhat --config hardhat.build.config.ts compile", + "deploy:InverseApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags InverseApi3ReaderProxyV1", + "deploy:NormalizedApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags NormalizedApi3ReaderProxyV1", + "deploy:ProductApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags ProductApi3ReaderProxyV1", + "deploy:ScaledApi3FeedProxyV1": "hardhat deploy --network $NETWORK --tags ScaledApi3FeedProxyV1", "lint": "pnpm run prettier:check && pnpm run lint:eslint && pnpm run lint:solhint", "lint:solhint": "solhint ./contracts/**/*.sol", "lint:eslint": "eslint . --ext .js,.ts", @@ -47,6 +51,7 @@ "ethers": "^6.14.0", "glob": "^11.0.2", "hardhat": "^2.24.0", + "hardhat-deploy": "^1.0.2", "prettier": "^3.5.3", "prettier-plugin-solidity": "^2.0.0", "solhint": "^5.1.0", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 60ba0c0..86511e0 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -53,6 +53,9 @@ importers: hardhat: specifier: ^2.24.0 version: 2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3) + hardhat-deploy: + specifier: ^1.0.2 + version: 1.0.2 prettier: specifier: ^3.5.3 version: 3.5.3 @@ -1134,6 +1137,9 @@ packages: resolution: {integrity: sha512-Xm7bpRXnDSX2YE2YFfBk2FnF0ep6tmG7xPh8iHee8MIcrgq762Nkce856dYtJYLkuIoYZvGfTs/PbZhideTcEg==} engines: {node: '>=4'} + axios@0.21.4: + resolution: {integrity: sha512-ut5vewkiu8jjGBdqpM44XxjuCjq9LAKeHVmoVfHVzy8eHgxxq8SbAVQNovDA8mVi05kP0Ea/n/UzcSHcTJQfNg==} + axios@1.9.0: resolution: {integrity: sha512-re4CqKTJaURpzbLHtIi6XpDv20/CnpXOtjRY5/CU32L8gU8ek9UIivcfvSWvmKEngmVbrUtPpdDwWDWL7DNHvg==} @@ -1548,6 +1554,9 @@ packages: emoji-regex@9.2.2: resolution: {integrity: sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==} + encode-utf8@1.0.3: + resolution: {integrity: sha512-ucAnuBEhUK4boH2HjVYG5Q2mQyPorvv0u/ocS+zhdw0S8AlHYY+GOFhP1Gio5z4icpP2ivFSvhtFjQi8+T9ppw==} + enquirer@2.4.1: resolution: {integrity: sha512-rRqJg/6gd538VHvR3PSrdRBb/1Vy2YfzHqzvbhGIQpDRKIa4FgV/54b5Q1xYSxOOwKvjXweS26E0Q+nAMwp2pQ==} engines: {node: '>=8.6'} @@ -1978,6 +1987,9 @@ packages: flatted@3.3.3: resolution: {integrity: sha512-GX+ysw4PBCz0PzosHDepZGANEuFCMLrnRTiEy9McGjmkCQYwRq4A/X786G/fjM/+OjsWSU1ZrY5qyARZmO/uwg==} + fmix@0.1.0: + resolution: {integrity: sha512-Y6hyofImk9JdzU8k5INtTXX1cu8LDlePWDFU5sftm9H+zKCr5SGrVjdhkvsim646cw5zD0nADj8oHyXMZmCZ9w==} + follow-redirects@1.15.9: resolution: {integrity: sha512-gew4GsXizNgdoRyqmyfMHyAmXsZDk6mHkSxZFCzW9gwlbtOW44CDtYavM+y+72qD/Vq2l550kMF52DT8fOLJqQ==} engines: {node: '>=4.0'} @@ -2174,6 +2186,9 @@ packages: engines: {node: '>=0.4.7'} hasBin: true + hardhat-deploy@1.0.2: + resolution: {integrity: sha512-FCeoGpYLQiGjROURihth6Qye+GWvRqalGbRsCTW33canhAS4g6mJEILbkWbWF8P2cPWgcpxe3cCJksk6n+oD7Q==} + hardhat-gas-reporter@1.0.10: resolution: {integrity: sha512-02N4+So/fZrzJ88ci54GqwVA3Zrf0C9duuTyGt0CFRIh/CdNwbnTgkXkRfojOMLBQ+6t+lBIkgbsOtqMvNwikA==} peerDependencies: @@ -2293,6 +2308,10 @@ packages: resolution: {integrity: sha512-TR3KfrTZTYLPB6jUjfx6MF9WcWrHL9su5TObK4ZkYgBdWKPOFoSoQIdEuTuR82pmtxH2spWG9h6etwfr1pLBqQ==} engines: {node: '>=6'} + imul@1.0.1: + resolution: {integrity: sha512-WFAgfwPLAjU66EKt6vRdTlKj4nAgIDQzh29JonLa4Bqtl6D8JrIMvWjCnx7xEjVNmP3U0fM5o8ZObk7d0f62bA==} + engines: {node: '>=0.10.0'} + imurmurhash@0.1.4: resolution: {integrity: sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==} engines: {node: '>=0.8.19'} @@ -2656,6 +2675,9 @@ packages: markdown-table@1.1.3: resolution: {integrity: sha512-1RUZVgQlpJSPWYbFSpmudq5nHY1doEIv89gBtF0s4gW1GF2XorxcA/70M5vq7rLv0a6mhOUccRsqkwhwLCIQ2Q==} + match-all@1.2.7: + resolution: {integrity: sha512-qSpsBKarh55r9KyXzFC3xBLRf2GlGasba2em9kbpRsSlGvdTAqjx3QD0r3FKSARiW+OE4iMHYsolM3aX9n5djw==} + math-intrinsics@1.1.0: resolution: {integrity: sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==} engines: {node: '>= 0.4'} @@ -2752,6 +2774,9 @@ packages: ms@2.1.3: resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==} + murmur-128@0.2.1: + resolution: {integrity: sha512-WseEgiRkI6aMFBbj8Cg9yBj/y+OdipwVC7zUo3W2W1JAJITwouUOtpqsmGSg67EQmwwSyod7hsVsWY5LsrfQVg==} + napi-postinstall@0.2.4: resolution: {integrity: sha512-ZEzHJwBhZ8qQSbknHqYcdtQVr8zUgGyM/q6h6qAyhtyVMNrSgDhrC4disf03dYW0e+czXyLnZINnCTEkWy0eJg==} engines: {node: ^12.20.0 || ^14.18.0 || >=16.0.0} @@ -3856,6 +3881,12 @@ packages: resolution: {integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==} engines: {node: '>=10'} + zksync-ethers@5.10.0: + resolution: {integrity: sha512-OAjTGAHF9wbdkRGkj7XZuF/a1Sk/FVbwH4pmLjAKlR7mJ7sQtQhBhrPU2dCc67xLaNvEESPfwil19ES5wooYFg==} + engines: {node: '>=16.0.0'} + peerDependencies: + ethers: ~5.7.0 + zod@3.24.4: resolution: {integrity: sha512-OdqJE9UDRPwWsrHjLN2F8bPxvwJBK22EHLWtanu0LSYr5YqzsaaW3RMgmjwr8Rypg5k+meEJdSPXJZXE/yqOMg==} @@ -5259,6 +5290,12 @@ snapshots: axe-core@4.10.3: {} + axios@0.21.4(debug@4.4.1): + dependencies: + follow-redirects: 1.15.9(debug@4.4.1) + transitivePeerDependencies: + - debug + axios@1.9.0: dependencies: follow-redirects: 1.15.9(debug@4.4.1) @@ -5725,6 +5762,8 @@ snapshots: emoji-regex@9.2.2: {} + encode-utf8@1.0.3: {} + enquirer@2.4.1: dependencies: ansi-colors: 4.1.3 @@ -6426,6 +6465,10 @@ snapshots: flatted@3.3.3: {} + fmix@0.1.0: + dependencies: + imul: 1.0.1 + follow-redirects@1.15.9(debug@4.4.1): optionalDependencies: debug: 4.4.1(supports-color@8.1.1) @@ -6679,6 +6722,37 @@ snapshots: optionalDependencies: uglify-js: 3.19.3 + hardhat-deploy@1.0.2: + dependencies: + '@ethersproject/abi': 5.8.0 + '@ethersproject/abstract-signer': 5.8.0 + '@ethersproject/address': 5.8.0 + '@ethersproject/bignumber': 5.8.0 + '@ethersproject/bytes': 5.8.0 + '@ethersproject/constants': 5.8.0 + '@ethersproject/contracts': 5.8.0 + '@ethersproject/providers': 5.8.0 + '@ethersproject/solidity': 5.8.0 + '@ethersproject/transactions': 5.8.0 + '@ethersproject/wallet': 5.8.0 + '@types/qs': 6.9.18 + axios: 0.21.4(debug@4.4.1) + chalk: 4.1.2 + chokidar: 3.6.0 + debug: 4.4.1(supports-color@8.1.1) + enquirer: 2.4.1 + ethers: 5.8.0 + form-data: 4.0.2 + fs-extra: 10.1.0 + match-all: 1.2.7 + murmur-128: 0.2.1 + qs: 6.14.0 + zksync-ethers: 5.10.0(ethers@5.8.0) + transitivePeerDependencies: + - bufferutil + - supports-color + - utf-8-validate + hardhat-gas-reporter@1.0.10(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)): dependencies: array-uniq: 1.0.3 @@ -6846,6 +6920,8 @@ snapshots: parent-module: 1.0.1 resolve-from: 4.0.0 + imul@1.0.1: {} + imurmurhash@0.1.4: {} indent-string@4.0.0: {} @@ -7186,6 +7262,8 @@ snapshots: markdown-table@1.1.3: {} + match-all@1.2.7: {} + math-intrinsics@1.1.0: {} md5.js@1.3.5: @@ -7286,6 +7364,12 @@ snapshots: ms@2.1.3: {} + murmur-128@0.2.1: + dependencies: + encode-utf8: 1.0.3 + fmix: 0.1.0 + imul: 1.0.1 + napi-postinstall@0.2.4: {} natural-compare@1.4.0: {} @@ -8557,4 +8641,8 @@ snapshots: yocto-queue@0.1.0: {} + zksync-ethers@5.10.0(ethers@5.8.0): + dependencies: + ethers: 5.8.0 + zod@3.24.4: {} From bef414ef961fa4a588924f36991838cb54621a65 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Santiago=20Ace=C3=B1olaza?= Date: Mon, 26 May 2025 11:47:30 -0300 Subject: [PATCH 06/19] Fixes eslint parser config --- .eslintrc.js | 4 +- deploy/001_deploy_InverseApi3ReaderProxyV1.ts | 54 ++- .../002_deploy_NormalizedApi3ReaderProxyV1.ts | 78 ++-- deploy/003_deploy_ProductApi3ReaderProxyV1.ts | 70 ++-- deploy/004_deploy_ScaledApi3FeedProxyV1.ts | 85 ++-- package.json | 6 +- pnpm-lock.yaml | 367 ++++++++++-------- tsconfig.json | 11 +- 8 files changed, 350 insertions(+), 325 deletions(-) diff --git a/.eslintrc.js b/.eslintrc.js index 2cafa70..6334a70 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -1,7 +1,8 @@ module.exports = { extends: ['plugin:@api3/eslint-plugin-commons/universal', 'plugin:@api3/eslint-plugin-commons/jest'], parserOptions: { - project: ['./tsconfig.json'], + project: './tsconfig.json', + tsconfigRootDir: __dirname, }, rules: { camelcase: 'off', @@ -26,4 +27,5 @@ module.exports = { '@typescript-eslint/no-unsafe-call': 'off', '@typescript-eslint/require-await': 'off', }, + ignorePatterns: ['typechain-types/*'], }; diff --git a/deploy/001_deploy_InverseApi3ReaderProxyV1.ts b/deploy/001_deploy_InverseApi3ReaderProxyV1.ts index dc3fb5d..b140cec 100644 --- a/deploy/001_deploy_InverseApi3ReaderProxyV1.ts +++ b/deploy/001_deploy_InverseApi3ReaderProxyV1.ts @@ -1,35 +1,29 @@ -import { DeployFunction } from 'hardhat-deploy/types'; -import { HardhatRuntimeEnvironment } from 'hardhat/types'; +import type { HardhatRuntimeEnvironment } from 'hardhat/types'; -const func: DeployFunction = async function (hre: HardhatRuntimeEnvironment) { - const { deployments, getUnnamedAccounts } = hre; - const { deploy, log } = deployments; +module.exports = async ({ getUnnamedAccounts, deployments, ethers }: HardhatRuntimeEnvironment) => { + const { deploy, log } = deployments; - const [deployerAddress] = await getUnnamedAccounts(); - if (!deployerAddress) { - throw new Error("No deployer address found."); - } - log(`Deployer address: ${deployerAddress}`); + const [deployerAddress] = await getUnnamedAccounts(); + if (!deployerAddress) { + throw new Error('No deployer address found.'); + } + log(`Deployer address: ${deployerAddress}`); - const proxyAddress = process.env.PROXY; - if (!proxyAddress) { - throw new Error("PROXY environment variable not set. Please provide the address of the proxy contract."); - } - if (!hre.ethers.isAddress(proxyAddress)) { - throw new Error(`Invalid address provided for PROXY: ${proxyAddress}`); - } - log(`Proxy address: ${proxyAddress}`); + const proxyAddress = process.env.PROXY; + if (!proxyAddress) { + throw new Error('PROXY environment variable not set. Please provide the address of the proxy contract.'); + } + if (!ethers.isAddress(proxyAddress)) { + throw new Error(`Invalid address provided for PROXY: ${proxyAddress}`); + } + log(`Proxy address: ${proxyAddress}`); - await deployments - .get("InverseApi3ReaderProxyV1") - .catch(async () => { - return deploy("InverseApi3ReaderProxyV1", { - from: deployerAddress, - args: [proxyAddress], - log: true, - }); - }); + await deployments.get('InverseApi3ReaderProxyV1').catch(async () => { + return deploy('InverseApi3ReaderProxyV1', { + from: deployerAddress, + args: [proxyAddress], + log: true, + }); + }); }; - -export default func; -func.tags = ['InverseApi3ReaderProxyV1']; \ No newline at end of file +module.exports.tags = ['InverseApi3ReaderProxyV1']; diff --git a/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts b/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts index 3e36ee4..24b9832 100644 --- a/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts +++ b/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts @@ -1,48 +1,44 @@ -import { DeployFunction, DeploymentsExtension } from 'hardhat-deploy/types'; -import { HardhatRuntimeEnvironment } from 'hardhat/types'; +import type { HardhatRuntimeEnvironment } from 'hardhat/types'; +import type { DeploymentsExtension } from 'hardhat-deploy/types'; const deployTestFeed = async (deployments: DeploymentsExtension, deployerAddress: string) => { - const { address: scaledApi3FeedProxyV1Address } = await deployments - .get("ScaledApi3FeedProxyV1") - .catch(async () => { - return deployments.deploy("ScaledApi3FeedProxyV1", { - from: deployerAddress, - args: ["0x5b0cf2b36a65a6BB085D501B971e4c102B9Cd473", 8], - log: true, - }); - }); - return scaledApi3FeedProxyV1Address; -} + const { address: scaledApi3FeedProxyV1Address } = await deployments.get('ScaledApi3FeedProxyV1').catch(async () => { + return deployments.deploy('ScaledApi3FeedProxyV1', { + from: deployerAddress, + args: ['0x5b0cf2b36a65a6BB085D501B971e4c102B9Cd473', 8], + log: true, + }); + }); + return scaledApi3FeedProxyV1Address; +}; -const func: DeployFunction = async function (hre: HardhatRuntimeEnvironment) { - const { deployments, getUnnamedAccounts, network } = hre; - const { deploy, log } = deployments; +module.exports = async ({ getUnnamedAccounts, deployments, network, ethers }: HardhatRuntimeEnvironment) => { + const { deploy, log } = deployments; - const [deployerAddress] = await getUnnamedAccounts(); - if (!deployerAddress) { - throw new Error("No deployer address found."); - } - log(`Deployer address: ${deployerAddress}`); + const [deployerAddress] = await getUnnamedAccounts(); + if (!deployerAddress) { + throw new Error('No deployer address found.'); + } + log(`Deployer address: ${deployerAddress}`); - const feedAddress = network.name !== "hardhat" ? process.env.FEED : await deployTestFeed(deployments, deployerAddress); - if (!feedAddress) { - throw new Error("FEED environment variable not set. Please provide the address of the AggregatorV2V3Interface contract."); - } - if (!hre.ethers.isAddress(feedAddress)) { - throw new Error(`Invalid address provided for FEED: ${feedAddress}`); - } - log(`Feed address: ${feedAddress}`); + const feedAddress = + network.name === 'hardhat' ? await deployTestFeed(deployments, deployerAddress) : process.env.FEED; + if (!feedAddress) { + throw new Error( + 'FEED environment variable not set. Please provide the address of the AggregatorV2V3Interface contract.' + ); + } + if (!ethers.isAddress(feedAddress)) { + throw new Error(`Invalid address provided for FEED: ${feedAddress}`); + } + log(`Feed address: ${feedAddress}`); - await deployments - .get("NormalizedApi3ReaderProxyV1") - .catch(async () => { - return deploy("NormalizedApi3ReaderProxyV1", { - from: deployerAddress, - args: [feedAddress], - log: true, - }); - }); + await deployments.get('NormalizedApi3ReaderProxyV1').catch(async () => { + return deploy('NormalizedApi3ReaderProxyV1', { + from: deployerAddress, + args: [feedAddress], + log: true, + }); + }); }; - -export default func; -func.tags = ['NormalizedApi3ReaderProxyV1']; \ No newline at end of file +module.exports.tags = ['NormalizedApi3ReaderProxyV1']; diff --git a/deploy/003_deploy_ProductApi3ReaderProxyV1.ts b/deploy/003_deploy_ProductApi3ReaderProxyV1.ts index 9f3ab94..ff633bb 100644 --- a/deploy/003_deploy_ProductApi3ReaderProxyV1.ts +++ b/deploy/003_deploy_ProductApi3ReaderProxyV1.ts @@ -1,44 +1,38 @@ -import { DeployFunction } from 'hardhat-deploy/types'; -import { HardhatRuntimeEnvironment } from 'hardhat/types'; +import type { HardhatRuntimeEnvironment } from 'hardhat/types'; -const func: DeployFunction = async function (hre: HardhatRuntimeEnvironment) { - const { deployments, getUnnamedAccounts } = hre; - const { deploy, log } = deployments; +module.exports = async ({ getUnnamedAccounts, deployments, ethers }: HardhatRuntimeEnvironment) => { + const { deploy, log } = deployments; - const [deployerAddress] = await getUnnamedAccounts(); - if (!deployerAddress) { - throw new Error("No deployer address found."); - } - log(`Deployer address: ${deployerAddress}`); + const [deployerAddress] = await getUnnamedAccounts(); + if (!deployerAddress) { + throw new Error('No deployer address found.'); + } + log(`Deployer address: ${deployerAddress}`); - const proxy1Address = process.env.PROXY1; - if (!proxy1Address) { - throw new Error("PROXY1 environment variable not set. Please provide the address of the first proxy contract."); - } - if (!hre.ethers.isAddress(proxy1Address)) { - throw new Error(`Invalid address provided for PROXY1: ${proxy1Address}`); - } - log(`Proxy 1 address: ${proxy1Address}`); + const proxy1Address = process.env.PROXY1; + if (!proxy1Address) { + throw new Error('PROXY1 environment variable not set. Please provide the address of the first proxy contract.'); + } + if (!ethers.isAddress(proxy1Address)) { + throw new Error(`Invalid address provided for PROXY1: ${proxy1Address}`); + } + log(`Proxy 1 address: ${proxy1Address}`); - const proxy2Address = process.env.PROXY2; - if (!proxy2Address) { - throw new Error("PROXY2 environment variable not set. Please provide the address of the second proxy contract."); - } - if (!hre.ethers.isAddress(proxy2Address)) { - throw new Error(`Invalid address provided for PROXY2: ${proxy2Address}`); - } - log(`Proxy 2 address: ${proxy2Address}`); + const proxy2Address = process.env.PROXY2; + if (!proxy2Address) { + throw new Error('PROXY2 environment variable not set. Please provide the address of the second proxy contract.'); + } + if (!ethers.isAddress(proxy2Address)) { + throw new Error(`Invalid address provided for PROXY2: ${proxy2Address}`); + } + log(`Proxy 2 address: ${proxy2Address}`); - await deployments - .get("ProductApi3ReaderProxyV1") - .catch(async () => { - return deploy("ProductApi3ReaderProxyV1", { - from: deployerAddress, - args: [proxy1Address, proxy2Address], - log: true, - }); - }); + await deployments.get('ProductApi3ReaderProxyV1').catch(async () => { + return deploy('ProductApi3ReaderProxyV1', { + from: deployerAddress, + args: [proxy1Address, proxy2Address], + log: true, + }); + }); }; - -export default func; -func.tags = ['ProductApi3ReaderProxyV1']; \ No newline at end of file +module.exports.tags = ['ProductApi3ReaderProxyV1']; diff --git a/deploy/004_deploy_ScaledApi3FeedProxyV1.ts b/deploy/004_deploy_ScaledApi3FeedProxyV1.ts index 0730137..2520c3f 100644 --- a/deploy/004_deploy_ScaledApi3FeedProxyV1.ts +++ b/deploy/004_deploy_ScaledApi3FeedProxyV1.ts @@ -1,51 +1,50 @@ -import { DeployFunction, DeploymentsExtension } from 'hardhat-deploy/types'; -import { HardhatRuntimeEnvironment } from 'hardhat/types'; +import type { HardhatRuntimeEnvironment } from 'hardhat/types'; +import type { DeploymentsExtension } from 'hardhat-deploy/types'; const deployTestProxy = async (deployments: DeploymentsExtension, deployerAddress: string) => { - const { address: inverseApi3ReaderProxyV1Address } = await deployments - .get("InverseApi3ReaderProxyV1") - .catch(async () => { - return deployments.deploy("InverseApi3ReaderProxyV1", { - from: deployerAddress, - args: ["0x5b0cf2b36a65a6BB085D501B971e4c102B9Cd473"], - log: true, - }); - }); - return inverseApi3ReaderProxyV1Address; -} + const { address: inverseApi3ReaderProxyV1Address } = await deployments + .get('InverseApi3ReaderProxyV1') + .catch(async () => { + return deployments.deploy('InverseApi3ReaderProxyV1', { + from: deployerAddress, + args: ['0x5b0cf2b36a65a6BB085D501B971e4c102B9Cd473'], + log: true, + }); + }); + return inverseApi3ReaderProxyV1Address; +}; -const func: DeployFunction = async function (hre: HardhatRuntimeEnvironment) { - const { deployments, getUnnamedAccounts, network } = hre; - const { deploy, log } = deployments; +module.exports = async ({ getUnnamedAccounts, deployments, network, ethers }: HardhatRuntimeEnvironment) => { + const { deploy, log } = deployments; - const [deployerAddress] = await getUnnamedAccounts(); - if (!deployerAddress) { - throw new Error("No deployer address found."); - } - log(`Deployer address: ${deployerAddress}`); + const [deployerAddress] = await getUnnamedAccounts(); + if (!deployerAddress) { + throw new Error('No deployer address found.'); + } + log(`Deployer address: ${deployerAddress}`); - const proxyAddress = network.name !== "hardhat" ? process.env.PROXY : await deployTestProxy(deployments, deployerAddress); - if (!proxyAddress) { - throw new Error("PROXY environment variable not set. Please provide the address of the Api3ReaderProxy contract."); - } - if (!hre.ethers.isAddress(proxyAddress)) { - throw new Error(`Invalid address provided for PROXY: ${proxyAddress}`); - } - log(`Proxy address: ${proxyAddress}`); + if (!process.env.DECIMALS) { + throw new Error('DECIMALS environment variable not set. Please provide the number of decimals to use.'); + } + const decimals = Number.parseInt(process.env.DECIMALS, 10); + log(`Decimals: ${decimals}`); - const decimals = process.env.DECIMALS ? parseInt(process.env.DECIMALS) : 18; - log(`Decimals: ${decimals}`); + const proxyAddress = + network.name === 'hardhat' ? await deployTestProxy(deployments, deployerAddress) : process.env.PROXY; + if (!proxyAddress) { + throw new Error('PROXY environment variable not set. Please provide the address of the Api3ReaderProxy contract.'); + } + if (!ethers.isAddress(proxyAddress)) { + throw new Error(`Invalid address provided for PROXY: ${proxyAddress}`); + } + log(`Proxy address: ${proxyAddress}`); - await deployments - .get("ScaledApi3FeedProxyV1") - .catch(async () => { - return deploy("ScaledApi3FeedProxyV1", { - from: deployerAddress, - args: [proxyAddress, decimals], - log: true, - }); - }); + await deployments.get('ScaledApi3FeedProxyV1').catch(async () => { + return deploy('ScaledApi3FeedProxyV1', { + from: deployerAddress, + args: [proxyAddress, decimals], + log: true, + }); + }); }; - -export default func; -func.tags = ['ScaledApi3FeedProxyV1']; \ No newline at end of file +module.exports.tags = ['ScaledApi3FeedProxyV1']; diff --git a/package.json b/package.json index 64acfa1..fc150da 100644 --- a/package.json +++ b/package.json @@ -38,6 +38,7 @@ "devDependencies": { "@api3/contracts": "^21.3.0", "@api3/eslint-plugin-commons": "^3.0.0", + "@eslint/js": "^9.27.0", "@nomicfoundation/hardhat-ethers": "^3.0.8", "@nomicfoundation/hardhat-network-helpers": "^1.0.12", "@nomicfoundation/hardhat-toolbox": "^5.0.0", @@ -47,7 +48,7 @@ "@typescript-eslint/eslint-plugin": "^7.18.0", "@typescript-eslint/parser": "^7.18.0", "chai": "^4.5.0", - "eslint": "8.57.0", + "eslint": "8.57.1", "ethers": "^6.14.0", "glob": "^11.0.2", "hardhat": "^2.24.0", @@ -58,7 +59,8 @@ "solidity-coverage": "^0.8.16", "ts-node": "^10.9.2", "typechain": "^8.3.2", - "typescript": "^5.8.3" + "typescript": "^5.8.3", + "typescript-eslint": "^8.32.1" }, "packageManager": "pnpm@9.15.2" } diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 86511e0..c7f1d2b 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -13,7 +13,10 @@ importers: version: 21.3.0(typescript@5.8.3) '@api3/eslint-plugin-commons': specifier: ^3.0.0 - version: 3.0.0(@babel/core@7.27.1)(eslint@8.57.0)(prettier@3.5.3)(typescript@5.8.3) + version: 3.0.0(@babel/core@7.27.1)(eslint@8.57.1)(prettier@3.5.3)(typescript@5.8.3) + '@eslint/js': + specifier: ^9.27.0 + version: 9.27.0 '@nomicfoundation/hardhat-ethers': specifier: ^3.0.8 version: 3.0.8(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) @@ -34,16 +37,16 @@ importers: version: 22.15.18 '@typescript-eslint/eslint-plugin': specifier: ^7.18.0 - version: 7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3) + version: 7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3) '@typescript-eslint/parser': specifier: ^7.18.0 - version: 7.18.0(eslint@8.57.0)(typescript@5.8.3) + version: 7.18.0(eslint@8.57.1)(typescript@5.8.3) chai: specifier: ^4.5.0 version: 4.5.0 eslint: - specifier: 8.57.0 - version: 8.57.0 + specifier: 8.57.1 + version: 8.57.1 ethers: specifier: ^6.14.0 version: 6.14.0 @@ -77,6 +80,9 @@ importers: typescript: specifier: ^5.8.3 version: 5.8.3 + typescript-eslint: + specifier: ^8.32.1 + version: 8.32.1(eslint@8.57.1)(typescript@5.8.3) packages: @@ -208,10 +214,14 @@ packages: resolution: {integrity: sha512-269Z39MS6wVJtsoUl10L60WdkhJVdPG24Q4eZTH3nnF6lpvSShEK3wQjDX9JRWAUPvPh7COouPpU9IrqaZFvtQ==} engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} - '@eslint/js@8.57.0': - resolution: {integrity: sha512-Ys+3g2TaW7gADOJzPt83SJtCDhMjndcDMFVQ/Tj9iA1BfJzFKD9mAUXT3OenpuPHbI6P/myECxRJrofUsDx/5g==} + '@eslint/js@8.57.1': + resolution: {integrity: sha512-d9zaMRSTIKDLhctzH12MtXvJKSSUhaHcjV+2Z+GK+EEY7XKpP5yR4x+N3TAcHTcu963nIr+TMcCb4DBCYX1z6Q==} engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + '@eslint/js@9.27.0': + resolution: {integrity: sha512-G5JD9Tu5HJEu4z2Uo4aHY2sLV64B7CDMXxFzqzjl3NKd6RVzSXNoE80jk7Y0lJkTTkjiIhBAqmlYwjuBY3tvpA==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + '@ethereumjs/rlp@4.0.1': resolution: {integrity: sha512-tqsQiBQDQdmPWE1xkkBq4rlSW5QZpLOUJ5RJh2/9fug+q9tnUhuZoVLk7s0scUIKTOzEtR72DFBXI4WiZcMpvw==} engines: {node: '>=14'} @@ -327,8 +337,8 @@ packages: resolution: {integrity: sha512-vBZP4NlzfOlerQTnba4aqZoMhE/a9HY7HRqoOPaETQcSQuWEIyZMHGfVu6w9wGtGK5fED5qRs2DteVCjOH60sA==} engines: {node: '>=14'} - '@humanwhocodes/config-array@0.11.14': - resolution: {integrity: sha512-3T8LkOmg45BV5FICb15QQMsyUSWrQ8AygVfC7ZG32zOalnqrilm018ZVCw0eapXux8FtA33q8PSRSstjee3jSg==} + '@humanwhocodes/config-array@0.13.0': + resolution: {integrity: sha512-DZLEEqFWQFiyK6h5YIeynKx7JlvCYWL0cImfSRXZ9l4Sg2efkFGTuFf6vzXjK1cq6IYkU+Eg/JizXw+TD2vRNw==} engines: {node: '>=10.10.0'} deprecated: Use @eslint/config-array instead @@ -1841,8 +1851,8 @@ packages: resolution: {integrity: sha512-UyLnSehNt62FFhSwjZlHmeokpRK59rcz29j+F1/aDgbkbRTk7wIc9XzdoasMUbRNKDM0qQt/+BJ4BrpFeABemw==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - eslint@8.57.0: - resolution: {integrity: sha512-dZ6+mexnaTIbSBZWgou51U6OmzIhYM2VcNdtiTtI7qPNZm35Akpr0f6vtw3w1Kmn5PYo+tZVfh13WrhpS6oLqQ==} + eslint@8.57.1: + resolution: {integrity: sha512-ypowyDxpVSYpkXr9WPv2PAZCtNip1Mv5KTW0SCurXv/9iOpcrH9PaqUElksqEB6pChqHGDRCFTyrZlGhnLNGiA==} engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} deprecated: This version is no longer supported. Please see https://eslint.org/version-support for other options. hasBin: true @@ -3654,6 +3664,13 @@ packages: typedarray@0.0.6: resolution: {integrity: sha512-/aCDEGatGvZ2BIk+HmLf4ifCJFwvKFNb9/JeZPMulfgFracn9QFcAf5GO8B/mweUjSoblS5In0cWhqpfs/5PQA==} + typescript-eslint@8.32.1: + resolution: {integrity: sha512-D7el+eaDHAmXvrZBy1zpzSNIRqnCOrkwTgZxTu3MUqRWk8k0q9m9Ho4+vPf7iHtgUfrK/o8IZaEApsxPlHTFCg==} + engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + peerDependencies: + eslint: ^8.57.0 || ^9.0.0 + typescript: '>=4.8.4 <5.9.0' + typescript@5.8.3: resolution: {integrity: sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ==} engines: {node: '>=14.17'} @@ -3912,26 +3929,26 @@ snapshots: - typescript - utf-8-validate - '@api3/eslint-plugin-commons@3.0.0(@babel/core@7.27.1)(eslint@8.57.0)(prettier@3.5.3)(typescript@5.8.3)': - dependencies: - '@shopify/eslint-plugin': 45.0.0(@babel/core@7.27.1)(eslint@8.57.0)(prettier@3.5.3)(typescript@5.8.3) - '@typescript-eslint/eslint-plugin': 8.32.1(@typescript-eslint/parser@8.32.1(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3) - '@typescript-eslint/parser': 8.32.1(eslint@8.57.0)(typescript@5.8.3) - eslint: 8.57.0 - eslint-config-next: 14.2.28(eslint@8.57.0)(typescript@5.8.3) - eslint-plugin-check-file: 2.8.0(eslint@8.57.0) - eslint-plugin-cypress: 3.6.0(eslint@8.57.0) - eslint-plugin-deprecation: 3.0.0(eslint@8.57.0)(typescript@5.8.3) - eslint-plugin-functional: 6.6.3(eslint@8.57.0)(typescript@5.8.3) - eslint-plugin-import: 2.31.0(@typescript-eslint/parser@8.32.1(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0) - eslint-plugin-jest: 28.11.0(@typescript-eslint/eslint-plugin@8.32.1(@typescript-eslint/parser@8.32.1(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3) - eslint-plugin-jest-formatting: 3.1.0(eslint@8.57.0) - eslint-plugin-lodash: 7.4.0(eslint@8.57.0) + '@api3/eslint-plugin-commons@3.0.0(@babel/core@7.27.1)(eslint@8.57.1)(prettier@3.5.3)(typescript@5.8.3)': + dependencies: + '@shopify/eslint-plugin': 45.0.0(@babel/core@7.27.1)(eslint@8.57.1)(prettier@3.5.3)(typescript@5.8.3) + '@typescript-eslint/eslint-plugin': 8.32.1(@typescript-eslint/parser@8.32.1(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/parser': 8.32.1(eslint@8.57.1)(typescript@5.8.3) + eslint: 8.57.1 + eslint-config-next: 14.2.28(eslint@8.57.1)(typescript@5.8.3) + eslint-plugin-check-file: 2.8.0(eslint@8.57.1) + eslint-plugin-cypress: 3.6.0(eslint@8.57.1) + eslint-plugin-deprecation: 3.0.0(eslint@8.57.1)(typescript@5.8.3) + eslint-plugin-functional: 6.6.3(eslint@8.57.1)(typescript@5.8.3) + eslint-plugin-import: 2.31.0(@typescript-eslint/parser@8.32.1(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1) + eslint-plugin-jest: 28.11.0(@typescript-eslint/eslint-plugin@8.32.1(@typescript-eslint/parser@8.32.1(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3) + eslint-plugin-jest-formatting: 3.1.0(eslint@8.57.1) + eslint-plugin-lodash: 7.4.0(eslint@8.57.1) eslint-plugin-no-only-tests: 3.3.0 - eslint-plugin-promise: 7.2.1(eslint@8.57.0) - eslint-plugin-react: 7.37.5(eslint@8.57.0) - eslint-plugin-react-hooks: 4.6.2(eslint@8.57.0) - eslint-plugin-unicorn: 55.0.0(eslint@8.57.0) + eslint-plugin-promise: 7.2.1(eslint@8.57.1) + eslint-plugin-react: 7.37.5(eslint@8.57.1) + eslint-plugin-react-hooks: 4.6.2(eslint@8.57.1) + eslint-plugin-unicorn: 55.0.0(eslint@8.57.1) lodash: 4.17.21 transitivePeerDependencies: - '@babel/core' @@ -3973,18 +3990,18 @@ snapshots: transitivePeerDependencies: - supports-color - '@babel/eslint-parser@7.27.1(@babel/core@7.27.1)(eslint@8.57.0)': + '@babel/eslint-parser@7.27.1(@babel/core@7.27.1)(eslint@8.57.1)': dependencies: '@babel/core': 7.27.1 '@nicolo-ribaudo/eslint-scope-5-internals': 5.1.1-v1 - eslint: 8.57.0 + eslint: 8.57.1 eslint-visitor-keys: 2.1.0 semver: 6.3.1 - '@babel/eslint-plugin@7.27.1(@babel/eslint-parser@7.27.1(@babel/core@7.27.1)(eslint@8.57.0))(eslint@8.57.0)': + '@babel/eslint-plugin@7.27.1(@babel/eslint-parser@7.27.1(@babel/core@7.27.1)(eslint@8.57.1))(eslint@8.57.1)': dependencies: - '@babel/eslint-parser': 7.27.1(@babel/core@7.27.1)(eslint@8.57.0) - eslint: 8.57.0 + '@babel/eslint-parser': 7.27.1(@babel/core@7.27.1)(eslint@8.57.1) + eslint: 8.57.1 eslint-rule-composer: 0.3.0 '@babel/generator@7.27.1': @@ -4079,9 +4096,9 @@ snapshots: tslib: 2.8.1 optional: true - '@eslint-community/eslint-utils@4.7.0(eslint@8.57.0)': + '@eslint-community/eslint-utils@4.7.0(eslint@8.57.1)': dependencies: - eslint: 8.57.0 + eslint: 8.57.1 eslint-visitor-keys: 3.4.3 '@eslint-community/regexpp@4.12.1': {} @@ -4100,7 +4117,9 @@ snapshots: transitivePeerDependencies: - supports-color - '@eslint/js@8.57.0': {} + '@eslint/js@8.57.1': {} + + '@eslint/js@9.27.0': {} '@ethereumjs/rlp@4.0.1': {} @@ -4382,7 +4401,7 @@ snapshots: '@fastify/busboy@2.1.1': {} - '@humanwhocodes/config-array@0.11.14': + '@humanwhocodes/config-array@0.13.0': dependencies: '@humanwhocodes/object-schema': 2.0.3 debug: 4.4.1(supports-color@8.1.1) @@ -4747,29 +4766,29 @@ snapshots: '@sentry/types': 5.30.0 tslib: 1.14.1 - '@shopify/eslint-plugin@45.0.0(@babel/core@7.27.1)(eslint@8.57.0)(prettier@3.5.3)(typescript@5.8.3)': + '@shopify/eslint-plugin@45.0.0(@babel/core@7.27.1)(eslint@8.57.1)(prettier@3.5.3)(typescript@5.8.3)': dependencies: - '@babel/eslint-parser': 7.27.1(@babel/core@7.27.1)(eslint@8.57.0) - '@babel/eslint-plugin': 7.27.1(@babel/eslint-parser@7.27.1(@babel/core@7.27.1)(eslint@8.57.0))(eslint@8.57.0) - '@typescript-eslint/eslint-plugin': 7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3) - '@typescript-eslint/parser': 7.18.0(eslint@8.57.0)(typescript@5.8.3) + '@babel/eslint-parser': 7.27.1(@babel/core@7.27.1)(eslint@8.57.1) + '@babel/eslint-plugin': 7.27.1(@babel/eslint-parser@7.27.1(@babel/core@7.27.1)(eslint@8.57.1))(eslint@8.57.1) + '@typescript-eslint/eslint-plugin': 7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/parser': 7.18.0(eslint@8.57.1)(typescript@5.8.3) change-case: 4.1.2 common-tags: 1.8.2 doctrine: 2.1.0 - eslint: 8.57.0 - eslint-config-prettier: 9.1.0(eslint@8.57.0) - eslint-module-utils: 2.12.0(@typescript-eslint/parser@7.18.0(eslint@8.57.0)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.0) - eslint-plugin-eslint-comments: 3.2.0(eslint@8.57.0) - eslint-plugin-import: 2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.0)(typescript@5.8.3))(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.0) - eslint-plugin-jest: 28.11.0(@typescript-eslint/eslint-plugin@7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3) - eslint-plugin-jest-formatting: 3.1.0(eslint@8.57.0) - eslint-plugin-jsx-a11y: 6.10.2(eslint@8.57.0) - eslint-plugin-node: 11.1.0(eslint@8.57.0) - eslint-plugin-prettier: 5.4.0(eslint-config-prettier@9.1.0(eslint@8.57.0))(eslint@8.57.0)(prettier@3.5.3) - eslint-plugin-promise: 6.6.0(eslint@8.57.0) - eslint-plugin-react: 7.37.5(eslint@8.57.0) - eslint-plugin-react-hooks: 4.6.2(eslint@8.57.0) - eslint-plugin-sort-class-members: 1.21.0(eslint@8.57.0) + eslint: 8.57.1 + eslint-config-prettier: 9.1.0(eslint@8.57.1) + eslint-module-utils: 2.12.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1))(eslint@8.57.1))(eslint@8.57.1) + eslint-plugin-eslint-comments: 3.2.0(eslint@8.57.1) + eslint-plugin-import: 2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.1) + eslint-plugin-jest: 28.11.0(@typescript-eslint/eslint-plugin@7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3) + eslint-plugin-jest-formatting: 3.1.0(eslint@8.57.1) + eslint-plugin-jsx-a11y: 6.10.2(eslint@8.57.1) + eslint-plugin-node: 11.1.0(eslint@8.57.1) + eslint-plugin-prettier: 5.4.0(eslint-config-prettier@9.1.0(eslint@8.57.1))(eslint@8.57.1)(prettier@3.5.3) + eslint-plugin-promise: 6.6.0(eslint@8.57.1) + eslint-plugin-react: 7.37.5(eslint@8.57.1) + eslint-plugin-react-hooks: 4.6.2(eslint@8.57.1) + eslint-plugin-sort-class-members: 1.21.0(eslint@8.57.1) jsx-ast-utils: 3.3.5 pkg-dir: 5.0.0 pluralize: 8.0.0 @@ -4884,15 +4903,15 @@ snapshots: dependencies: '@types/node': 22.15.18 - '@typescript-eslint/eslint-plugin@7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3)': + '@typescript-eslint/eslint-plugin@7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3)': dependencies: '@eslint-community/regexpp': 4.12.1 - '@typescript-eslint/parser': 7.18.0(eslint@8.57.0)(typescript@5.8.3) + '@typescript-eslint/parser': 7.18.0(eslint@8.57.1)(typescript@5.8.3) '@typescript-eslint/scope-manager': 7.18.0 - '@typescript-eslint/type-utils': 7.18.0(eslint@8.57.0)(typescript@5.8.3) - '@typescript-eslint/utils': 7.18.0(eslint@8.57.0)(typescript@5.8.3) + '@typescript-eslint/type-utils': 7.18.0(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/utils': 7.18.0(eslint@8.57.1)(typescript@5.8.3) '@typescript-eslint/visitor-keys': 7.18.0 - eslint: 8.57.0 + eslint: 8.57.1 graphemer: 1.4.0 ignore: 5.3.2 natural-compare: 1.4.0 @@ -4902,15 +4921,15 @@ snapshots: transitivePeerDependencies: - supports-color - '@typescript-eslint/eslint-plugin@8.32.1(@typescript-eslint/parser@8.32.1(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3)': + '@typescript-eslint/eslint-plugin@8.32.1(@typescript-eslint/parser@8.32.1(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3)': dependencies: '@eslint-community/regexpp': 4.12.1 - '@typescript-eslint/parser': 8.32.1(eslint@8.57.0)(typescript@5.8.3) + '@typescript-eslint/parser': 8.32.1(eslint@8.57.1)(typescript@5.8.3) '@typescript-eslint/scope-manager': 8.32.1 - '@typescript-eslint/type-utils': 8.32.1(eslint@8.57.0)(typescript@5.8.3) - '@typescript-eslint/utils': 8.32.1(eslint@8.57.0)(typescript@5.8.3) + '@typescript-eslint/type-utils': 8.32.1(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/utils': 8.32.1(eslint@8.57.1)(typescript@5.8.3) '@typescript-eslint/visitor-keys': 8.32.1 - eslint: 8.57.0 + eslint: 8.57.1 graphemer: 1.4.0 ignore: 7.0.4 natural-compare: 1.4.0 @@ -4919,27 +4938,27 @@ snapshots: transitivePeerDependencies: - supports-color - '@typescript-eslint/parser@7.18.0(eslint@8.57.0)(typescript@5.8.3)': + '@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3)': dependencies: '@typescript-eslint/scope-manager': 7.18.0 '@typescript-eslint/types': 7.18.0 '@typescript-eslint/typescript-estree': 7.18.0(typescript@5.8.3) '@typescript-eslint/visitor-keys': 7.18.0 debug: 4.4.1(supports-color@8.1.1) - eslint: 8.57.0 + eslint: 8.57.1 optionalDependencies: typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/parser@8.32.1(eslint@8.57.0)(typescript@5.8.3)': + '@typescript-eslint/parser@8.32.1(eslint@8.57.1)(typescript@5.8.3)': dependencies: '@typescript-eslint/scope-manager': 8.32.1 '@typescript-eslint/types': 8.32.1 '@typescript-eslint/typescript-estree': 8.32.1(typescript@5.8.3) '@typescript-eslint/visitor-keys': 8.32.1 debug: 4.4.1(supports-color@8.1.1) - eslint: 8.57.0 + eslint: 8.57.1 typescript: 5.8.3 transitivePeerDependencies: - supports-color @@ -4954,24 +4973,24 @@ snapshots: '@typescript-eslint/types': 8.32.1 '@typescript-eslint/visitor-keys': 8.32.1 - '@typescript-eslint/type-utils@7.18.0(eslint@8.57.0)(typescript@5.8.3)': + '@typescript-eslint/type-utils@7.18.0(eslint@8.57.1)(typescript@5.8.3)': dependencies: '@typescript-eslint/typescript-estree': 7.18.0(typescript@5.8.3) - '@typescript-eslint/utils': 7.18.0(eslint@8.57.0)(typescript@5.8.3) + '@typescript-eslint/utils': 7.18.0(eslint@8.57.1)(typescript@5.8.3) debug: 4.4.1(supports-color@8.1.1) - eslint: 8.57.0 + eslint: 8.57.1 ts-api-utils: 1.4.3(typescript@5.8.3) optionalDependencies: typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/type-utils@8.32.1(eslint@8.57.0)(typescript@5.8.3)': + '@typescript-eslint/type-utils@8.32.1(eslint@8.57.1)(typescript@5.8.3)': dependencies: '@typescript-eslint/typescript-estree': 8.32.1(typescript@5.8.3) - '@typescript-eslint/utils': 8.32.1(eslint@8.57.0)(typescript@5.8.3) + '@typescript-eslint/utils': 8.32.1(eslint@8.57.1)(typescript@5.8.3) debug: 4.4.1(supports-color@8.1.1) - eslint: 8.57.0 + eslint: 8.57.1 ts-api-utils: 2.1.0(typescript@5.8.3) typescript: 5.8.3 transitivePeerDependencies: @@ -5010,24 +5029,24 @@ snapshots: transitivePeerDependencies: - supports-color - '@typescript-eslint/utils@7.18.0(eslint@8.57.0)(typescript@5.8.3)': + '@typescript-eslint/utils@7.18.0(eslint@8.57.1)(typescript@5.8.3)': dependencies: - '@eslint-community/eslint-utils': 4.7.0(eslint@8.57.0) + '@eslint-community/eslint-utils': 4.7.0(eslint@8.57.1) '@typescript-eslint/scope-manager': 7.18.0 '@typescript-eslint/types': 7.18.0 '@typescript-eslint/typescript-estree': 7.18.0(typescript@5.8.3) - eslint: 8.57.0 + eslint: 8.57.1 transitivePeerDependencies: - supports-color - typescript - '@typescript-eslint/utils@8.32.1(eslint@8.57.0)(typescript@5.8.3)': + '@typescript-eslint/utils@8.32.1(eslint@8.57.1)(typescript@5.8.3)': dependencies: - '@eslint-community/eslint-utils': 4.7.0(eslint@8.57.0) + '@eslint-community/eslint-utils': 4.7.0(eslint@8.57.1) '@typescript-eslint/scope-manager': 8.32.1 '@typescript-eslint/types': 8.32.1 '@typescript-eslint/typescript-estree': 8.32.1(typescript@5.8.3) - eslint: 8.57.0 + eslint: 8.57.1 typescript: 5.8.3 transitivePeerDependencies: - supports-color @@ -5888,19 +5907,19 @@ snapshots: optionalDependencies: source-map: 0.2.0 - eslint-config-next@14.2.28(eslint@8.57.0)(typescript@5.8.3): + eslint-config-next@14.2.28(eslint@8.57.1)(typescript@5.8.3): dependencies: '@next/eslint-plugin-next': 14.2.28 '@rushstack/eslint-patch': 1.11.0 - '@typescript-eslint/eslint-plugin': 7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3) - '@typescript-eslint/parser': 7.18.0(eslint@8.57.0)(typescript@5.8.3) - eslint: 8.57.0 + '@typescript-eslint/eslint-plugin': 7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/parser': 7.18.0(eslint@8.57.1)(typescript@5.8.3) + eslint: 8.57.1 eslint-import-resolver-node: 0.3.9 - eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.31.0)(eslint@8.57.0) - eslint-plugin-import: 2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.0)(typescript@5.8.3))(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.0) - eslint-plugin-jsx-a11y: 6.10.2(eslint@8.57.0) - eslint-plugin-react: 7.37.5(eslint@8.57.0) - eslint-plugin-react-hooks: 4.6.2(eslint@8.57.0) + eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1))(eslint@8.57.1) + eslint-plugin-import: 2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.1) + eslint-plugin-jsx-a11y: 6.10.2(eslint@8.57.1) + eslint-plugin-react: 7.37.5(eslint@8.57.1) + eslint-plugin-react-hooks: 4.6.2(eslint@8.57.1) optionalDependencies: typescript: 5.8.3 transitivePeerDependencies: @@ -5908,9 +5927,9 @@ snapshots: - eslint-plugin-import-x - supports-color - eslint-config-prettier@9.1.0(eslint@8.57.0): + eslint-config-prettier@9.1.0(eslint@8.57.1): dependencies: - eslint: 8.57.0 + eslint: 8.57.1 eslint-import-resolver-node@0.3.9: dependencies: @@ -5920,82 +5939,82 @@ snapshots: transitivePeerDependencies: - supports-color - eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.31.0)(eslint@8.57.0): + eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1))(eslint@8.57.1): dependencies: '@nolyfill/is-core-module': 1.0.39 debug: 4.4.1(supports-color@8.1.1) - eslint: 8.57.0 + eslint: 8.57.1 get-tsconfig: 4.10.0 is-bun-module: 2.0.0 stable-hash: 0.0.5 tinyglobby: 0.2.13 unrs-resolver: 1.7.2 optionalDependencies: - eslint-plugin-import: 2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.0)(typescript@5.8.3))(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.0) + eslint-plugin-import: 2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.1) transitivePeerDependencies: - supports-color - eslint-module-utils@2.12.0(@typescript-eslint/parser@7.18.0(eslint@8.57.0)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.0): + eslint-module-utils@2.12.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1))(eslint@8.57.1))(eslint@8.57.1): dependencies: debug: 3.2.7 optionalDependencies: - '@typescript-eslint/parser': 7.18.0(eslint@8.57.0)(typescript@5.8.3) - eslint: 8.57.0 + '@typescript-eslint/parser': 7.18.0(eslint@8.57.1)(typescript@5.8.3) + eslint: 8.57.1 eslint-import-resolver-node: 0.3.9 - eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.31.0)(eslint@8.57.0) + eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1))(eslint@8.57.1) transitivePeerDependencies: - supports-color - eslint-module-utils@2.12.0(@typescript-eslint/parser@8.32.1(eslint@8.57.0)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint@8.57.0): + eslint-module-utils@2.12.0(@typescript-eslint/parser@8.32.1(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint@8.57.1): dependencies: debug: 3.2.7 optionalDependencies: - '@typescript-eslint/parser': 8.32.1(eslint@8.57.0)(typescript@5.8.3) - eslint: 8.57.0 + '@typescript-eslint/parser': 8.32.1(eslint@8.57.1)(typescript@5.8.3) + eslint: 8.57.1 eslint-import-resolver-node: 0.3.9 transitivePeerDependencies: - supports-color - eslint-plugin-check-file@2.8.0(eslint@8.57.0): + eslint-plugin-check-file@2.8.0(eslint@8.57.1): dependencies: - eslint: 8.57.0 + eslint: 8.57.1 is-glob: 4.0.3 micromatch: 4.0.8 - eslint-plugin-cypress@3.6.0(eslint@8.57.0): + eslint-plugin-cypress@3.6.0(eslint@8.57.1): dependencies: - eslint: 8.57.0 + eslint: 8.57.1 globals: 13.24.0 - eslint-plugin-deprecation@3.0.0(eslint@8.57.0)(typescript@5.8.3): + eslint-plugin-deprecation@3.0.0(eslint@8.57.1)(typescript@5.8.3): dependencies: - '@typescript-eslint/utils': 7.18.0(eslint@8.57.0)(typescript@5.8.3) - eslint: 8.57.0 + '@typescript-eslint/utils': 7.18.0(eslint@8.57.1)(typescript@5.8.3) + eslint: 8.57.1 ts-api-utils: 1.4.3(typescript@5.8.3) tslib: 2.8.1 typescript: 5.8.3 transitivePeerDependencies: - supports-color - eslint-plugin-es@3.0.1(eslint@8.57.0): + eslint-plugin-es@3.0.1(eslint@8.57.1): dependencies: - eslint: 8.57.0 + eslint: 8.57.1 eslint-utils: 2.1.0 regexpp: 3.2.0 - eslint-plugin-eslint-comments@3.2.0(eslint@8.57.0): + eslint-plugin-eslint-comments@3.2.0(eslint@8.57.1): dependencies: escape-string-regexp: 1.0.5 - eslint: 8.57.0 + eslint: 8.57.1 ignore: 5.3.2 - eslint-plugin-functional@6.6.3(eslint@8.57.0)(typescript@5.8.3): + eslint-plugin-functional@6.6.3(eslint@8.57.1)(typescript@5.8.3): dependencies: - '@typescript-eslint/utils': 7.18.0(eslint@8.57.0)(typescript@5.8.3) + '@typescript-eslint/utils': 7.18.0(eslint@8.57.1)(typescript@5.8.3) deepmerge-ts: 5.1.0 escape-string-regexp: 4.0.0 - eslint: 8.57.0 - is-immutable-type: 4.0.0(eslint@8.57.0)(typescript@5.8.3) + eslint: 8.57.1 + is-immutable-type: 4.0.0(eslint@8.57.1)(typescript@5.8.3) semver: 7.7.2 ts-api-utils: 1.4.3(typescript@5.8.3) optionalDependencies: @@ -6003,7 +6022,7 @@ snapshots: transitivePeerDependencies: - supports-color - eslint-plugin-import@2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.0)(typescript@5.8.3))(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.0): + eslint-plugin-import@2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.1): dependencies: '@rtsao/scc': 1.1.0 array-includes: 3.1.8 @@ -6012,9 +6031,9 @@ snapshots: array.prototype.flatmap: 1.3.3 debug: 3.2.7 doctrine: 2.1.0 - eslint: 8.57.0 + eslint: 8.57.1 eslint-import-resolver-node: 0.3.9 - eslint-module-utils: 2.12.0(@typescript-eslint/parser@7.18.0(eslint@8.57.0)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.0) + eslint-module-utils: 2.12.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1))(eslint@8.57.1))(eslint@8.57.1) hasown: 2.0.2 is-core-module: 2.16.1 is-glob: 4.0.3 @@ -6026,13 +6045,13 @@ snapshots: string.prototype.trimend: 1.0.9 tsconfig-paths: 3.15.0 optionalDependencies: - '@typescript-eslint/parser': 7.18.0(eslint@8.57.0)(typescript@5.8.3) + '@typescript-eslint/parser': 7.18.0(eslint@8.57.1)(typescript@5.8.3) transitivePeerDependencies: - eslint-import-resolver-typescript - eslint-import-resolver-webpack - supports-color - eslint-plugin-import@2.31.0(@typescript-eslint/parser@8.32.1(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0): + eslint-plugin-import@2.31.0(@typescript-eslint/parser@8.32.1(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1): dependencies: '@rtsao/scc': 1.1.0 array-includes: 3.1.8 @@ -6041,9 +6060,9 @@ snapshots: array.prototype.flatmap: 1.3.3 debug: 3.2.7 doctrine: 2.1.0 - eslint: 8.57.0 + eslint: 8.57.1 eslint-import-resolver-node: 0.3.9 - eslint-module-utils: 2.12.0(@typescript-eslint/parser@8.32.1(eslint@8.57.0)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint@8.57.0) + eslint-module-utils: 2.12.0(@typescript-eslint/parser@8.32.1(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint@8.57.1) hasown: 2.0.2 is-core-module: 2.16.1 is-glob: 4.0.3 @@ -6055,37 +6074,37 @@ snapshots: string.prototype.trimend: 1.0.9 tsconfig-paths: 3.15.0 optionalDependencies: - '@typescript-eslint/parser': 8.32.1(eslint@8.57.0)(typescript@5.8.3) + '@typescript-eslint/parser': 8.32.1(eslint@8.57.1)(typescript@5.8.3) transitivePeerDependencies: - eslint-import-resolver-typescript - eslint-import-resolver-webpack - supports-color - eslint-plugin-jest-formatting@3.1.0(eslint@8.57.0): + eslint-plugin-jest-formatting@3.1.0(eslint@8.57.1): dependencies: - eslint: 8.57.0 + eslint: 8.57.1 - eslint-plugin-jest@28.11.0(@typescript-eslint/eslint-plugin@7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3): + eslint-plugin-jest@28.11.0(@typescript-eslint/eslint-plugin@7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3): dependencies: - '@typescript-eslint/utils': 8.32.1(eslint@8.57.0)(typescript@5.8.3) - eslint: 8.57.0 + '@typescript-eslint/utils': 8.32.1(eslint@8.57.1)(typescript@5.8.3) + eslint: 8.57.1 optionalDependencies: - '@typescript-eslint/eslint-plugin': 7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3) + '@typescript-eslint/eslint-plugin': 7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3) transitivePeerDependencies: - supports-color - typescript - eslint-plugin-jest@28.11.0(@typescript-eslint/eslint-plugin@8.32.1(@typescript-eslint/parser@8.32.1(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3): + eslint-plugin-jest@28.11.0(@typescript-eslint/eslint-plugin@8.32.1(@typescript-eslint/parser@8.32.1(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3): dependencies: - '@typescript-eslint/utils': 8.32.1(eslint@8.57.0)(typescript@5.8.3) - eslint: 8.57.0 + '@typescript-eslint/utils': 8.32.1(eslint@8.57.1)(typescript@5.8.3) + eslint: 8.57.1 optionalDependencies: - '@typescript-eslint/eslint-plugin': 8.32.1(@typescript-eslint/parser@8.32.1(eslint@8.57.0)(typescript@5.8.3))(eslint@8.57.0)(typescript@5.8.3) + '@typescript-eslint/eslint-plugin': 8.32.1(@typescript-eslint/parser@8.32.1(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3) transitivePeerDependencies: - supports-color - typescript - eslint-plugin-jsx-a11y@6.10.2(eslint@8.57.0): + eslint-plugin-jsx-a11y@6.10.2(eslint@8.57.1): dependencies: aria-query: 5.3.2 array-includes: 3.1.8 @@ -6095,7 +6114,7 @@ snapshots: axobject-query: 4.1.0 damerau-levenshtein: 1.0.8 emoji-regex: 9.2.2 - eslint: 8.57.0 + eslint: 8.57.1 hasown: 2.0.2 jsx-ast-utils: 3.3.5 language-tags: 1.0.9 @@ -6104,46 +6123,46 @@ snapshots: safe-regex-test: 1.1.0 string.prototype.includes: 2.0.1 - eslint-plugin-lodash@7.4.0(eslint@8.57.0): + eslint-plugin-lodash@7.4.0(eslint@8.57.1): dependencies: - eslint: 8.57.0 + eslint: 8.57.1 lodash: 4.17.21 eslint-plugin-no-only-tests@3.3.0: {} - eslint-plugin-node@11.1.0(eslint@8.57.0): + eslint-plugin-node@11.1.0(eslint@8.57.1): dependencies: - eslint: 8.57.0 - eslint-plugin-es: 3.0.1(eslint@8.57.0) + eslint: 8.57.1 + eslint-plugin-es: 3.0.1(eslint@8.57.1) eslint-utils: 2.1.0 ignore: 5.3.2 minimatch: 3.1.2 resolve: 1.22.10 semver: 6.3.1 - eslint-plugin-prettier@5.4.0(eslint-config-prettier@9.1.0(eslint@8.57.0))(eslint@8.57.0)(prettier@3.5.3): + eslint-plugin-prettier@5.4.0(eslint-config-prettier@9.1.0(eslint@8.57.1))(eslint@8.57.1)(prettier@3.5.3): dependencies: - eslint: 8.57.0 + eslint: 8.57.1 prettier: 3.5.3 prettier-linter-helpers: 1.0.0 synckit: 0.11.5 optionalDependencies: - eslint-config-prettier: 9.1.0(eslint@8.57.0) + eslint-config-prettier: 9.1.0(eslint@8.57.1) - eslint-plugin-promise@6.6.0(eslint@8.57.0): + eslint-plugin-promise@6.6.0(eslint@8.57.1): dependencies: - eslint: 8.57.0 + eslint: 8.57.1 - eslint-plugin-promise@7.2.1(eslint@8.57.0): + eslint-plugin-promise@7.2.1(eslint@8.57.1): dependencies: - '@eslint-community/eslint-utils': 4.7.0(eslint@8.57.0) - eslint: 8.57.0 + '@eslint-community/eslint-utils': 4.7.0(eslint@8.57.1) + eslint: 8.57.1 - eslint-plugin-react-hooks@4.6.2(eslint@8.57.0): + eslint-plugin-react-hooks@4.6.2(eslint@8.57.1): dependencies: - eslint: 8.57.0 + eslint: 8.57.1 - eslint-plugin-react@7.37.5(eslint@8.57.0): + eslint-plugin-react@7.37.5(eslint@8.57.1): dependencies: array-includes: 3.1.8 array.prototype.findlast: 1.2.5 @@ -6151,7 +6170,7 @@ snapshots: array.prototype.tosorted: 1.1.4 doctrine: 2.1.0 es-iterator-helpers: 1.2.1 - eslint: 8.57.0 + eslint: 8.57.1 estraverse: 5.3.0 hasown: 2.0.2 jsx-ast-utils: 3.3.5 @@ -6165,18 +6184,18 @@ snapshots: string.prototype.matchall: 4.0.12 string.prototype.repeat: 1.0.0 - eslint-plugin-sort-class-members@1.21.0(eslint@8.57.0): + eslint-plugin-sort-class-members@1.21.0(eslint@8.57.1): dependencies: - eslint: 8.57.0 + eslint: 8.57.1 - eslint-plugin-unicorn@55.0.0(eslint@8.57.0): + eslint-plugin-unicorn@55.0.0(eslint@8.57.1): dependencies: '@babel/helper-validator-identifier': 7.27.1 - '@eslint-community/eslint-utils': 4.7.0(eslint@8.57.0) + '@eslint-community/eslint-utils': 4.7.0(eslint@8.57.1) ci-info: 4.2.0 clean-regexp: 1.0.0 core-js-compat: 3.42.0 - eslint: 8.57.0 + eslint: 8.57.1 esquery: 1.6.0 globals: 15.15.0 indent-string: 4.0.0 @@ -6213,13 +6232,13 @@ snapshots: eslint-visitor-keys@4.2.0: {} - eslint@8.57.0: + eslint@8.57.1: dependencies: - '@eslint-community/eslint-utils': 4.7.0(eslint@8.57.0) + '@eslint-community/eslint-utils': 4.7.0(eslint@8.57.1) '@eslint-community/regexpp': 4.12.1 '@eslint/eslintrc': 2.1.4 - '@eslint/js': 8.57.0 - '@humanwhocodes/config-array': 0.11.14 + '@eslint/js': 8.57.1 + '@humanwhocodes/config-array': 0.13.0 '@humanwhocodes/module-importer': 1.0.1 '@nodelib/fs.walk': 1.2.8 '@ungap/structured-clone': 1.3.0 @@ -7024,10 +7043,10 @@ snapshots: is-hex-prefixed@1.0.0: {} - is-immutable-type@4.0.0(eslint@8.57.0)(typescript@5.8.3): + is-immutable-type@4.0.0(eslint@8.57.1)(typescript@5.8.3): dependencies: - '@typescript-eslint/type-utils': 7.18.0(eslint@8.57.0)(typescript@5.8.3) - eslint: 8.57.0 + '@typescript-eslint/type-utils': 7.18.0(eslint@8.57.1)(typescript@5.8.3) + eslint: 8.57.1 ts-api-utils: 1.4.3(typescript@5.8.3) ts-declaration-location: 1.0.7(typescript@5.8.3) typescript: 5.8.3 @@ -8405,6 +8424,16 @@ snapshots: typedarray@0.0.6: {} + typescript-eslint@8.32.1(eslint@8.57.1)(typescript@5.8.3): + dependencies: + '@typescript-eslint/eslint-plugin': 8.32.1(@typescript-eslint/parser@8.32.1(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/parser': 8.32.1(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/utils': 8.32.1(eslint@8.57.1)(typescript@5.8.3) + eslint: 8.57.1 + typescript: 5.8.3 + transitivePeerDependencies: + - supports-color + typescript@5.8.3: {} typical@4.0.0: {} diff --git a/tsconfig.json b/tsconfig.json index 56e4b90..e8dfce1 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -28,5 +28,14 @@ "baseUrl": "./", "outDir": "./dist" }, - "include": ["**/*", ".eslintrc.js"] + "exclude": ["dist/**/*", "node_modules/**/*"], + "include": [ + "./deploy/**/*", + "./scripts/**/*", + "./src/**/*", + "./test/**/*", + ".eslintrc.js", + ".solcover.js", + "hardhat*.config.ts" + ] } From f9a155db5aa4d36310bf8860df9237db5f088355 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Santiago=20Ace=C3=B1olaza?= Date: Mon, 26 May 2025 13:22:53 -0300 Subject: [PATCH 07/19] Fixes type mismatch in tests --- package.json | 2 +- pnpm-lock.yaml | 89 ++++++++++++++++++++++++++++++++------------------ tsconfig.json | 4 ++- 3 files changed, 62 insertions(+), 33 deletions(-) diff --git a/package.json b/package.json index fc150da..e1670c4 100644 --- a/package.json +++ b/package.json @@ -49,7 +49,7 @@ "@typescript-eslint/parser": "^7.18.0", "chai": "^4.5.0", "eslint": "8.57.1", - "ethers": "^6.14.0", + "ethers": "^6.13.2", "glob": "^11.0.2", "hardhat": "^2.24.0", "hardhat-deploy": "^1.0.2", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index c7f1d2b..2dc24b0 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -19,13 +19,13 @@ importers: version: 9.27.0 '@nomicfoundation/hardhat-ethers': specifier: ^3.0.8 - version: 3.0.8(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) + version: 3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) '@nomicfoundation/hardhat-network-helpers': specifier: ^1.0.12 version: 1.0.12(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) '@nomicfoundation/hardhat-toolbox': specifier: ^5.0.0 - version: 5.0.0(oa6ffqnvyzeztptbpf2yiefg4m) + version: 5.0.0(a6kpgdsxfxicrejf26ezaasetm) '@types/chai': specifier: ^4.3.20 version: 4.3.20 @@ -48,8 +48,8 @@ importers: specifier: 8.57.1 version: 8.57.1 ethers: - specifier: ^6.14.0 - version: 6.14.0 + specifier: ^6.13.2 + version: 6.13.2 glob: specifier: ^11.0.2 version: 11.0.2 @@ -729,6 +729,9 @@ packages: '@types/node@10.17.60': resolution: {integrity: sha512-F0KIgDJfy2nA3zMLmWGKxcH2ZVEtCZXHHdOQs2gSaQ27+lNeEfGxzkIw90aXswATX7AZ33tahPbzy6KAfUreVw==} + '@types/node@18.15.13': + resolution: {integrity: sha512-N+0kuo9KgrUQ1Sn/ifDXsvg0TTleP7rIy4zOBGECxAljqvqfqpTfzx0Q1NUedOixRMBfe2Whhb056a42cWs26Q==} + '@types/node@22.15.18': resolution: {integrity: sha512-v1DKRfUdyW+jJhZNEI1PYy29S2YRxMV5AOO/x/SjKmW0acCIOqmbj6Haf9eHAhsPmrhlHSxEhv/1WszcLWV4cg==} @@ -1922,6 +1925,10 @@ packages: ethers@5.8.0: resolution: {integrity: sha512-DUq+7fHrCg1aPDFCHx6UIPb3nmt2XMpM7Y/g2gLhsl3lIBqeAfOJIl1qEvRf2uq3BiKxmh6Fh5pfp2ieyek7Kg==} + ethers@6.13.2: + resolution: {integrity: sha512-9VkriTTed+/27BGuY1s0hf441kqwHJ1wtN2edksEtiRvXx+soxRX3iSXTfFqq2+YwrOqbDoTHjIhQnjJRlzKmg==} + engines: {node: '>=14.0.0'} + ethers@6.14.0: resolution: {integrity: sha512-KgHwltNSMdbrGWEyKkM0Rt2s+u1nDH/5BVDQakLinzGEJi4bWindBzZSCC4gKsbZjwDTI6ex/8suR9Ihbmz4IQ==} engines: {node: '>=14.0.0'} @@ -3598,6 +3605,9 @@ packages: tslib@1.14.1: resolution: {integrity: sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==} + tslib@2.4.0: + resolution: {integrity: sha512-d6xOpEDfsi2CZVlPQzGeux8XMwLT9hssAsaPYExaQMuYskwb+x1x7J371tWlbBdWHroy99KnVB6qIkUbs5X3UQ==} + tslib@2.7.0: resolution: {integrity: sha512-gLXCKdN1/j47AiHiOkJN69hJmcbGTHI0ImLmbYLHykhgeN0jVGola9yVjFgzCUklsZQMW55o+dW7IXv3RCXDzA==} @@ -3920,7 +3930,7 @@ snapshots: '@api3/contracts@21.3.0(typescript@5.8.3)': dependencies: - ethers: 6.14.0 + ethers: 6.13.2 viem: 2.29.2(typescript@5.8.3)(zod@3.24.4) yargs: 17.7.2 zod: 3.24.4 @@ -4521,32 +4531,32 @@ snapshots: '@nomicfoundation/edr-linux-x64-musl': 0.11.0 '@nomicfoundation/edr-win32-x64-msvc': 0.11.0 - '@nomicfoundation/hardhat-chai-matchers@2.0.8(@nomicfoundation/hardhat-ethers@3.0.8(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(chai@4.5.0)(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))': + '@nomicfoundation/hardhat-chai-matchers@2.0.8(@nomicfoundation/hardhat-ethers@3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(chai@4.5.0)(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))': dependencies: - '@nomicfoundation/hardhat-ethers': 3.0.8(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) + '@nomicfoundation/hardhat-ethers': 3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) '@types/chai-as-promised': 7.1.8 chai: 4.5.0 chai-as-promised: 7.1.2(chai@4.5.0) deep-eql: 4.1.4 - ethers: 6.14.0 + ethers: 6.13.2 hardhat: 2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3) ordinal: 1.0.3 - '@nomicfoundation/hardhat-ethers@3.0.8(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))': + '@nomicfoundation/hardhat-ethers@3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))': dependencies: debug: 4.4.1(supports-color@8.1.1) - ethers: 6.14.0 + ethers: 6.13.2 hardhat: 2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3) lodash.isequal: 4.5.0 transitivePeerDependencies: - supports-color - '@nomicfoundation/hardhat-ignition-ethers@0.15.11(@nomicfoundation/hardhat-ethers@3.0.8(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/hardhat-ignition@0.15.11(@nomicfoundation/hardhat-verify@2.0.13(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/ignition-core@0.15.11)(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))': + '@nomicfoundation/hardhat-ignition-ethers@0.15.11(@nomicfoundation/hardhat-ethers@3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/hardhat-ignition@0.15.11(@nomicfoundation/hardhat-verify@2.0.13(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/ignition-core@0.15.11)(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))': dependencies: - '@nomicfoundation/hardhat-ethers': 3.0.8(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) + '@nomicfoundation/hardhat-ethers': 3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) '@nomicfoundation/hardhat-ignition': 0.15.11(@nomicfoundation/hardhat-verify@2.0.13(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) '@nomicfoundation/ignition-core': 0.15.11 - ethers: 6.14.0 + ethers: 6.13.2 hardhat: 2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3) '@nomicfoundation/hardhat-ignition@0.15.11(@nomicfoundation/hardhat-verify@2.0.13(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))': @@ -4570,20 +4580,20 @@ snapshots: ethereumjs-util: 7.1.5 hardhat: 2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3) - '@nomicfoundation/hardhat-toolbox@5.0.0(oa6ffqnvyzeztptbpf2yiefg4m)': + '@nomicfoundation/hardhat-toolbox@5.0.0(a6kpgdsxfxicrejf26ezaasetm)': dependencies: - '@nomicfoundation/hardhat-chai-matchers': 2.0.8(@nomicfoundation/hardhat-ethers@3.0.8(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(chai@4.5.0)(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) - '@nomicfoundation/hardhat-ethers': 3.0.8(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) - '@nomicfoundation/hardhat-ignition-ethers': 0.15.11(@nomicfoundation/hardhat-ethers@3.0.8(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/hardhat-ignition@0.15.11(@nomicfoundation/hardhat-verify@2.0.13(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/ignition-core@0.15.11)(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) + '@nomicfoundation/hardhat-chai-matchers': 2.0.8(@nomicfoundation/hardhat-ethers@3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(chai@4.5.0)(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) + '@nomicfoundation/hardhat-ethers': 3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) + '@nomicfoundation/hardhat-ignition-ethers': 0.15.11(@nomicfoundation/hardhat-ethers@3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/hardhat-ignition@0.15.11(@nomicfoundation/hardhat-verify@2.0.13(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/ignition-core@0.15.11)(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) '@nomicfoundation/hardhat-network-helpers': 1.0.12(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) '@nomicfoundation/hardhat-verify': 2.0.13(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) - '@typechain/ethers-v6': 0.5.1(ethers@6.14.0)(typechain@8.3.2(typescript@5.8.3))(typescript@5.8.3) - '@typechain/hardhat': 9.1.0(@typechain/ethers-v6@0.5.1(ethers@6.14.0)(typechain@8.3.2(typescript@5.8.3))(typescript@5.8.3))(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))(typechain@8.3.2(typescript@5.8.3)) + '@typechain/ethers-v6': 0.5.1(ethers@6.13.2)(typechain@8.3.2(typescript@5.8.3))(typescript@5.8.3) + '@typechain/hardhat': 9.1.0(@typechain/ethers-v6@0.5.1(ethers@6.13.2)(typechain@8.3.2(typescript@5.8.3))(typescript@5.8.3))(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))(typechain@8.3.2(typescript@5.8.3)) '@types/chai': 4.3.20 '@types/mocha': 10.0.10 '@types/node': 22.15.18 chai: 4.5.0 - ethers: 6.14.0 + ethers: 6.13.2 hardhat: 2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3) hardhat-gas-reporter: 1.0.10(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) solidity-coverage: 0.8.16(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) @@ -4777,7 +4787,7 @@ snapshots: doctrine: 2.1.0 eslint: 8.57.1 eslint-config-prettier: 9.1.0(eslint@8.57.1) - eslint-module-utils: 2.12.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1))(eslint@8.57.1))(eslint@8.57.1) + eslint-module-utils: 2.12.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.1) eslint-plugin-eslint-comments: 3.2.0(eslint@8.57.1) eslint-plugin-import: 2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.1) eslint-plugin-jest: 28.11.0(@typescript-eslint/eslint-plugin@7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3) @@ -4828,18 +4838,18 @@ snapshots: tslib: 2.8.1 optional: true - '@typechain/ethers-v6@0.5.1(ethers@6.14.0)(typechain@8.3.2(typescript@5.8.3))(typescript@5.8.3)': + '@typechain/ethers-v6@0.5.1(ethers@6.13.2)(typechain@8.3.2(typescript@5.8.3))(typescript@5.8.3)': dependencies: - ethers: 6.14.0 + ethers: 6.13.2 lodash: 4.17.21 ts-essentials: 7.0.3(typescript@5.8.3) typechain: 8.3.2(typescript@5.8.3) typescript: 5.8.3 - '@typechain/hardhat@9.1.0(@typechain/ethers-v6@0.5.1(ethers@6.14.0)(typechain@8.3.2(typescript@5.8.3))(typescript@5.8.3))(ethers@6.14.0)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))(typechain@8.3.2(typescript@5.8.3))': + '@typechain/hardhat@9.1.0(@typechain/ethers-v6@0.5.1(ethers@6.13.2)(typechain@8.3.2(typescript@5.8.3))(typescript@5.8.3))(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))(typechain@8.3.2(typescript@5.8.3))': dependencies: - '@typechain/ethers-v6': 0.5.1(ethers@6.14.0)(typechain@8.3.2(typescript@5.8.3))(typescript@5.8.3) - ethers: 6.14.0 + '@typechain/ethers-v6': 0.5.1(ethers@6.13.2)(typechain@8.3.2(typescript@5.8.3))(typescript@5.8.3) + ethers: 6.13.2 fs-extra: 9.1.0 hardhat: 2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3) typechain: 8.3.2(typescript@5.8.3) @@ -4879,6 +4889,8 @@ snapshots: '@types/node@10.17.60': {} + '@types/node@18.15.13': {} + '@types/node@22.15.18': dependencies: undici-types: 6.21.0 @@ -5915,7 +5927,7 @@ snapshots: '@typescript-eslint/parser': 7.18.0(eslint@8.57.1)(typescript@5.8.3) eslint: 8.57.1 eslint-import-resolver-node: 0.3.9 - eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1))(eslint@8.57.1) + eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.31.0)(eslint@8.57.1) eslint-plugin-import: 2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.1) eslint-plugin-jsx-a11y: 6.10.2(eslint@8.57.1) eslint-plugin-react: 7.37.5(eslint@8.57.1) @@ -5939,7 +5951,7 @@ snapshots: transitivePeerDependencies: - supports-color - eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1))(eslint@8.57.1): + eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.31.0)(eslint@8.57.1): dependencies: '@nolyfill/is-core-module': 1.0.39 debug: 4.4.1(supports-color@8.1.1) @@ -5954,14 +5966,14 @@ snapshots: transitivePeerDependencies: - supports-color - eslint-module-utils@2.12.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1))(eslint@8.57.1))(eslint@8.57.1): + eslint-module-utils@2.12.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.1): dependencies: debug: 3.2.7 optionalDependencies: '@typescript-eslint/parser': 7.18.0(eslint@8.57.1)(typescript@5.8.3) eslint: 8.57.1 eslint-import-resolver-node: 0.3.9 - eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1))(eslint@8.57.1) + eslint-import-resolver-typescript: 3.10.1(eslint-plugin-import@2.31.0)(eslint@8.57.1) transitivePeerDependencies: - supports-color @@ -6033,7 +6045,7 @@ snapshots: doctrine: 2.1.0 eslint: 8.57.1 eslint-import-resolver-node: 0.3.9 - eslint-module-utils: 2.12.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1(eslint-plugin-import@2.31.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1))(eslint@8.57.1))(eslint@8.57.1) + eslint-module-utils: 2.12.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.10.1)(eslint@8.57.1) hasown: 2.0.2 is-core-module: 2.16.1 is-glob: 4.0.3 @@ -6401,6 +6413,19 @@ snapshots: - bufferutil - utf-8-validate + ethers@6.13.2: + dependencies: + '@adraffy/ens-normalize': 1.10.1 + '@noble/curves': 1.2.0 + '@noble/hashes': 1.3.2 + '@types/node': 18.15.13 + aes-js: 4.0.0-beta.5 + tslib: 2.4.0 + ws: 8.17.1 + transitivePeerDependencies: + - bufferutil + - utf-8-validate + ethers@6.14.0: dependencies: '@adraffy/ens-normalize': 1.10.1 @@ -8347,6 +8372,8 @@ snapshots: tslib@1.14.1: {} + tslib@2.4.0: {} + tslib@2.7.0: {} tslib@2.8.1: {} diff --git a/tsconfig.json b/tsconfig.json index e8dfce1..a50169f 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -34,8 +34,10 @@ "./scripts/**/*", "./src/**/*", "./test/**/*", + "./typechain-types/**/*", ".eslintrc.js", ".solcover.js", - "hardhat*.config.ts" + "hardhat.build.config.ts", + "hardhat.config.ts" ] } From 8bb04bb41f2d35b06d6c143d34cee318d5bcd707 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Santiago=20Ace=C3=B1olaza?= Date: Mon, 26 May 2025 19:15:18 -0300 Subject: [PATCH 08/19] Adds hardhat-verify to hardhat-deploy scripts --- deploy/001_deploy_InverseApi3ReaderProxyV1.ts | 34 ++++++++++--- .../002_deploy_NormalizedApi3ReaderProxyV1.ts | 34 ++++++++++--- deploy/003_deploy_ProductApi3ReaderProxyV1.ts | 34 ++++++++++--- deploy/004_deploy_ScaledApi3FeedProxyV1.ts | 34 ++++++++++--- example.env | 48 +++++++++++++++++++ hardhat.config.ts | 2 + package.json | 2 + pnpm-lock.yaml | 36 +++++++++----- 8 files changed, 184 insertions(+), 40 deletions(-) create mode 100644 example.env diff --git a/deploy/001_deploy_InverseApi3ReaderProxyV1.ts b/deploy/001_deploy_InverseApi3ReaderProxyV1.ts index b140cec..bdcb658 100644 --- a/deploy/001_deploy_InverseApi3ReaderProxyV1.ts +++ b/deploy/001_deploy_InverseApi3ReaderProxyV1.ts @@ -1,6 +1,9 @@ import type { HardhatRuntimeEnvironment } from 'hardhat/types'; -module.exports = async ({ getUnnamedAccounts, deployments, ethers }: HardhatRuntimeEnvironment) => { +const VERIFICATION_BLOCK_CONFIRMATIONS = 5; + +module.exports = async (hre: HardhatRuntimeEnvironment) => { + const { getUnnamedAccounts, deployments, ethers, network, run } = hre; const { deploy, log } = deployments; const [deployerAddress] = await getUnnamedAccounts(); @@ -18,12 +21,29 @@ module.exports = async ({ getUnnamedAccounts, deployments, ethers }: HardhatRunt } log(`Proxy address: ${proxyAddress}`); - await deployments.get('InverseApi3ReaderProxyV1').catch(async () => { - return deploy('InverseApi3ReaderProxyV1', { - from: deployerAddress, - args: [proxyAddress], - log: true, - }); + const isLocalNetwork = network.name === 'hardhat' || network.name === 'localhost'; + + const confirmations = isLocalNetwork ? 1 : VERIFICATION_BLOCK_CONFIRMATIONS; + log(`Deployment confirmations: ${confirmations}`); + + const contractName = 'InverseApi3ReaderProxyV1'; + + const deployment = await deploy(contractName, { + from: deployerAddress, + args: [proxyAddress], + log: true, + waitConfirmations: confirmations, + }); + + if (isLocalNetwork) { + log('Skipping verification on local network.'); + return; + } + + log(`Attempting verification of ${contractName} (already waited for confirmations)...`); + await run('verify:verify', { + address: deployment.address, + constructorArguments: deployment.args, }); }; module.exports.tags = ['InverseApi3ReaderProxyV1']; diff --git a/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts b/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts index 24b9832..6220cb9 100644 --- a/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts +++ b/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts @@ -1,6 +1,8 @@ import type { HardhatRuntimeEnvironment } from 'hardhat/types'; import type { DeploymentsExtension } from 'hardhat-deploy/types'; +const VERIFICATION_BLOCK_CONFIRMATIONS = 5; + const deployTestFeed = async (deployments: DeploymentsExtension, deployerAddress: string) => { const { address: scaledApi3FeedProxyV1Address } = await deployments.get('ScaledApi3FeedProxyV1').catch(async () => { return deployments.deploy('ScaledApi3FeedProxyV1', { @@ -12,7 +14,8 @@ const deployTestFeed = async (deployments: DeploymentsExtension, deployerAddress return scaledApi3FeedProxyV1Address; }; -module.exports = async ({ getUnnamedAccounts, deployments, network, ethers }: HardhatRuntimeEnvironment) => { +module.exports = async (hre: HardhatRuntimeEnvironment) => { + const { getUnnamedAccounts, deployments, network, ethers, run } = hre; const { deploy, log } = deployments; const [deployerAddress] = await getUnnamedAccounts(); @@ -33,12 +36,29 @@ module.exports = async ({ getUnnamedAccounts, deployments, network, ethers }: Ha } log(`Feed address: ${feedAddress}`); - await deployments.get('NormalizedApi3ReaderProxyV1').catch(async () => { - return deploy('NormalizedApi3ReaderProxyV1', { - from: deployerAddress, - args: [feedAddress], - log: true, - }); + const isLocalNetwork = network.name === 'hardhat' || network.name === 'localhost'; + + const confirmations = isLocalNetwork ? 1 : VERIFICATION_BLOCK_CONFIRMATIONS; + log(`Deployment confirmations: ${confirmations}`); + + const contractName = 'NormalizedApi3ReaderProxyV1'; + + const deployment = await deploy(contractName, { + from: deployerAddress, + args: [feedAddress], + log: true, + waitConfirmations: confirmations, + }); + + if (isLocalNetwork) { + log('Skipping verification on local network.'); + return; + } + + log(`Attempting verification of ${contractName} (already waited for confirmations)...`); + await run('verify:verify', { + address: deployment.address, + constructorArguments: deployment.args, }); }; module.exports.tags = ['NormalizedApi3ReaderProxyV1']; diff --git a/deploy/003_deploy_ProductApi3ReaderProxyV1.ts b/deploy/003_deploy_ProductApi3ReaderProxyV1.ts index ff633bb..51f23ae 100644 --- a/deploy/003_deploy_ProductApi3ReaderProxyV1.ts +++ b/deploy/003_deploy_ProductApi3ReaderProxyV1.ts @@ -1,6 +1,9 @@ import type { HardhatRuntimeEnvironment } from 'hardhat/types'; -module.exports = async ({ getUnnamedAccounts, deployments, ethers }: HardhatRuntimeEnvironment) => { +const VERIFICATION_BLOCK_CONFIRMATIONS = 5; + +module.exports = async (hre: HardhatRuntimeEnvironment) => { + const { getUnnamedAccounts, deployments, ethers, network, run } = hre; const { deploy, log } = deployments; const [deployerAddress] = await getUnnamedAccounts(); @@ -27,12 +30,29 @@ module.exports = async ({ getUnnamedAccounts, deployments, ethers }: HardhatRunt } log(`Proxy 2 address: ${proxy2Address}`); - await deployments.get('ProductApi3ReaderProxyV1').catch(async () => { - return deploy('ProductApi3ReaderProxyV1', { - from: deployerAddress, - args: [proxy1Address, proxy2Address], - log: true, - }); + const isLocalNetwork = network.name === 'hardhat' || network.name === 'localhost'; + + const confirmations = isLocalNetwork ? 1 : VERIFICATION_BLOCK_CONFIRMATIONS; + log(`Deployment confirmations: ${confirmations}`); + + const contractName = 'ProductApi3ReaderProxyV1'; + + const deployment = await deploy(contractName, { + from: deployerAddress, + args: [proxy1Address, proxy2Address], + log: true, + waitConfirmations: confirmations, + }); + + if (isLocalNetwork) { + log('Skipping verification on local network.'); + return; + } + + log(`Attempting verification of ${contractName} (already waited for confirmations)...`); + await run('verify:verify', { + address: deployment.address, + constructorArguments: deployment.args, }); }; module.exports.tags = ['ProductApi3ReaderProxyV1']; diff --git a/deploy/004_deploy_ScaledApi3FeedProxyV1.ts b/deploy/004_deploy_ScaledApi3FeedProxyV1.ts index 2520c3f..3e22351 100644 --- a/deploy/004_deploy_ScaledApi3FeedProxyV1.ts +++ b/deploy/004_deploy_ScaledApi3FeedProxyV1.ts @@ -1,6 +1,8 @@ import type { HardhatRuntimeEnvironment } from 'hardhat/types'; import type { DeploymentsExtension } from 'hardhat-deploy/types'; +const VERIFICATION_BLOCK_CONFIRMATIONS = 5; + const deployTestProxy = async (deployments: DeploymentsExtension, deployerAddress: string) => { const { address: inverseApi3ReaderProxyV1Address } = await deployments .get('InverseApi3ReaderProxyV1') @@ -14,7 +16,8 @@ const deployTestProxy = async (deployments: DeploymentsExtension, deployerAddres return inverseApi3ReaderProxyV1Address; }; -module.exports = async ({ getUnnamedAccounts, deployments, network, ethers }: HardhatRuntimeEnvironment) => { +module.exports = async (hre: HardhatRuntimeEnvironment) => { + const { getUnnamedAccounts, deployments, network, ethers, run } = hre; const { deploy, log } = deployments; const [deployerAddress] = await getUnnamedAccounts(); @@ -39,12 +42,29 @@ module.exports = async ({ getUnnamedAccounts, deployments, network, ethers }: Ha } log(`Proxy address: ${proxyAddress}`); - await deployments.get('ScaledApi3FeedProxyV1').catch(async () => { - return deploy('ScaledApi3FeedProxyV1', { - from: deployerAddress, - args: [proxyAddress, decimals], - log: true, - }); + const isLocalNetwork = network.name === 'hardhat' || network.name === 'localhost'; + + const confirmations = isLocalNetwork ? 1 : VERIFICATION_BLOCK_CONFIRMATIONS; + log(`Deployment confirmations: ${confirmations}`); + + const contractName = 'ScaledApi3FeedProxyV1'; + + const deployment = await deploy(contractName, { + from: deployerAddress, + args: [proxyAddress, decimals], + log: true, + waitConfirmations: confirmations, + }); + + if (isLocalNetwork) { + log('Skipping verification on local network.'); + return; + } + + log(`Attempting verification of ${contractName} (already waited for confirmations)...`); + await run('verify:verify', { + address: deployment.address, + constructorArguments: deployment.args, }); }; module.exports.tags = ['ScaledApi3FeedProxyV1']; diff --git a/example.env b/example.env new file mode 100644 index 0000000..fdfa646 --- /dev/null +++ b/example.env @@ -0,0 +1,48 @@ +MNEMONIC= +ETHERSCAN_API_KEY_APECHAIN= +ETHERSCAN_API_KEY_ARBITRUM_SEPOLIA_TESTNET= +ETHERSCAN_API_KEY_ARBITRUM= +ETHERSCAN_API_KEY_AVALANCHE_TESTNET= +ETHERSCAN_API_KEY_AVALANCHE= +ETHERSCAN_API_KEY_BASE_SEPOLIA_TESTNET= +ETHERSCAN_API_KEY_BASE= +ETHERSCAN_API_KEY_BERACHAIN= +ETHERSCAN_API_KEY_BLAST_SEPOLIA_TESTNET= +ETHERSCAN_API_KEY_BLAST= +ETHERSCAN_API_KEY_BSC_TESTNET= +ETHERSCAN_API_KEY_BSC= +ETHERSCAN_API_KEY_CORE_TESTNET= +ETHERSCAN_API_KEY_CORE= +ETHERSCAN_API_KEY_ETHEREUM_HOLESKY_TESTNET= +ETHERSCAN_API_KEY_ETHEREUM_SEPOLIA_TESTNET= +ETHERSCAN_API_KEY_ETHEREUM= +ETHERSCAN_API_KEY_FRAXTAL_HOLESKY_TESTNET= +ETHERSCAN_API_KEY_FRAXTAL= +ETHERSCAN_API_KEY_GNOSIS= +ETHERSCAN_API_KEY_KROMA_SEPOLIA_TESTNET= +ETHERSCAN_API_KEY_LINEA_SEPOLIA_TESTNET= +ETHERSCAN_API_KEY_LINEA= +ETHERSCAN_API_KEY_MANTLE_SEPOLIA_TESTNET= +ETHERSCAN_API_KEY_MANTLE= +ETHERSCAN_API_KEY_MOONBEAM_TESTNET= +ETHERSCAN_API_KEY_MOONBEAM= +ETHERSCAN_API_KEY_MOONRIVER= +ETHERSCAN_API_KEY_OPBNB_TESTNET= +ETHERSCAN_API_KEY_OPBNB= +ETHERSCAN_API_KEY_OPTIMISM_SEPOLIA_TESTNET= +ETHERSCAN_API_KEY_OPTIMISM= +ETHERSCAN_API_KEY_POLYGON_SEPOLIA_TESTNET= +ETHERSCAN_API_KEY_POLYGON_ZKEVM_SEPOLIA_TESTNET= +ETHERSCAN_API_KEY_POLYGON_ZKEVM= +ETHERSCAN_API_KEY_POLYGON= +ETHERSCAN_API_KEY_SCROLL_SEPOLIA_TESTNET= +ETHERSCAN_API_KEY_SCROLL= +ETHERSCAN_API_KEY_SONIC_TESTNET= +ETHERSCAN_API_KEY_SONIC= +ETHERSCAN_API_KEY_TAIKO_HOLESKY_TESTNET= +ETHERSCAN_API_KEY_TAIKO= +ETHERSCAN_API_KEY_UNICHAIN_SEPOLIA_TESTNET= +ETHERSCAN_API_KEY_UNICHAIN= +ETHERSCAN_API_KEY_WORLD= +ETHERSCAN_API_KEY_ZIRCUIT_SEPOLIA_TESTNET= +ETHERSCAN_API_KEY_ZIRCUIT= diff --git a/hardhat.config.ts b/hardhat.config.ts index 21f0325..ad8ce39 100644 --- a/hardhat.config.ts +++ b/hardhat.config.ts @@ -1,6 +1,8 @@ import { hardhatConfig } from '@api3/contracts'; import '@nomicfoundation/hardhat-toolbox'; +import '@nomicfoundation/hardhat-verify'; import 'hardhat-deploy'; +import 'dotenv/config'; import type { HardhatUserConfig } from 'hardhat/config'; const config: HardhatUserConfig = { diff --git a/package.json b/package.json index e1670c4..e82b979 100644 --- a/package.json +++ b/package.json @@ -42,12 +42,14 @@ "@nomicfoundation/hardhat-ethers": "^3.0.8", "@nomicfoundation/hardhat-network-helpers": "^1.0.12", "@nomicfoundation/hardhat-toolbox": "^5.0.0", + "@nomicfoundation/hardhat-verify": "^2.0.14", "@types/chai": "^4.3.20", "@types/mocha": "^10.0.10", "@types/node": "^22.15.18", "@typescript-eslint/eslint-plugin": "^7.18.0", "@typescript-eslint/parser": "^7.18.0", "chai": "^4.5.0", + "dotenv": "^16.5.0", "eslint": "8.57.1", "ethers": "^6.13.2", "glob": "^11.0.2", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 2dc24b0..0192416 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -25,7 +25,10 @@ importers: version: 1.0.12(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) '@nomicfoundation/hardhat-toolbox': specifier: ^5.0.0 - version: 5.0.0(a6kpgdsxfxicrejf26ezaasetm) + version: 5.0.0(zs46phtpxu4vedqxmqwrnkrgcu) + '@nomicfoundation/hardhat-verify': + specifier: ^2.0.14 + version: 2.0.14(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) '@types/chai': specifier: ^4.3.20 version: 4.3.20 @@ -44,6 +47,9 @@ importers: chai: specifier: ^4.5.0 version: 4.5.0 + dotenv: + specifier: ^16.5.0 + version: 16.5.0 eslint: specifier: 8.57.1 version: 8.57.1 @@ -520,10 +526,10 @@ packages: typechain: ^8.3.0 typescript: '>=4.5.0' - '@nomicfoundation/hardhat-verify@2.0.13': - resolution: {integrity: sha512-i57GX1sC0kYGyRVnbQrjjyBTpWTKgrvKC+jH8CMKV6gHp959Upb8lKaZ58WRHIU0espkulTxLnacYeUDirwJ2g==} + '@nomicfoundation/hardhat-verify@2.0.14': + resolution: {integrity: sha512-z3iVF1WYZHzcdMMUuureFpSAfcnlfJbJx3faOnGrOYg6PRTki1Ut9JAuRccnFzMHf1AmTEoSUpWcyvBCoxL5Rg==} peerDependencies: - hardhat: ^2.0.4 + hardhat: ^2.24.1 '@nomicfoundation/ignition-core@0.15.11': resolution: {integrity: sha512-PeYKRlrQ0koT72yRnlyyG66cXMFiv5X/cIB8hBFPl3ekeg5tPXcHAgs/VZhOsgwEox4ejphTtItLESb1IDBw0w==} @@ -1548,6 +1554,10 @@ packages: dot-case@3.0.4: resolution: {integrity: sha512-Kv5nKlh6yRrdrGvxeJ2e5y2eRUpkUosIW4A2AS38zwSz27zu7ufDwQPi5Jhs3XAlGNetl3bmnGhQsMtkKJnj3w==} + dotenv@16.5.0: + resolution: {integrity: sha512-m/C+AwOAr9/W1UOIZUo232ejMNnJAJtYQjUbHoNTBNTJSvqzzDh7vnrei3o3r3m9blf6ZoDkvcw0VmozNRFJxg==} + engines: {node: '>=12'} + dunder-proto@1.0.1: resolution: {integrity: sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==} engines: {node: '>= 0.4'} @@ -4551,17 +4561,17 @@ snapshots: transitivePeerDependencies: - supports-color - '@nomicfoundation/hardhat-ignition-ethers@0.15.11(@nomicfoundation/hardhat-ethers@3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/hardhat-ignition@0.15.11(@nomicfoundation/hardhat-verify@2.0.13(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/ignition-core@0.15.11)(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))': + '@nomicfoundation/hardhat-ignition-ethers@0.15.11(@nomicfoundation/hardhat-ethers@3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/hardhat-ignition@0.15.11(@nomicfoundation/hardhat-verify@2.0.14(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/ignition-core@0.15.11)(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))': dependencies: '@nomicfoundation/hardhat-ethers': 3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) - '@nomicfoundation/hardhat-ignition': 0.15.11(@nomicfoundation/hardhat-verify@2.0.13(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) + '@nomicfoundation/hardhat-ignition': 0.15.11(@nomicfoundation/hardhat-verify@2.0.14(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) '@nomicfoundation/ignition-core': 0.15.11 ethers: 6.13.2 hardhat: 2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3) - '@nomicfoundation/hardhat-ignition@0.15.11(@nomicfoundation/hardhat-verify@2.0.13(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))': + '@nomicfoundation/hardhat-ignition@0.15.11(@nomicfoundation/hardhat-verify@2.0.14(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))': dependencies: - '@nomicfoundation/hardhat-verify': 2.0.13(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) + '@nomicfoundation/hardhat-verify': 2.0.14(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) '@nomicfoundation/ignition-core': 0.15.11 '@nomicfoundation/ignition-ui': 0.15.11 chalk: 4.1.2 @@ -4580,13 +4590,13 @@ snapshots: ethereumjs-util: 7.1.5 hardhat: 2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3) - '@nomicfoundation/hardhat-toolbox@5.0.0(a6kpgdsxfxicrejf26ezaasetm)': + '@nomicfoundation/hardhat-toolbox@5.0.0(zs46phtpxu4vedqxmqwrnkrgcu)': dependencies: '@nomicfoundation/hardhat-chai-matchers': 2.0.8(@nomicfoundation/hardhat-ethers@3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(chai@4.5.0)(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) '@nomicfoundation/hardhat-ethers': 3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) - '@nomicfoundation/hardhat-ignition-ethers': 0.15.11(@nomicfoundation/hardhat-ethers@3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/hardhat-ignition@0.15.11(@nomicfoundation/hardhat-verify@2.0.13(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/ignition-core@0.15.11)(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) + '@nomicfoundation/hardhat-ignition-ethers': 0.15.11(@nomicfoundation/hardhat-ethers@3.0.8(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/hardhat-ignition@0.15.11(@nomicfoundation/hardhat-verify@2.0.14(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)))(@nomicfoundation/ignition-core@0.15.11)(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) '@nomicfoundation/hardhat-network-helpers': 1.0.12(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) - '@nomicfoundation/hardhat-verify': 2.0.13(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) + '@nomicfoundation/hardhat-verify': 2.0.14(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3)) '@typechain/ethers-v6': 0.5.1(ethers@6.13.2)(typechain@8.3.2(typescript@5.8.3))(typescript@5.8.3) '@typechain/hardhat': 9.1.0(@typechain/ethers-v6@0.5.1(ethers@6.13.2)(typechain@8.3.2(typescript@5.8.3))(typescript@5.8.3))(ethers@6.13.2)(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))(typechain@8.3.2(typescript@5.8.3)) '@types/chai': 4.3.20 @@ -4601,7 +4611,7 @@ snapshots: typechain: 8.3.2(typescript@5.8.3) typescript: 5.8.3 - '@nomicfoundation/hardhat-verify@2.0.13(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))': + '@nomicfoundation/hardhat-verify@2.0.14(hardhat@2.24.0(ts-node@10.9.2(@types/node@22.15.18)(typescript@5.8.3))(typescript@5.8.3))': dependencies: '@ethersproject/abi': 5.8.0 '@ethersproject/address': 5.8.0 @@ -5769,6 +5779,8 @@ snapshots: no-case: 3.0.4 tslib: 2.8.1 + dotenv@16.5.0: {} + dunder-proto@1.0.1: dependencies: call-bind-apply-helpers: 1.0.2 From c59f5ddbba090c260b5fed01168252bdf970e1c9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Santiago=20Ace=C3=B1olaza?= Date: Tue, 27 May 2025 16:13:13 -0300 Subject: [PATCH 09/19] Derives a hash for each deployment name and adds a script to generate addresses.json --- deploy/001_deploy_InverseApi3ReaderProxyV1.ts | 16 ++++- .../002_deploy_NormalizedApi3ReaderProxyV1.ts | 16 ++++- deploy/003_deploy_ProductApi3ReaderProxyV1.ts | 16 ++++- deploy/004_deploy_ScaledApi3FeedProxyV1.ts | 16 ++++- deployments/addresses.json | 1 + package.json | 1 + scripts/generate-deployment-addresses.ts | 16 +++++ scripts/src/deployment-addresses.ts | 64 +++++++++++++++++++ scripts/verify-vendor-contracts.ts | 2 +- src/deployment.ts | 21 ++++++ src/index.ts | 1 + 11 files changed, 157 insertions(+), 13 deletions(-) create mode 100644 deployments/addresses.json create mode 100644 scripts/generate-deployment-addresses.ts create mode 100644 scripts/src/deployment-addresses.ts create mode 100644 src/deployment.ts diff --git a/deploy/001_deploy_InverseApi3ReaderProxyV1.ts b/deploy/001_deploy_InverseApi3ReaderProxyV1.ts index bdcb658..812ee7a 100644 --- a/deploy/001_deploy_InverseApi3ReaderProxyV1.ts +++ b/deploy/001_deploy_InverseApi3ReaderProxyV1.ts @@ -1,5 +1,7 @@ import type { HardhatRuntimeEnvironment } from 'hardhat/types'; +import { getDeploymentName } from '../src'; + const VERIFICATION_BLOCK_CONFIRMATIONS = 5; module.exports = async (hre: HardhatRuntimeEnvironment) => { @@ -27,10 +29,16 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { log(`Deployment confirmations: ${confirmations}`); const contractName = 'InverseApi3ReaderProxyV1'; + const constructorArgs = [proxyAddress]; + const constructorArgTypes = ['address']; + + const deploymentName = getDeploymentName(contractName, constructorArgTypes, constructorArgs); + log(`Generated deterministic deployment name for this instance: ${deploymentName}`); - const deployment = await deploy(contractName, { + const deployment = await deploy(deploymentName, { + contract: contractName, from: deployerAddress, - args: [proxyAddress], + args: constructorArgs, log: true, waitConfirmations: confirmations, }); @@ -40,7 +48,9 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { return; } - log(`Attempting verification of ${contractName} (already waited for confirmations)...`); + log( + `Attempting verification of ${deploymentName} (contract type ${contractName}) at ${deployment.address} (already waited for confirmations)...` + ); await run('verify:verify', { address: deployment.address, constructorArguments: deployment.args, diff --git a/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts b/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts index 6220cb9..f8eacbf 100644 --- a/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts +++ b/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts @@ -3,6 +3,8 @@ import type { DeploymentsExtension } from 'hardhat-deploy/types'; const VERIFICATION_BLOCK_CONFIRMATIONS = 5; +import { getDeploymentName } from '../src'; + const deployTestFeed = async (deployments: DeploymentsExtension, deployerAddress: string) => { const { address: scaledApi3FeedProxyV1Address } = await deployments.get('ScaledApi3FeedProxyV1').catch(async () => { return deployments.deploy('ScaledApi3FeedProxyV1', { @@ -42,10 +44,16 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { log(`Deployment confirmations: ${confirmations}`); const contractName = 'NormalizedApi3ReaderProxyV1'; + const constructorArgs = [feedAddress]; + const constructorArgTypes = ['address']; + + const deploymentName = getDeploymentName(contractName, constructorArgTypes, constructorArgs); + log(`Generated deterministic deployment name for this instance: ${deploymentName}`); - const deployment = await deploy(contractName, { + const deployment = await deploy(deploymentName, { + contract: contractName, from: deployerAddress, - args: [feedAddress], + args: constructorArgs, log: true, waitConfirmations: confirmations, }); @@ -55,7 +63,9 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { return; } - log(`Attempting verification of ${contractName} (already waited for confirmations)...`); + log( + `Attempting verification of ${deploymentName} (contract type ${contractName}) at ${deployment.address} (already waited for confirmations)...` + ); await run('verify:verify', { address: deployment.address, constructorArguments: deployment.args, diff --git a/deploy/003_deploy_ProductApi3ReaderProxyV1.ts b/deploy/003_deploy_ProductApi3ReaderProxyV1.ts index 51f23ae..58495ed 100644 --- a/deploy/003_deploy_ProductApi3ReaderProxyV1.ts +++ b/deploy/003_deploy_ProductApi3ReaderProxyV1.ts @@ -1,5 +1,7 @@ import type { HardhatRuntimeEnvironment } from 'hardhat/types'; +import { getDeploymentName } from '../src'; + const VERIFICATION_BLOCK_CONFIRMATIONS = 5; module.exports = async (hre: HardhatRuntimeEnvironment) => { @@ -36,10 +38,16 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { log(`Deployment confirmations: ${confirmations}`); const contractName = 'ProductApi3ReaderProxyV1'; + const constructorArgs = [proxy1Address, proxy2Address]; + const constructorArgTypes = ['address', 'address']; + + const deploymentName = getDeploymentName(contractName, constructorArgTypes, constructorArgs); + log(`Generated deterministic deployment name for this instance: ${deploymentName}`); - const deployment = await deploy(contractName, { + const deployment = await deploy(deploymentName, { + contract: contractName, from: deployerAddress, - args: [proxy1Address, proxy2Address], + args: constructorArgs, log: true, waitConfirmations: confirmations, }); @@ -49,7 +57,9 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { return; } - log(`Attempting verification of ${contractName} (already waited for confirmations)...`); + log( + `Attempting verification of ${deploymentName} (contract type ${contractName}) at ${deployment.address} (already waited for confirmations)...` + ); await run('verify:verify', { address: deployment.address, constructorArguments: deployment.args, diff --git a/deploy/004_deploy_ScaledApi3FeedProxyV1.ts b/deploy/004_deploy_ScaledApi3FeedProxyV1.ts index 3e22351..0adb74b 100644 --- a/deploy/004_deploy_ScaledApi3FeedProxyV1.ts +++ b/deploy/004_deploy_ScaledApi3FeedProxyV1.ts @@ -3,6 +3,8 @@ import type { DeploymentsExtension } from 'hardhat-deploy/types'; const VERIFICATION_BLOCK_CONFIRMATIONS = 5; +import { getDeploymentName } from '../src'; + const deployTestProxy = async (deployments: DeploymentsExtension, deployerAddress: string) => { const { address: inverseApi3ReaderProxyV1Address } = await deployments .get('InverseApi3ReaderProxyV1') @@ -48,10 +50,16 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { log(`Deployment confirmations: ${confirmations}`); const contractName = 'ScaledApi3FeedProxyV1'; + const constructorArgs = [proxyAddress, decimals]; + const constructorArgTypes = ['address', 'uint8']; + + const deploymentName = getDeploymentName(contractName, constructorArgTypes, constructorArgs); + log(`Generated deterministic deployment name for this instance: ${deploymentName}`); - const deployment = await deploy(contractName, { + const deployment = await deploy(deploymentName, { + contract: contractName, from: deployerAddress, - args: [proxyAddress, decimals], + args: constructorArgs, log: true, waitConfirmations: confirmations, }); @@ -61,7 +69,9 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { return; } - log(`Attempting verification of ${contractName} (already waited for confirmations)...`); + log( + `Attempting verification of ${deploymentName} (contract type ${contractName}) at ${deployment.address} (already waited for confirmations)...` + ); await run('verify:verify', { address: deployment.address, constructorArguments: deployment.args, diff --git a/deployments/addresses.json b/deployments/addresses.json new file mode 100644 index 0000000..0967ef4 --- /dev/null +++ b/deployments/addresses.json @@ -0,0 +1 @@ +{} diff --git a/package.json b/package.json index e82b979..cf9fbbd 100644 --- a/package.json +++ b/package.json @@ -27,6 +27,7 @@ "deploy:NormalizedApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags NormalizedApi3ReaderProxyV1", "deploy:ProductApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags ProductApi3ReaderProxyV1", "deploy:ScaledApi3FeedProxyV1": "hardhat deploy --network $NETWORK --tags ScaledApi3FeedProxyV1", + "generate:deployment-addresses": "ts-node scripts/generate-deployment-addresses.ts", "lint": "pnpm run prettier:check && pnpm run lint:eslint && pnpm run lint:solhint", "lint:solhint": "solhint ./contracts/**/*.sol", "lint:eslint": "eslint . --ext .js,.ts", diff --git a/scripts/generate-deployment-addresses.ts b/scripts/generate-deployment-addresses.ts new file mode 100644 index 0000000..6fe4409 --- /dev/null +++ b/scripts/generate-deployment-addresses.ts @@ -0,0 +1,16 @@ +import * as fs from 'node:fs'; +import { join } from 'node:path'; + +import { getDeploymentAddresses } from './src/deployment-addresses'; + +async function main(): Promise { + fs.writeFileSync(join('deployments', 'addresses.json'), getDeploymentAddresses()); +} + +main() + .then(() => process.exit(0)) + .catch((error) => { + // eslint-disable-next-line no-console + console.error(error); + process.exit(1); + }); diff --git a/scripts/src/deployment-addresses.ts b/scripts/src/deployment-addresses.ts new file mode 100644 index 0000000..58dbfd7 --- /dev/null +++ b/scripts/src/deployment-addresses.ts @@ -0,0 +1,64 @@ +import * as fs from 'node:fs'; +import { join, parse as parsePath } from 'node:path'; + +import type { AddressLike } from 'ethers'; + +export interface DeploymentAddressEntry { + address: AddressLike; + constructorArgs?: any[]; + constructorArgTypes?: string[]; +} + +export interface ChainDeploymentAddresses { + [chainId: string]: DeploymentAddressEntry; +} + +export interface AllDeploymentAddresses { + [deploymentName: string]: ChainDeploymentAddresses; +} + +/** + * Reads deployment artifacts from the `deployments` directory (specific to data-feed-proxy-combinators) + * and aggregates contract addresses, constructor arguments, and types by deployment name and chain ID. + * @returns A stringified JSON object of deployment addresses. + */ +export function getDeploymentAddresses(): string { + const allAddresses: AllDeploymentAddresses = {}; + const deploymentsRoot = join(__dirname, '..', '..', 'deployments'); + + if (!fs.existsSync(deploymentsRoot)) { + throw new Error(`Deployments directory not found at ${deploymentsRoot}.`); + } + + const networkDirs = fs + .readdirSync(deploymentsRoot, { withFileTypes: true }) + .filter((dirent) => dirent.isDirectory() && dirent.name !== 'localhost' && dirent.name !== 'hardhat') + .map((dirent) => dirent.name); + + for (const networkName of networkDirs) { + const networkPath = join(deploymentsRoot, networkName); + const chainIdFilePath = join(networkPath, '.chainId'); + if (!fs.existsSync(chainIdFilePath)) continue; + const chainId = fs.readFileSync(chainIdFilePath, 'utf8').trim(); + + const deploymentFiles = fs + .readdirSync(networkPath, { withFileTypes: true }) + .filter((dirent) => dirent.isFile() && dirent.name.endsWith('.json')) + .map((dirent) => dirent.name); + + for (const deploymentFile of deploymentFiles) { + const deploymentName = parsePath(deploymentFile).name; + const artifact = JSON.parse(fs.readFileSync(join(networkPath, deploymentFile), 'utf8')); + const constructorEntry = artifact.abi.find((item: any) => item.type === 'constructor'); + const constructorArgTypes = constructorEntry?.inputs?.map((input: any) => input.type) || []; + + if (!allAddresses[deploymentName]) allAddresses[deploymentName] = {}; + allAddresses[deploymentName][chainId] = { + address: artifact.address, + constructorArgs: artifact.args || [], + constructorArgTypes, + }; + } + } + return `${JSON.stringify(allAddresses, null, 2)}\n`; +} diff --git a/scripts/verify-vendor-contracts.ts b/scripts/verify-vendor-contracts.ts index 0b510f2..bed5c4e 100644 --- a/scripts/verify-vendor-contracts.ts +++ b/scripts/verify-vendor-contracts.ts @@ -43,10 +43,10 @@ async function main() { } } -/* eslint-disable */ main() .then(() => process.exit(0)) .catch((error) => { + // eslint-disable-next-line no-console console.log(error); process.exit(1); }); diff --git a/src/deployment.ts b/src/deployment.ts new file mode 100644 index 0000000..07e0ab0 --- /dev/null +++ b/src/deployment.ts @@ -0,0 +1,21 @@ +import { ethers } from 'ethers'; + +/** + * Creates a deterministic deployment name based on a base name and constructor arguments. + * @param baseName The base name for the contract (e.g., 'ProductApi3ReaderProxyV1'). + * @param constructorArgTypes Array of Solidity types for the constructor arguments. + * @param constructorArgs Array of actual constructor argument values. + * @returns A deterministic deployment name string. + */ +export const getDeploymentName = (baseName: string, constructorArgTypes: string[], constructorArgs: any[]): string => { + // Ensure addresses are checksummed for consistent ABI encoding + const processedArgs = constructorArgs.map((arg, index) => { + if (constructorArgTypes[index] === 'address' && typeof arg === 'string' && ethers.isAddress(arg)) { + return ethers.getAddress(arg); // Ensures checksum + } + return arg; + }); + const encodedArgs = ethers.AbiCoder.defaultAbiCoder().encode(constructorArgTypes, processedArgs); + const argsHash = ethers.keccak256(encodedArgs).slice(2, 10); // Use a short 8-char hex hash (e.g., 'a1b2c3d4') + return `${baseName}_${argsHash}`; +}; diff --git a/src/index.ts b/src/index.ts index 1eba20f..1fce1e9 100644 --- a/src/index.ts +++ b/src/index.ts @@ -1 +1,2 @@ +export * from './deployment'; export * from '../typechain-types'; From 7b5bcfd24b849880c70180168f9ea2f40769a19f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Santiago=20Ace=C3=B1olaza?= Date: Tue, 27 May 2025 16:52:31 -0300 Subject: [PATCH 10/19] Adds check-deployment-addresses.ts script --- package.json | 1 + scripts/check-deployment-addresses.ts | 29 +++++++++++++++++++++++++++ 2 files changed, 30 insertions(+) create mode 100644 scripts/check-deployment-addresses.ts diff --git a/package.json b/package.json index cf9fbbd..2772a52 100644 --- a/package.json +++ b/package.json @@ -23,6 +23,7 @@ "scripts": { "build": "pnpm build:hardhat && tsc -p tsconfig.build.json", "build:hardhat": "hardhat --config hardhat.build.config.ts compile", + "check:deployment-addresses": "ts-node scripts/check-deployment-addresses.ts", "deploy:InverseApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags InverseApi3ReaderProxyV1", "deploy:NormalizedApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags NormalizedApi3ReaderProxyV1", "deploy:ProductApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags ProductApi3ReaderProxyV1", diff --git a/scripts/check-deployment-addresses.ts b/scripts/check-deployment-addresses.ts new file mode 100644 index 0000000..c23fc69 --- /dev/null +++ b/scripts/check-deployment-addresses.ts @@ -0,0 +1,29 @@ +import * as fs from 'node:fs'; +import { join } from 'node:path'; + +import { getDeploymentAddresses } from './src/deployment-addresses'; + +async function main(): Promise { + const addressesJsonPath = join('deployments', 'addresses.json'); + const existingAddressesJsonString = fs.existsSync(addressesJsonPath) + ? fs.readFileSync(addressesJsonPath, 'utf8') + : '{}'; + + const generatedAddressesJsonString = getDeploymentAddresses(); + + // Normalize by parsing and re-stringifying to ensure consistent formatting for comparison + const normalizedExisting = `${JSON.stringify(JSON.parse(existingAddressesJsonString), null, 2)}\n`; + const normalizedGenerated = `${JSON.stringify(JSON.parse(generatedAddressesJsonString), null, 2)}\n`; + + if (normalizedExisting !== normalizedGenerated) { + throw new Error(`${addressesJsonPath} is outdated. Please run "pnpm generate:deployment-addresses".`); + } +} + +main() + .then(() => process.exit(0)) + .catch((error) => { + // eslint-disable-next-line no-console + console.error(error); + process.exit(1); + }); From abeb3102ba0063c59c56002d75cac12a6e2c2153 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Santiago=20Ace=C3=B1olaza?= Date: Tue, 27 May 2025 16:55:47 -0300 Subject: [PATCH 11/19] Adds husky with a pre-push githook that checks addresses.json --- .husky/pre-push | 1 + package.json | 2 ++ pnpm-lock.yaml | 10 ++++++++++ 3 files changed, 13 insertions(+) create mode 100644 .husky/pre-push diff --git a/.husky/pre-push b/.husky/pre-push new file mode 100644 index 0000000..ecb6d11 --- /dev/null +++ b/.husky/pre-push @@ -0,0 +1 @@ +pnpm check:deployment-addresses \ No newline at end of file diff --git a/package.json b/package.json index 2772a52..a8c51d5 100644 --- a/package.json +++ b/package.json @@ -32,6 +32,7 @@ "lint": "pnpm run prettier:check && pnpm run lint:eslint && pnpm run lint:solhint", "lint:solhint": "solhint ./contracts/**/*.sol", "lint:eslint": "eslint . --ext .js,.ts", + "prepare": "husky", "prettier:check": "prettier --check \"./**/*.{js,ts,md,json,sol}\"", "prettier": "prettier --write \"./**/*.{js,ts,md,json,sol}\"", "verify-vendor-contracts": "hardhat run scripts/verify-vendor-contracts.ts", @@ -57,6 +58,7 @@ "glob": "^11.0.2", "hardhat": "^2.24.0", "hardhat-deploy": "^1.0.2", + "husky": "^9.1.7", "prettier": "^3.5.3", "prettier-plugin-solidity": "^2.0.0", "solhint": "^5.1.0", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 0192416..ce415e2 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -65,6 +65,9 @@ importers: hardhat-deploy: specifier: ^1.0.2 version: 1.0.2 + husky: + specifier: ^9.1.7 + version: 9.1.7 prettier: specifier: ^3.5.3 version: 3.5.3 @@ -2313,6 +2316,11 @@ packages: resolution: {integrity: sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA==} engines: {node: '>= 6'} + husky@9.1.7: + resolution: {integrity: sha512-5gs5ytaNjBrh5Ow3zrvdUUY+0VxIuWVL4i9irt6friV+BqdCfmV11CQTWMiBYWHbXhco+J1kHfTOUkePhCDvMA==} + engines: {node: '>=18'} + hasBin: true + iconv-lite@0.4.24: resolution: {integrity: sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==} engines: {node: '>=0.10.0'} @@ -6959,6 +6967,8 @@ snapshots: transitivePeerDependencies: - supports-color + husky@9.1.7: {} + iconv-lite@0.4.24: dependencies: safer-buffer: 2.1.2 From 9a737e6cd62fa84b559c4225e38b1d3b81c2a14e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Santiago=20Ace=C3=B1olaza?= Date: Tue, 27 May 2025 17:52:40 -0300 Subject: [PATCH 12/19] Moves contract name to module constant in deploy scripts --- deploy/001_deploy_InverseApi3ReaderProxyV1.ts | 13 ++++++------- deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts | 15 +++++++-------- deploy/003_deploy_ProductApi3ReaderProxyV1.ts | 13 ++++++------- deploy/004_deploy_ScaledApi3FeedProxyV1.ts | 15 +++++++-------- 4 files changed, 26 insertions(+), 30 deletions(-) diff --git a/deploy/001_deploy_InverseApi3ReaderProxyV1.ts b/deploy/001_deploy_InverseApi3ReaderProxyV1.ts index 812ee7a..fa169f4 100644 --- a/deploy/001_deploy_InverseApi3ReaderProxyV1.ts +++ b/deploy/001_deploy_InverseApi3ReaderProxyV1.ts @@ -2,7 +2,7 @@ import type { HardhatRuntimeEnvironment } from 'hardhat/types'; import { getDeploymentName } from '../src'; -const VERIFICATION_BLOCK_CONFIRMATIONS = 5; +export const CONTRACT_NAME = 'InverseApi3ReaderProxyV1'; module.exports = async (hre: HardhatRuntimeEnvironment) => { const { getUnnamedAccounts, deployments, ethers, network, run } = hre; @@ -25,18 +25,17 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { const isLocalNetwork = network.name === 'hardhat' || network.name === 'localhost'; - const confirmations = isLocalNetwork ? 1 : VERIFICATION_BLOCK_CONFIRMATIONS; + const confirmations = isLocalNetwork ? 1 : 5; log(`Deployment confirmations: ${confirmations}`); - const contractName = 'InverseApi3ReaderProxyV1'; const constructorArgs = [proxyAddress]; const constructorArgTypes = ['address']; - const deploymentName = getDeploymentName(contractName, constructorArgTypes, constructorArgs); + const deploymentName = getDeploymentName(CONTRACT_NAME, constructorArgTypes, constructorArgs); log(`Generated deterministic deployment name for this instance: ${deploymentName}`); const deployment = await deploy(deploymentName, { - contract: contractName, + contract: CONTRACT_NAME, from: deployerAddress, args: constructorArgs, log: true, @@ -49,11 +48,11 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { } log( - `Attempting verification of ${deploymentName} (contract type ${contractName}) at ${deployment.address} (already waited for confirmations)...` + `Attempting verification of ${deploymentName} (contract type ${CONTRACT_NAME}) at ${deployment.address} (already waited for confirmations)...` ); await run('verify:verify', { address: deployment.address, constructorArguments: deployment.args, }); }; -module.exports.tags = ['InverseApi3ReaderProxyV1']; +module.exports.tags = [CONTRACT_NAME]; diff --git a/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts b/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts index f8eacbf..5f97e81 100644 --- a/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts +++ b/deploy/002_deploy_NormalizedApi3ReaderProxyV1.ts @@ -1,10 +1,10 @@ import type { HardhatRuntimeEnvironment } from 'hardhat/types'; import type { DeploymentsExtension } from 'hardhat-deploy/types'; -const VERIFICATION_BLOCK_CONFIRMATIONS = 5; - import { getDeploymentName } from '../src'; +export const CONTRACT_NAME = 'NormalizedApi3ReaderProxyV1'; + const deployTestFeed = async (deployments: DeploymentsExtension, deployerAddress: string) => { const { address: scaledApi3FeedProxyV1Address } = await deployments.get('ScaledApi3FeedProxyV1').catch(async () => { return deployments.deploy('ScaledApi3FeedProxyV1', { @@ -40,18 +40,17 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { const isLocalNetwork = network.name === 'hardhat' || network.name === 'localhost'; - const confirmations = isLocalNetwork ? 1 : VERIFICATION_BLOCK_CONFIRMATIONS; + const confirmations = isLocalNetwork ? 1 : 5; log(`Deployment confirmations: ${confirmations}`); - const contractName = 'NormalizedApi3ReaderProxyV1'; const constructorArgs = [feedAddress]; const constructorArgTypes = ['address']; - const deploymentName = getDeploymentName(contractName, constructorArgTypes, constructorArgs); + const deploymentName = getDeploymentName(CONTRACT_NAME, constructorArgTypes, constructorArgs); log(`Generated deterministic deployment name for this instance: ${deploymentName}`); const deployment = await deploy(deploymentName, { - contract: contractName, + contract: CONTRACT_NAME, from: deployerAddress, args: constructorArgs, log: true, @@ -64,11 +63,11 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { } log( - `Attempting verification of ${deploymentName} (contract type ${contractName}) at ${deployment.address} (already waited for confirmations)...` + `Attempting verification of ${deploymentName} (contract type ${CONTRACT_NAME}) at ${deployment.address} (already waited for confirmations)...` ); await run('verify:verify', { address: deployment.address, constructorArguments: deployment.args, }); }; -module.exports.tags = ['NormalizedApi3ReaderProxyV1']; +module.exports.tags = [CONTRACT_NAME]; diff --git a/deploy/003_deploy_ProductApi3ReaderProxyV1.ts b/deploy/003_deploy_ProductApi3ReaderProxyV1.ts index 58495ed..189afa1 100644 --- a/deploy/003_deploy_ProductApi3ReaderProxyV1.ts +++ b/deploy/003_deploy_ProductApi3ReaderProxyV1.ts @@ -2,7 +2,7 @@ import type { HardhatRuntimeEnvironment } from 'hardhat/types'; import { getDeploymentName } from '../src'; -const VERIFICATION_BLOCK_CONFIRMATIONS = 5; +export const CONTRACT_NAME = 'ProductApi3ReaderProxyV1'; module.exports = async (hre: HardhatRuntimeEnvironment) => { const { getUnnamedAccounts, deployments, ethers, network, run } = hre; @@ -34,18 +34,17 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { const isLocalNetwork = network.name === 'hardhat' || network.name === 'localhost'; - const confirmations = isLocalNetwork ? 1 : VERIFICATION_BLOCK_CONFIRMATIONS; + const confirmations = isLocalNetwork ? 1 : 5; log(`Deployment confirmations: ${confirmations}`); - const contractName = 'ProductApi3ReaderProxyV1'; const constructorArgs = [proxy1Address, proxy2Address]; const constructorArgTypes = ['address', 'address']; - const deploymentName = getDeploymentName(contractName, constructorArgTypes, constructorArgs); + const deploymentName = getDeploymentName(CONTRACT_NAME, constructorArgTypes, constructorArgs); log(`Generated deterministic deployment name for this instance: ${deploymentName}`); const deployment = await deploy(deploymentName, { - contract: contractName, + contract: CONTRACT_NAME, from: deployerAddress, args: constructorArgs, log: true, @@ -58,11 +57,11 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { } log( - `Attempting verification of ${deploymentName} (contract type ${contractName}) at ${deployment.address} (already waited for confirmations)...` + `Attempting verification of ${deploymentName} (contract type ${CONTRACT_NAME}) at ${deployment.address} (already waited for confirmations)...` ); await run('verify:verify', { address: deployment.address, constructorArguments: deployment.args, }); }; -module.exports.tags = ['ProductApi3ReaderProxyV1']; +module.exports.tags = [CONTRACT_NAME]; diff --git a/deploy/004_deploy_ScaledApi3FeedProxyV1.ts b/deploy/004_deploy_ScaledApi3FeedProxyV1.ts index 0adb74b..da21aee 100644 --- a/deploy/004_deploy_ScaledApi3FeedProxyV1.ts +++ b/deploy/004_deploy_ScaledApi3FeedProxyV1.ts @@ -1,10 +1,10 @@ import type { HardhatRuntimeEnvironment } from 'hardhat/types'; import type { DeploymentsExtension } from 'hardhat-deploy/types'; -const VERIFICATION_BLOCK_CONFIRMATIONS = 5; - import { getDeploymentName } from '../src'; +export const CONTRACT_NAME = 'ScaledApi3FeedProxyV1'; + const deployTestProxy = async (deployments: DeploymentsExtension, deployerAddress: string) => { const { address: inverseApi3ReaderProxyV1Address } = await deployments .get('InverseApi3ReaderProxyV1') @@ -46,18 +46,17 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { const isLocalNetwork = network.name === 'hardhat' || network.name === 'localhost'; - const confirmations = isLocalNetwork ? 1 : VERIFICATION_BLOCK_CONFIRMATIONS; + const confirmations = isLocalNetwork ? 1 : 5; log(`Deployment confirmations: ${confirmations}`); - const contractName = 'ScaledApi3FeedProxyV1'; const constructorArgs = [proxyAddress, decimals]; const constructorArgTypes = ['address', 'uint8']; - const deploymentName = getDeploymentName(contractName, constructorArgTypes, constructorArgs); + const deploymentName = getDeploymentName(CONTRACT_NAME, constructorArgTypes, constructorArgs); log(`Generated deterministic deployment name for this instance: ${deploymentName}`); const deployment = await deploy(deploymentName, { - contract: contractName, + contract: CONTRACT_NAME, from: deployerAddress, args: constructorArgs, log: true, @@ -70,11 +69,11 @@ module.exports = async (hre: HardhatRuntimeEnvironment) => { } log( - `Attempting verification of ${deploymentName} (contract type ${contractName}) at ${deployment.address} (already waited for confirmations)...` + `Attempting verification of ${deploymentName} (contract type ${CONTRACT_NAME}) at ${deployment.address} (already waited for confirmations)...` ); await run('verify:verify', { address: deployment.address, constructorArguments: deployment.args, }); }; -module.exports.tags = ['ScaledApi3FeedProxyV1']; +module.exports.tags = [CONTRACT_NAME]; From d357ad92d8cda4a3ebef8fef1efc899581ceb260 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Santiago=20Ace=C3=B1olaza?= Date: Tue, 27 May 2025 18:31:43 -0300 Subject: [PATCH 13/19] Refactor deployment-addresses.ts --- scripts/src/deployment-addresses.ts | 54 ++++++++++++++++++++++------- 1 file changed, 42 insertions(+), 12 deletions(-) diff --git a/scripts/src/deployment-addresses.ts b/scripts/src/deployment-addresses.ts index 58dbfd7..5595549 100644 --- a/scripts/src/deployment-addresses.ts +++ b/scripts/src/deployment-addresses.ts @@ -3,27 +3,48 @@ import { join, parse as parsePath } from 'node:path'; import type { AddressLike } from 'ethers'; -export interface DeploymentAddressEntry { +export interface Deployment { + deploymentName: string; // The full deterministic name from the artifact file address: AddressLike; constructorArgs?: any[]; constructorArgTypes?: string[]; } -export interface ChainDeploymentAddresses { - [chainId: string]: DeploymentAddressEntry; +export interface DeploymentsByChain { + [chainId: string]: Deployment[]; } -export interface AllDeploymentAddresses { - [deploymentName: string]: ChainDeploymentAddresses; +export interface AllDeploymentsByContract { + [contractName: string]: DeploymentsByChain; +} + +// Helper to extract contract name from a deployment name +function extractContractName(deploymentName: string): string { + if (!deploymentName) return ''; + + const lastUnderscoreIndex = deploymentName.lastIndexOf('_'); + if (lastUnderscoreIndex < 0 || lastUnderscoreIndex === deploymentName.length - 1) { + return deploymentName; + } + + const potentialSuffix = deploymentName.slice(lastUnderscoreIndex + 1); + if (potentialSuffix.length === 8 && /^[\dA-Fa-f]+$/.test(potentialSuffix)) { + return deploymentName.slice(0, lastUnderscoreIndex); + } + + return deploymentName; } /** * Reads deployment artifacts from the `deployments` directory (specific to data-feed-proxy-combinators) - * and aggregates contract addresses, constructor arguments, and types by deployment name and chain ID. + * and aggregates contract addresses, constructor arguments, and types by contract name, then by chain ID, + * with an array of deployment instances. * @returns A stringified JSON object of deployment addresses. */ export function getDeploymentAddresses(): string { - const allAddresses: AllDeploymentAddresses = {}; + const allDeployments: AllDeploymentsByContract = {}; + // Assumes this script is in data-feed-proxy-combinators/scripts/src/ + // and the deployments directory is at data-feed-proxy-combinators/deployments/ const deploymentsRoot = join(__dirname, '..', '..', 'deployments'); if (!fs.existsSync(deploymentsRoot)) { @@ -48,17 +69,26 @@ export function getDeploymentAddresses(): string { for (const deploymentFile of deploymentFiles) { const deploymentName = parsePath(deploymentFile).name; + const contractName = extractContractName(deploymentName); + const artifact = JSON.parse(fs.readFileSync(join(networkPath, deploymentFile), 'utf8')); - const constructorEntry = artifact.abi.find((item: any) => item.type === 'constructor'); - const constructorArgTypes = constructorEntry?.inputs?.map((input: any) => input.type) || []; + const constructorEntry = artifact.abi?.find( + (item: { type: string; inputs?: unknown[] }) => item.type === 'constructor' + ); + const constructorArgTypes = constructorEntry?.inputs?.map((input: { type: string }) => input.type) ?? []; - if (!allAddresses[deploymentName]) allAddresses[deploymentName] = {}; - allAddresses[deploymentName][chainId] = { + const instanceDetail: Deployment = { + deploymentName, address: artifact.address, constructorArgs: artifact.args || [], constructorArgTypes, }; + + allDeployments[contractName] = { + ...allDeployments[contractName], + [chainId]: [...(allDeployments[contractName]?.[chainId] ?? []), instanceDetail], + }; } } - return `${JSON.stringify(allAddresses, null, 2)}\n`; + return `${JSON.stringify(allDeployments, null, 2)}\n`; } From 28eb2743a9276df83b3bb190cd86ed8cf4e66eec Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Santiago=20Ace=C3=B1olaza?= Date: Tue, 27 May 2025 18:49:35 -0300 Subject: [PATCH 14/19] Changes the addresses.json format and runs prettify on generated JSON --- scripts/check-deployment-addresses.ts | 2 +- scripts/generate-deployment-addresses.ts | 2 +- scripts/src/deployment-addresses.ts | 10 ++++++++-- 3 files changed, 10 insertions(+), 4 deletions(-) diff --git a/scripts/check-deployment-addresses.ts b/scripts/check-deployment-addresses.ts index c23fc69..db031cd 100644 --- a/scripts/check-deployment-addresses.ts +++ b/scripts/check-deployment-addresses.ts @@ -9,7 +9,7 @@ async function main(): Promise { ? fs.readFileSync(addressesJsonPath, 'utf8') : '{}'; - const generatedAddressesJsonString = getDeploymentAddresses(); + const generatedAddressesJsonString = await getDeploymentAddresses(); // Normalize by parsing and re-stringifying to ensure consistent formatting for comparison const normalizedExisting = `${JSON.stringify(JSON.parse(existingAddressesJsonString), null, 2)}\n`; diff --git a/scripts/generate-deployment-addresses.ts b/scripts/generate-deployment-addresses.ts index 6fe4409..6c97948 100644 --- a/scripts/generate-deployment-addresses.ts +++ b/scripts/generate-deployment-addresses.ts @@ -4,7 +4,7 @@ import { join } from 'node:path'; import { getDeploymentAddresses } from './src/deployment-addresses'; async function main(): Promise { - fs.writeFileSync(join('deployments', 'addresses.json'), getDeploymentAddresses()); + fs.writeFileSync(join('deployments', 'addresses.json'), await getDeploymentAddresses()); } main() diff --git a/scripts/src/deployment-addresses.ts b/scripts/src/deployment-addresses.ts index 5595549..6193f6d 100644 --- a/scripts/src/deployment-addresses.ts +++ b/scripts/src/deployment-addresses.ts @@ -2,6 +2,9 @@ import * as fs from 'node:fs'; import { join, parse as parsePath } from 'node:path'; import type { AddressLike } from 'ethers'; +import { format } from 'prettier'; + +const PRETTIER_CONFIG = join(__dirname, '..', '..', '.prettierrc'); export interface Deployment { deploymentName: string; // The full deterministic name from the artifact file @@ -41,7 +44,7 @@ function extractContractName(deploymentName: string): string { * with an array of deployment instances. * @returns A stringified JSON object of deployment addresses. */ -export function getDeploymentAddresses(): string { +export async function getDeploymentAddresses(): Promise { const allDeployments: AllDeploymentsByContract = {}; // Assumes this script is in data-feed-proxy-combinators/scripts/src/ // and the deployments directory is at data-feed-proxy-combinators/deployments/ @@ -90,5 +93,8 @@ export function getDeploymentAddresses(): string { }; } } - return `${JSON.stringify(allDeployments, null, 2)}\n`; + + const rawContent = JSON.stringify(allDeployments); + const prettierConfig = JSON.parse(fs.readFileSync(PRETTIER_CONFIG, 'utf8')); + return format(rawContent, { ...prettierConfig, parser: 'json' }); } From caea57923fe7f77f41b46864db18e545bedb70f8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Santiago=20Ace=C3=B1olaza?= Date: Tue, 27 May 2025 18:49:58 -0300 Subject: [PATCH 15/19] Adds WstETHApi3ReaderProxyV1 deploy script --- deploy/005_deploy_WstETHApi3ReaderProxyV1.ts | 45 ++++++++++++++++++++ package.json | 1 + 2 files changed, 46 insertions(+) create mode 100644 deploy/005_deploy_WstETHApi3ReaderProxyV1.ts diff --git a/deploy/005_deploy_WstETHApi3ReaderProxyV1.ts b/deploy/005_deploy_WstETHApi3ReaderProxyV1.ts new file mode 100644 index 0000000..3844bfa --- /dev/null +++ b/deploy/005_deploy_WstETHApi3ReaderProxyV1.ts @@ -0,0 +1,45 @@ +import type { HardhatRuntimeEnvironment } from 'hardhat/types'; + +// Note: getDeploymentName is not strictly needed here as there are no constructor args, +// but kept for potential future consistency if desired. For no-arg singletons, +// using the contract name directly as the deployment name is often simplest. +// import { getDeploymentName } from '../src/deployment'; + +const CONTRACT_NAME = 'WstETHApi3ReaderProxyV1'; + +module.exports = async (hre: HardhatRuntimeEnvironment) => { + const { getUnnamedAccounts, deployments, network, run } = hre; + const { deploy, log } = deployments; + + const [deployerAddress] = await getUnnamedAccounts(); + if (!deployerAddress) { + throw new Error('No deployer address found.'); + } + log(`Deployer address: ${deployerAddress}`); + + const isLocalNetwork = network.name === 'hardhat' || network.name === 'localhost'; + + const confirmations = isLocalNetwork ? 1 : 5; + log(`Deployment confirmations: ${confirmations}`); + + // For contracts with no constructor args, using the contract name directly is common. + log(`Deployment name for this instance: ${CONTRACT_NAME}`); + + const deployment = await deploy(CONTRACT_NAME, { + contract: CONTRACT_NAME, + from: deployerAddress, + log: true, + waitConfirmations: confirmations, + }); + + if (isLocalNetwork) { + log('Skipping verification on local network.'); + return; + } + + log(`Attempting verification of ${CONTRACT_NAME} at ${deployment.address} (already waited for confirmations)...`); + await run('verify:verify', { + address: deployment.address, + }); +}; +module.exports.tags = [CONTRACT_NAME]; diff --git a/package.json b/package.json index a8c51d5..8d2b139 100644 --- a/package.json +++ b/package.json @@ -28,6 +28,7 @@ "deploy:NormalizedApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags NormalizedApi3ReaderProxyV1", "deploy:ProductApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags ProductApi3ReaderProxyV1", "deploy:ScaledApi3FeedProxyV1": "hardhat deploy --network $NETWORK --tags ScaledApi3FeedProxyV1", + "deploy:WstETHApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags WstETHApi3ReaderProxyV1", "generate:deployment-addresses": "ts-node scripts/generate-deployment-addresses.ts", "lint": "pnpm run prettier:check && pnpm run lint:eslint && pnpm run lint:solhint", "lint:solhint": "solhint ./contracts/**/*.sol", From 1b58070f7407631bdf31e8fdb5b9f14fa31c5073 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Santiago=20Ace=C3=B1olaza?= Date: Tue, 27 May 2025 18:55:35 -0300 Subject: [PATCH 16/19] Minor change on index.ts --- src/index.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/index.ts b/src/index.ts index 1fce1e9..028e50a 100644 --- a/src/index.ts +++ b/src/index.ts @@ -1,2 +1,2 @@ -export * from './deployment'; export * from '../typechain-types'; +export * from './deployment'; From 2d24ba63f0333f84cf8ee147122c555d737a6235 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Santiago=20Ace=C3=B1olaza?= Date: Wed, 28 May 2025 09:31:24 -0300 Subject: [PATCH 17/19] Ignores deployments directory --- .eslintignore | 3 +++ .gitignore | 3 +++ .prettierignore | 3 +++ 3 files changed, 9 insertions(+) diff --git a/.eslintignore b/.eslintignore index a033a3c..b3edb79 100644 --- a/.eslintignore +++ b/.eslintignore @@ -17,3 +17,6 @@ dist gas_report contracts/vendor + +# Hardhat deploy artifacts +/deployments diff --git a/.gitignore b/.gitignore index 9fae613..fa9da55 100644 --- a/.gitignore +++ b/.gitignore @@ -15,3 +15,6 @@ dist /coverage.json gas_report + +# Hardhat deploy artifacts +/deployments \ No newline at end of file diff --git a/.prettierignore b/.prettierignore index a033a3c..b3edb79 100644 --- a/.prettierignore +++ b/.prettierignore @@ -17,3 +17,6 @@ dist gas_report contracts/vendor + +# Hardhat deploy artifacts +/deployments From b38c9a80eb6de41b6d5959125f033c15d857536a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Santiago=20Ace=C3=B1olaza?= Date: Wed, 28 May 2025 09:40:38 -0300 Subject: [PATCH 18/19] Removes scripts that generates and checks addresses.json --- .husky/pre-push | 1 - deployments/addresses.json | 1 - package.json | 4 - pnpm-lock.yaml | 10 --- scripts/check-deployment-addresses.ts | 29 ------- scripts/generate-deployment-addresses.ts | 16 ---- scripts/src/deployment-addresses.ts | 100 ----------------------- 7 files changed, 161 deletions(-) delete mode 100644 .husky/pre-push delete mode 100644 deployments/addresses.json delete mode 100644 scripts/check-deployment-addresses.ts delete mode 100644 scripts/generate-deployment-addresses.ts delete mode 100644 scripts/src/deployment-addresses.ts diff --git a/.husky/pre-push b/.husky/pre-push deleted file mode 100644 index ecb6d11..0000000 --- a/.husky/pre-push +++ /dev/null @@ -1 +0,0 @@ -pnpm check:deployment-addresses \ No newline at end of file diff --git a/deployments/addresses.json b/deployments/addresses.json deleted file mode 100644 index 0967ef4..0000000 --- a/deployments/addresses.json +++ /dev/null @@ -1 +0,0 @@ -{} diff --git a/package.json b/package.json index 8d2b139..ce4de02 100644 --- a/package.json +++ b/package.json @@ -23,17 +23,14 @@ "scripts": { "build": "pnpm build:hardhat && tsc -p tsconfig.build.json", "build:hardhat": "hardhat --config hardhat.build.config.ts compile", - "check:deployment-addresses": "ts-node scripts/check-deployment-addresses.ts", "deploy:InverseApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags InverseApi3ReaderProxyV1", "deploy:NormalizedApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags NormalizedApi3ReaderProxyV1", "deploy:ProductApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags ProductApi3ReaderProxyV1", "deploy:ScaledApi3FeedProxyV1": "hardhat deploy --network $NETWORK --tags ScaledApi3FeedProxyV1", "deploy:WstETHApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags WstETHApi3ReaderProxyV1", - "generate:deployment-addresses": "ts-node scripts/generate-deployment-addresses.ts", "lint": "pnpm run prettier:check && pnpm run lint:eslint && pnpm run lint:solhint", "lint:solhint": "solhint ./contracts/**/*.sol", "lint:eslint": "eslint . --ext .js,.ts", - "prepare": "husky", "prettier:check": "prettier --check \"./**/*.{js,ts,md,json,sol}\"", "prettier": "prettier --write \"./**/*.{js,ts,md,json,sol}\"", "verify-vendor-contracts": "hardhat run scripts/verify-vendor-contracts.ts", @@ -59,7 +56,6 @@ "glob": "^11.0.2", "hardhat": "^2.24.0", "hardhat-deploy": "^1.0.2", - "husky": "^9.1.7", "prettier": "^3.5.3", "prettier-plugin-solidity": "^2.0.0", "solhint": "^5.1.0", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index ce415e2..0192416 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -65,9 +65,6 @@ importers: hardhat-deploy: specifier: ^1.0.2 version: 1.0.2 - husky: - specifier: ^9.1.7 - version: 9.1.7 prettier: specifier: ^3.5.3 version: 3.5.3 @@ -2316,11 +2313,6 @@ packages: resolution: {integrity: sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA==} engines: {node: '>= 6'} - husky@9.1.7: - resolution: {integrity: sha512-5gs5ytaNjBrh5Ow3zrvdUUY+0VxIuWVL4i9irt6friV+BqdCfmV11CQTWMiBYWHbXhco+J1kHfTOUkePhCDvMA==} - engines: {node: '>=18'} - hasBin: true - iconv-lite@0.4.24: resolution: {integrity: sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==} engines: {node: '>=0.10.0'} @@ -6967,8 +6959,6 @@ snapshots: transitivePeerDependencies: - supports-color - husky@9.1.7: {} - iconv-lite@0.4.24: dependencies: safer-buffer: 2.1.2 diff --git a/scripts/check-deployment-addresses.ts b/scripts/check-deployment-addresses.ts deleted file mode 100644 index db031cd..0000000 --- a/scripts/check-deployment-addresses.ts +++ /dev/null @@ -1,29 +0,0 @@ -import * as fs from 'node:fs'; -import { join } from 'node:path'; - -import { getDeploymentAddresses } from './src/deployment-addresses'; - -async function main(): Promise { - const addressesJsonPath = join('deployments', 'addresses.json'); - const existingAddressesJsonString = fs.existsSync(addressesJsonPath) - ? fs.readFileSync(addressesJsonPath, 'utf8') - : '{}'; - - const generatedAddressesJsonString = await getDeploymentAddresses(); - - // Normalize by parsing and re-stringifying to ensure consistent formatting for comparison - const normalizedExisting = `${JSON.stringify(JSON.parse(existingAddressesJsonString), null, 2)}\n`; - const normalizedGenerated = `${JSON.stringify(JSON.parse(generatedAddressesJsonString), null, 2)}\n`; - - if (normalizedExisting !== normalizedGenerated) { - throw new Error(`${addressesJsonPath} is outdated. Please run "pnpm generate:deployment-addresses".`); - } -} - -main() - .then(() => process.exit(0)) - .catch((error) => { - // eslint-disable-next-line no-console - console.error(error); - process.exit(1); - }); diff --git a/scripts/generate-deployment-addresses.ts b/scripts/generate-deployment-addresses.ts deleted file mode 100644 index 6c97948..0000000 --- a/scripts/generate-deployment-addresses.ts +++ /dev/null @@ -1,16 +0,0 @@ -import * as fs from 'node:fs'; -import { join } from 'node:path'; - -import { getDeploymentAddresses } from './src/deployment-addresses'; - -async function main(): Promise { - fs.writeFileSync(join('deployments', 'addresses.json'), await getDeploymentAddresses()); -} - -main() - .then(() => process.exit(0)) - .catch((error) => { - // eslint-disable-next-line no-console - console.error(error); - process.exit(1); - }); diff --git a/scripts/src/deployment-addresses.ts b/scripts/src/deployment-addresses.ts deleted file mode 100644 index 6193f6d..0000000 --- a/scripts/src/deployment-addresses.ts +++ /dev/null @@ -1,100 +0,0 @@ -import * as fs from 'node:fs'; -import { join, parse as parsePath } from 'node:path'; - -import type { AddressLike } from 'ethers'; -import { format } from 'prettier'; - -const PRETTIER_CONFIG = join(__dirname, '..', '..', '.prettierrc'); - -export interface Deployment { - deploymentName: string; // The full deterministic name from the artifact file - address: AddressLike; - constructorArgs?: any[]; - constructorArgTypes?: string[]; -} - -export interface DeploymentsByChain { - [chainId: string]: Deployment[]; -} - -export interface AllDeploymentsByContract { - [contractName: string]: DeploymentsByChain; -} - -// Helper to extract contract name from a deployment name -function extractContractName(deploymentName: string): string { - if (!deploymentName) return ''; - - const lastUnderscoreIndex = deploymentName.lastIndexOf('_'); - if (lastUnderscoreIndex < 0 || lastUnderscoreIndex === deploymentName.length - 1) { - return deploymentName; - } - - const potentialSuffix = deploymentName.slice(lastUnderscoreIndex + 1); - if (potentialSuffix.length === 8 && /^[\dA-Fa-f]+$/.test(potentialSuffix)) { - return deploymentName.slice(0, lastUnderscoreIndex); - } - - return deploymentName; -} - -/** - * Reads deployment artifacts from the `deployments` directory (specific to data-feed-proxy-combinators) - * and aggregates contract addresses, constructor arguments, and types by contract name, then by chain ID, - * with an array of deployment instances. - * @returns A stringified JSON object of deployment addresses. - */ -export async function getDeploymentAddresses(): Promise { - const allDeployments: AllDeploymentsByContract = {}; - // Assumes this script is in data-feed-proxy-combinators/scripts/src/ - // and the deployments directory is at data-feed-proxy-combinators/deployments/ - const deploymentsRoot = join(__dirname, '..', '..', 'deployments'); - - if (!fs.existsSync(deploymentsRoot)) { - throw new Error(`Deployments directory not found at ${deploymentsRoot}.`); - } - - const networkDirs = fs - .readdirSync(deploymentsRoot, { withFileTypes: true }) - .filter((dirent) => dirent.isDirectory() && dirent.name !== 'localhost' && dirent.name !== 'hardhat') - .map((dirent) => dirent.name); - - for (const networkName of networkDirs) { - const networkPath = join(deploymentsRoot, networkName); - const chainIdFilePath = join(networkPath, '.chainId'); - if (!fs.existsSync(chainIdFilePath)) continue; - const chainId = fs.readFileSync(chainIdFilePath, 'utf8').trim(); - - const deploymentFiles = fs - .readdirSync(networkPath, { withFileTypes: true }) - .filter((dirent) => dirent.isFile() && dirent.name.endsWith('.json')) - .map((dirent) => dirent.name); - - for (const deploymentFile of deploymentFiles) { - const deploymentName = parsePath(deploymentFile).name; - const contractName = extractContractName(deploymentName); - - const artifact = JSON.parse(fs.readFileSync(join(networkPath, deploymentFile), 'utf8')); - const constructorEntry = artifact.abi?.find( - (item: { type: string; inputs?: unknown[] }) => item.type === 'constructor' - ); - const constructorArgTypes = constructorEntry?.inputs?.map((input: { type: string }) => input.type) ?? []; - - const instanceDetail: Deployment = { - deploymentName, - address: artifact.address, - constructorArgs: artifact.args || [], - constructorArgTypes, - }; - - allDeployments[contractName] = { - ...allDeployments[contractName], - [chainId]: [...(allDeployments[contractName]?.[chainId] ?? []), instanceDetail], - }; - } - } - - const rawContent = JSON.stringify(allDeployments); - const prettierConfig = JSON.parse(fs.readFileSync(PRETTIER_CONFIG, 'utf8')); - return format(rawContent, { ...prettierConfig, parser: 'json' }); -} From 1f0d70f603462b7667b2ea6c38b2b0cfad122815 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Santiago=20Ace=C3=B1olaza?= Date: Wed, 28 May 2025 09:47:15 -0300 Subject: [PATCH 19/19] Removes morpho related files --- contracts/WstETHApi3ReaderProxyV1.sol | 32 -------------- contracts/interfaces/IWstETH.sol | 11 ----- deploy/005_deploy_WstETHApi3ReaderProxyV1.ts | 45 -------------------- package.json | 1 - scripts/deploy-morpho.ts | 22 ---------- 5 files changed, 111 deletions(-) delete mode 100644 contracts/WstETHApi3ReaderProxyV1.sol delete mode 100644 contracts/interfaces/IWstETH.sol delete mode 100644 deploy/005_deploy_WstETHApi3ReaderProxyV1.ts delete mode 100644 scripts/deploy-morpho.ts diff --git a/contracts/WstETHApi3ReaderProxyV1.sol b/contracts/WstETHApi3ReaderProxyV1.sol deleted file mode 100644 index 7e5eb1d..0000000 --- a/contracts/WstETHApi3ReaderProxyV1.sol +++ /dev/null @@ -1,32 +0,0 @@ -// SPDX-License-Identifier: MIT -pragma solidity ^0.8.27; - -import "@api3/contracts/interfaces/IApi3ReaderProxy.sol"; -import "./interfaces/IWstETH.sol"; - -/// @title An immutable proxy contract that reads the stETH per wstETH ratio -/// directly from the WstETH contract on Ethereum. -/// @dev This contract implements only the IApi3ReaderProxy interface and not the -/// AggregatorV2V3Interface which is usually implemented by Api3 proxies. The -/// user of this contract needs to be aware of this limitation and only use this -/// contract where the IApi3ReaderProxy interface is expected. -contract WstETHApi3ReaderProxyV1 is IApi3ReaderProxy { - /// @notice The address of the wstETH contract on Ethereum mainnet. - address public constant WST_ETH = - 0x7f39C581F595B53c5cb19bD0b3f8dA6c935E2Ca0; - - /// @inheritdoc IApi3ReaderProxy - /// @dev Returns the stETH/wstETH exchange rate with 18 decimals precision. - /// The timestamp returned is the current block timestamp. - function read() - public - view - override - returns (int224 value, uint32 timestamp) - { - uint256 stEthPerToken = IWstETH(WST_ETH).stEthPerToken(); - - value = int224(int256(stEthPerToken)); // stEthPerToken value has 18 decimals. - timestamp = uint32(block.timestamp); - } -} diff --git a/contracts/interfaces/IWstETH.sol b/contracts/interfaces/IWstETH.sol deleted file mode 100644 index 019e4b6..0000000 --- a/contracts/interfaces/IWstETH.sol +++ /dev/null @@ -1,11 +0,0 @@ -// SPDX-License-Identifier: MIT -pragma solidity ^0.8.27; - -/// @title A minimal interface for the wstETH contract on Ethereum -/// @dev This interface only includes the stEthPerToken function needed to read -/// the exchange rate between stETH and wstETH. -interface IWstETH { - /// @notice Returns the amount of stETH that corresponds to 1 wstETH - /// @return The stETH/wstETH exchange rate with 18 decimals precision - function stEthPerToken() external view returns (uint256); -} diff --git a/deploy/005_deploy_WstETHApi3ReaderProxyV1.ts b/deploy/005_deploy_WstETHApi3ReaderProxyV1.ts deleted file mode 100644 index 3844bfa..0000000 --- a/deploy/005_deploy_WstETHApi3ReaderProxyV1.ts +++ /dev/null @@ -1,45 +0,0 @@ -import type { HardhatRuntimeEnvironment } from 'hardhat/types'; - -// Note: getDeploymentName is not strictly needed here as there are no constructor args, -// but kept for potential future consistency if desired. For no-arg singletons, -// using the contract name directly as the deployment name is often simplest. -// import { getDeploymentName } from '../src/deployment'; - -const CONTRACT_NAME = 'WstETHApi3ReaderProxyV1'; - -module.exports = async (hre: HardhatRuntimeEnvironment) => { - const { getUnnamedAccounts, deployments, network, run } = hre; - const { deploy, log } = deployments; - - const [deployerAddress] = await getUnnamedAccounts(); - if (!deployerAddress) { - throw new Error('No deployer address found.'); - } - log(`Deployer address: ${deployerAddress}`); - - const isLocalNetwork = network.name === 'hardhat' || network.name === 'localhost'; - - const confirmations = isLocalNetwork ? 1 : 5; - log(`Deployment confirmations: ${confirmations}`); - - // For contracts with no constructor args, using the contract name directly is common. - log(`Deployment name for this instance: ${CONTRACT_NAME}`); - - const deployment = await deploy(CONTRACT_NAME, { - contract: CONTRACT_NAME, - from: deployerAddress, - log: true, - waitConfirmations: confirmations, - }); - - if (isLocalNetwork) { - log('Skipping verification on local network.'); - return; - } - - log(`Attempting verification of ${CONTRACT_NAME} at ${deployment.address} (already waited for confirmations)...`); - await run('verify:verify', { - address: deployment.address, - }); -}; -module.exports.tags = [CONTRACT_NAME]; diff --git a/package.json b/package.json index ce4de02..e82b979 100644 --- a/package.json +++ b/package.json @@ -27,7 +27,6 @@ "deploy:NormalizedApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags NormalizedApi3ReaderProxyV1", "deploy:ProductApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags ProductApi3ReaderProxyV1", "deploy:ScaledApi3FeedProxyV1": "hardhat deploy --network $NETWORK --tags ScaledApi3FeedProxyV1", - "deploy:WstETHApi3ReaderProxyV1": "hardhat deploy --network $NETWORK --tags WstETHApi3ReaderProxyV1", "lint": "pnpm run prettier:check && pnpm run lint:eslint && pnpm run lint:solhint", "lint:solhint": "solhint ./contracts/**/*.sol", "lint:eslint": "eslint . --ext .js,.ts", diff --git a/scripts/deploy-morpho.ts b/scripts/deploy-morpho.ts deleted file mode 100644 index dd93ae5..0000000 --- a/scripts/deploy-morpho.ts +++ /dev/null @@ -1,22 +0,0 @@ -import { ethers } from 'ethers'; - -import { ProductApi3ReaderProxyV1__factory } from '../typechain-types'; - -const deployPriceFeedProxy = async () => { - const provider = new ethers.JsonRpcProvider(process.env.PROVIDER); - const signer = new ethers.Wallet(process.env.PK!, provider); - const productApi3ReaderProxyV1Factory = new ProductApi3ReaderProxyV1__factory(signer); - console.info('Deploying product proxy...'); - const tx = await productApi3ReaderProxyV1Factory.deploy( - '', // TODO: Deploy WstETHApi3ReaderProxyV1.sol - '0x37422cC8e1487a0452cc0D0BF75877d86c63c88A' // https://market.api3.org/ethereum/eth-usd/integrate?dappAlias=morpho-wsteth-usdc-860-lltv - ); - const productApi3ReaderProxyV1 = await tx.waitForDeployment(); - console.info('Deployed ProductApi3ReaderProxyV1:', await productApi3ReaderProxyV1.getAddress()); - console.info('ProductApi3ReaderProxyV1.read():', await productApi3ReaderProxyV1.read()); - // Deployed on Base: 0x707991d5533021021cC360dF093f1B396340Ef3E -}; - -deployPriceFeedProxy(); - -// NOTE: https://market.api3.org/ethereum/usdc-usd/integrate?dappAlias=morpho-wsteth-usdc-860-lltv