测试Ebay拍卖智能合约时遇No Contract deployed报错求助
问题:Hardhat测试报错Error: No Contract deployed with name Ebay
错误现象
开发产品拍卖用的Ebay智能合约,部署操作成功,但执行Hardhat测试时反复出现错误:Error: No Contract deployed with name Ebay,尝试在test.js中用ABI替代deployer后问题依旧。
测试执行日志
yarn run v1.22.15 warning package.json: No license field $ "E:\Block Chain Projects\30_SMARTCONTRACTS.sol\A Way To Testing\node_modules\.bin\hardhat" test Ebay Smart Contract Upload Product function This is deployer0xf39Fd6e51aad88F6F4ce6aB8827279cffFb92266 1) "before each" hook for "if the base Price is less than 0 or invalid should revert" 0 passing (2s) 1 failing 1) Ebay Smart Contract "before each" hook for "if the base Price is less than 0 or invalid should revert": Error: No Contract deployed with name Ebay at Object.getContract (node_modules\@nomiclabs\hardhat-ethers\src\internal\helpers.ts:447:11) at processTicksAndRejections (node:internal/process/task_queues:96:5) at Context.<anonymous> (test\Test.js:18:12) error Command failed with exit code 1.
相关代码
Test.js
//it //describe //beforeEach const { expect, assert } = require("chai"); const { ethers, getNamedAccounts } = require("hardhat"); describe("Ebay Smart Contract", async function() { let Ebay; let deployer; const product = { name: "CYCLE", description: "gare cycles", BasePrice: "5", }; beforeEach(async () => { deployer = (await getNamedAccounts()).deployer; console.log("This is deployer" + deployer); Ebay = await ethers.getContract("Ebay", deployer); }); describe("Upload Product function", async function() { it("if the base Price is less than 0 or invalid should revert", async function() { expect( Ebay.UploadProduct(product.name, product.description, product.BasePrice) ).to.be.revertedWith(Base_Price_cannot_be_Zero()); }); }); });
deploy.js
const { ethers, deployments } = require("hardhat"); require("dotenv").config(); async function main() { // const { deploy, log } = deployments; //const { deployer } = await getNamedAccounts(); const Auction = await ethers.getContractFactory("Ebay"); const auction = await Auction.deploy(); await auction.deployed(); console.log(auction.address); // const Auction = await deploy("Auctionbargain", { // from: deployer, // args: [], // log: true, // waitconfirmations: network.config.blockConfirmations || 1, // }); //console.log(Auction.address); //log("------------------------------------"); } main() .then(() => process.exit(0)) .catch((error) => { console.log(error); process.exit(1); });
hardhat.config.js
require("@nomicfoundation/hardhat-toolbox"); require("hardhat-deploy"); require("dotenv").config(); /** @type import('hardhat/config').HardhatUserConfig */ module.exports = { solidity: { compilers: [{ version: "0.6.6" }, { version: "0.8.8" }], }, networks: { hardhat: { chainId: 31337, }, // goerli: { // url: GOERLI_RPC_URL, // accounts: [PRIVATE_KEY], // chainId: 5, // blockConfirmations: 6, // }, }, namedAccounts: { deployer: { default: 0, // here this will by default take the first account as deployer }, }, };
问题原因及解决方案
核心原因
测试代码中使用ethers.getContract("Ebay")获取合约实例,这个方法依赖hardhat-deploy插件的部署记录。但当前deploy.js是直接用ethers.getContractFactory部署合约,不会将合约信息注册到hardhat-deploy的系统中,导致测试时找不到对应的合约记录。
解决方案一:改用hardhat-deploy的deploy函数部署(推荐)
修改deploy.js,启用注释的hardhat-deploy部署逻辑,确保合约名和测试中使用的"Ebay"一致:
const { deployments, getNamedAccounts } = require("hardhat"); const { deploy, log } = deployments; require("dotenv").config(); async function main() { const { deployer } = await getNamedAccounts(); const Auction = await deploy("Ebay", { // 合约名改为"Ebay",匹配测试中的调用 from: deployer, args: [], log: true, waitConfirmations: network.config.blockConfirmations || 1, // 修正拼写:waitConfirmations }); console.log(Auction.address); log("------------------------------------"); } main() .then(() => process.exit(0)) .catch((error) => { console.log(error); process.exit(1); });
之后测试前先执行部署命令:npx hardhat deploy,再运行测试即可正常获取合约实例。
解决方案二:测试时手动部署合约
如果不想依赖hardhat-deploy,修改Test.js的beforeEach逻辑,直接在测试环境中部署合约:
const { expect, assert } = require("chai"); const { ethers, getNamedAccounts } = require("hardhat"); describe("Ebay Smart Contract", async function() { let Ebay; let deployer; const product = { name: "CYCLE", description: "gare cycles", BasePrice: "-1", // 修改为负数触发回滚 }; beforeEach(async () => { deployer = (await getNamedAccounts()).deployer; console.log("This is deployer" + deployer); // 手动部署合约 const ebayFactory = await ethers.getContractFactory("Ebay"); Ebay = await ebayFactory.deploy(); await Ebay.deployed(); }); describe("Upload Product function", async function() { it("if the base Price is less than 0 or invalid should revert", async function() { // 修正:revertedWith参数为字符串,且需await异步操作 await expect( Ebay.UploadProduct(product.name, product.description, product.BasePrice) ).to.be.revertedWith("Base_Price_cannot_be_Zero"); }); }); });
额外修正点
测试代码中的revertedWith存在两个问题:
- 参数应该是字符串,不是函数调用
Base_Price_cannot_be_Zero(),需改为"Base_Price_cannot_be_Zero"(需和合约中定义的错误信息完全一致)。 - 原测试传入的BasePrice是"5",不会触发回滚,应改为负数如"-1"才能触发预期的回滚逻辑;同时要对合约方法调用添加
await,因为合约操作是异步的。
内容的提问来源于stack exchange,提问作者Abhishek Yadav
相关产品推荐
相关产品推荐

