Building Confidence: Setting Up Your Smart Contract Testing Framework with Hardhat

lakshya kumar
4 min readApr 28, 2024

--

This article equips you with the knowledge to set up a comprehensive testing framework for your blockchain project using Hardhat. Whether you’re a seasoned developer or just starting your journey in this exciting space, robust testing is crucial for ensuring the security and functionality of your smart contracts.

Part of a Series

This article is part of a comprehensive tutorial series designed to guide you through Account Abstraction or ERC-4337. If you’re new to the series, you can find the starting point here. The previous tutorial in this series can be found here.

Throughout this series, we’ll cover a variety of topics related to Account Abstraction. We’ll provide clear explanations, practical examples, and troubleshooting tips to help you on your learning journey.

To ensure you have access to all the code examples used throughout this series, we’ve created a dedicated repository on GitHub. This repository will be constantly updated as we progress through the tutorials. By following the repository, you can easily clone it to your local machine and follow along with the code demonstrations.

Setting Up the Hardhat Environment

Let’s begin by establishing the foundation for your testing environment. We’ll utilize Hardhat, a popular Ethereum development framework known for its user-friendliness and robust features.

  1. Installation: Begin by installing Hardhat using npm:
npm install --save-dev hardhat
  1. Project Initialization: Once installed, initiate a new JavaScript project using Hardhat’s built-in command:
npx hardhat init
> Create a JavaScript project

3. Dependencies: Install the necessary dependencies for development and testing:

npm install --save-dev "hardhat@^2.12.7" "@nomicfoundation/hardhat-toolbox@^5.0.0"

4. OpenZeppelin Contracts: Integrate the OpenZeppelin library for access to pre-audited and secure smart contract functionalities:

npm install @openzeppelin/contracts

5. Verification: Verify the successful installation by running these commands:

npx hardhat --version
npx hardhat test

These commands should output the installed Hardhat version and run sample tests

Housekeeping: To ensure a clean slate for our tutorial, delete the existing files related to a potentially pre-existing Lock contract:

  1. contracts/Lock.sol
  2. scripts/deploy.js
  3. test/Lock.js

Solidity Version: Double-check that your hardhat.config.js file specifies solidity: "0.8.20" to ensure compatibility with the code examples used throughout this guide.

Demystifying Testing Scripts: A Practical Approach

Understanding the structure of test scripts is crucial for writing effective tests. This section will provide a step-by-step approach, assuming you’re new to writing test scripts.

lets create a file test/01_WalletV1.test.js

  • loadFixture: This function enables us to define a reusable setup for each test case. It ensures that every test starts with a clean environment and a consistent initial state.
  • deployWallet function: This function, essential for each test case, is responsible for deploying and returning the required contracts needed for the specific tests.
  • describe blocks: These blocks help organize your tests logically. Here, we have one describe block for the overall “Wallet-V1” functionality and a nested one for “Deployment” specifically.
  • it statements: Each individual test case is defined within an it statement. These statements describe the specific behavior being tested along with the corresponding assertions using expect from Chai.
  • Test Case: In the provided example, the test case ensures that the deployed token contract has an address after deployment.
const { loadFixture } = require("@nomicfoundation/hardhat-network-helpers");
const { anyValue } = require("@nomicfoundation/hardhat-chai-matchers/withArgs");
const { expect } = require("chai");
describe("Wallet-V1", function () {
// We define a fixture to reuse the same setup in every test.
// We use loadFixture to run this setup once, snapshot that state,
// and reset Hardhat Network to that snapshot in every test.
async function deployWallet() {
// use this function to deploy and return the basic contracts required for the test cases
return { token };
}
describe("Deployment", function () {
it("Should Deploy wallet and token", async function () {
const { token } = await loadFixture(deployWallet);
expect(await token.getAddress()).to.exist;
});
});
});

Running Your Tests: Navigate to your project directory in the terminal and execute the following command to run your newly created test script:

npx hardhat test

Level Up

This article marks your gateway to the next level in here. Here, you’ll gain the knowledge and practical skills for Account Abstraction.

Code Repository and Continued Learning

For a comprehensive overview of the concepts and techniques discussed in this series, along with the complete code examples used throughout the tutorials, please refer to the dedicated GitHub repository:

This repository will serve as a valuable companion resource, allowing you to not only follow along with the code demonstrations but also explore the codebase in your own time. The repository will be continually updated as the series progresses, ensuring you have access to the latest code iterations.

Thank you for joining us on this exploration!

To delve deeper and contribute to the ongoing development, we encourage you to star our project’s GitHub repository. There, you can find valuable resources and raise Pull Requests (PRs) to address any issues or propose improvements. Let’s build a better blockchain UI together!

References

If you’d like to explore related topics in more depth, consider the below references

  1. Test File

--

--

lakshya kumar

Web3 Solution Architect | Masters In Mathemetics | Solving real-world problems with Blockchain (Hyperledger, ETH), React, JS, Node, Mongo. AWS/K8s