Let`s create and deploy Smart Contracts using Hardhat.
You can create Hardhat project as follows. After running 'npx hardhat', you select what type of project to create and set the the root path for the project. If You choose to add the '.gitignore file' or install the dependency module for the sample project, the necessary files are installed.
$ mkdir greeter
$ cd greeter
$ npm install --save-dev hardhat
$ npx hardhat
888 888 888 888 888
888 888 888 888 888
888 888 888 888 888
8888888888 8888b. 888d888 .d88888 88888b. 8888b. 888888
888 888 "88b 888P" d88" 888 888 "88b "88b 888
888 888 .d888888 888 888 888 888 888 .d888888 888
888 888 888 888 888 Y88b 888 888 888 888 888 Y88b.
888 888 "Y888888 888 "Y88888 888 888 "Y888888 "Y888
👷 Welcome to Hardhat v2.13.0 👷
✔ What do you want to do? · Create a JavaScript project
✔ Hardhat project root: · /Users/trident/Projects/Solidity/hardhat-test
✔ Do you want to add a .gitignore? (Y/n) · y
✔ Do you want to install this sample project's dependencies with npm (hardhat @nomicfoundation/hardhat-toolbox)? (Y/n) · y
After installation, the directory structure is as follows. Smart contracts will be located in contracts, deployed scripts in scripts, test code in tests, and compiled results in artifacts, cache. Set the network connection information, solidity compiler version information, and so on in hardhat.config.js.
The Lock.sol that is created by default is compiled as follows.
// SPDX-License-Identifier: UNLICENSEDpragmasolidity ^0.8.0;// Uncomment this line to use console.log// import "hardhat/console.sol";contract Lock {uintpublic unlockTime;addresspayablepublic owner;eventWithdrawal(uint amount, uint when);constructor(uint_unlockTime) payable {require( block.timestamp < _unlockTime,"Unlock time should be in the future" ); unlockTime = _unlockTime; owner =payable(msg.sender); }functionwithdraw() public {// Uncomment this line, and the import of "hardhat/console.sol", to print a log in your terminal// console.log("Unlock time is %o and block timestamp is %o", unlockTime, block.timestamp);require(block.timestamp >= unlockTime,"You can't withdraw yet");require(msg.sender == owner,"You aren't the owner");emitWithdrawal(address(this).balance, block.timestamp); owner.transfer(address(this).balance); }}
Run the test using Lock.js, which is created by default.
$ npx hardhat test
Lock
Deployment
✔ Should set the right unlockTime (2392ms)
✔ Should set the right owner
✔ Should receive and store the funds to lock
✔ Should fail if the unlockTime is not in the future (46ms)
Withdrawals
Validations
✔ Should revert with the right error if called too soon
✔ Should revert with the right error if called from another account
✔ Shouldn't fail if the unlockTime has arrived and the owner calls it
Events
✔ Should emit an event on withdrawals
Transfers
✔ Should transfer the funds to the owner
9 passing (3s)
Deploying smart contracts uses deploy.js, which is provided by default. You need to set up a network to deploy in advance, but add the WEMIX3.0 Testnet and Mainnet to hardhat.config.js as shown below. If you save the private key of the account address that use for deployment, it is easy to work with, so we recommend that you create a test account and then send as many WEMIX as you need. How to extract private keys from a MetaMask is omitted here.
// We require the Hardhat Runtime Environment explicitly here. This is optional
// but useful for running the script in a standalone fashion through `node <script>`.
//
// You can also run a script with `npx hardhat run <script>`. If you do that, Hardhat
// will compile your contracts, add the Hardhat Runtime Environment's members to the
// global scope, and execute the script.
const hre = require("hardhat");
async function main() {
const currentTimestampInSeconds = Math.round(Date.now() / 1000);
const unlockTime = currentTimestampInSeconds + 60;
const lockedAmount = hre.ethers.utils.parseEther("0.001");
const Lock = await hre.ethers.getContractFactory("Lock");
const lock = await Lock.deploy(unlockTime, { value: lockedAmount });
await lock.deployed();
console.log(
`Lock with ${ethers.utils.formatEther(
lockedAmount
)}ETH and unlock timestamp ${unlockTime} deployed to ${lock.address}`
);
}
// We recommend this pattern to be able to use async/await everywhere
// and properly handle errors.
main().catch((error) => {
console.error(error);
process.exitCode = 1;
});
When you are ready, run the following command to deploy. Upon successful deployment, the smart contract address is output according to the preset log.
$ npx hardhat run scripts/deploy.js --network wemix_testnet
Lock with 0.001ETH and unlock timestamp 1679558487 deployed to 0x813fbbbeF30f343da37332293546dc854