Introduction
Web3 development has gained a lot of traction in recent years, especially with the rise of decentralized applications built on blockchain technology. Web3 development involves building applications that interact with the Ethereum blockchain, which is a decentralized, distributed ledger that records transactions between parties.
NextJS is a popular framework for building server-side rendered React applications. Solidity is a programming language used to write smart contracts on the Ethereum blockchain. Truffle is a development environment, testing framework, and asset pipeline for Ethereum. It provides a suite of tools for developing smart contracts and deploying them to the blockchain.
In this blog post, we will explore how to build web3 applications with NextJS, Solidity, and Truffle. We will cover the basics of creating a Solidity smart contract, compiling and deploying the contract with Truffle, integrating the contract with a web3 application using the web3.js
library, and creating a component that interacts with the contract.
Requirements
To follow this tutorial, you will need the following:
- Node.js installed on your machine
- Basic knowledge of React and JavaScript
- A text editor of your choice
- Truffle installed on your machine
Getting Started
To get started, let’s initialize a new NextJS project. Open your terminal and navigate to the directory where you want to create the project. Then, run the following command:
npx create-next-app my-app
This will create a new NextJS project in the my-app
directory.
Next, navigate to the my-app
directory and install the necessary dependencies:
cd my-app
npm install web3 @truffle/contract
Solidity Smart Contract
Solidity is a programming language used to write smart contracts on the Ethereum blockchain. In this example, we will create a simple smart contract that stores a message.
Create a new file called Message.sol
in the contracts
directory and add the following code:
pragma solidity ^0.8.0;
contract Message {
string private message;
function setMessage(string memory _message) public {
message = _message;
}
function getMessage() public view returns (string memory) {
return message;
}
}
This contract has two functions: setMessage
and getMessage
. The setMessage
function sets the message variable and the getMessage
function retrieves it.
Truffle Configuration
Truffle is a development environment, testing framework, and asset pipeline for Ethereum. It provides a suite of tools for developing smart contracts and deploying them to the blockchain.
Create a new file called truffle-config.js
in the root directory and add the following code:
module.exports = {
networks: {
development: {
host: "127.0.0.1",
port: 8545,
network_id: "*", // Match any network id
},
},
compilers: {
solc: {
version: "0.8.0",
},
},
};
This configuration file specifies the development network and the Solidity compiler version.
Compiling and Deploying Smart Contract
Now that we have our smart contract and Truffle configuration set up, we can compile and deploy the contract to the blockchain.
First, let’s compile the contract by running the following command:
truffle compile
This will compile the contract and create an output file in the build/contracts
directory.
Next, let’s deploy the contract to the blockchain by running the following command:
truffle migrate
This will deploy the contract to the blockchain and create a new instance of the contract.
Web3 Integration
Now that we have our smart contract deployed to the blockchain, we can integrate it with our web3 application.
Create a new file called web3.js
in the lib directory and add the following code:
import Web3 from "web3";
import messageArtifact from "../build/contracts/Message.json";
const getWeb3 = () =>
new Promise((resolve, reject) => {
window.addEventListener("load", async () => {
if (window.ethereum) {
const web3 = new Web3(window.ethereum);
try {
await window.ethereum.enable();
resolve(web3);
} catch (error) {
reject(error);
}
}
// Legacy dapp browsers...
else if (window.web3) {
const web3 = window.web3;
console.log("Injected web3 detected.");
resolve(web3);
}
// Non-dapp browsers...
else {
console.log("Non-Ethereum browser detected. You should consider trying MetaMask!");
}
});
});
const getContract = async (web3) => {
const networkId = await web3.eth.net.getId();
const deployedNetwork = messageArtifact.networks[networkId];
const contract = new web3.eth.Contract(
messageArtifact.abi,
deployedNetwork && deployedNetwork.address
);
return contract;
};
export { getWeb3, getContract };
This file exports two functions: getWeb3
and getContract
.
The getWeb3
function initializes a new instance of the Web3 class and
returns it. The getContract
the function retrieves the contract instance
from the blockchain and returns it.
Example Component
Now that we have our smart contract and web3 integration set up, we can create a new component that interacts with the contract.
Create a new file called Message.js
in the pages
directory and add the following code:
import React, { useState, useEffect } from "react";
import { getWeb3, getContract } from "../lib/web3";
const Message = () => {
const [web3, setWeb3] = useState(null);
const [contract, setContract] = useState(null);
const [message, setMessage] = useState("");
useEffect(() => {
const init = async () => {
const web3 = await getWeb3();
const contract = await getContract(web3);
setWeb3(web3);
setContract(contract);
};
init();
}, []);
const getMessage = async () => {
const message = await contract.methods.getMessage().call();
setMessage(message);
};
const setMessageValue = async () => {
await contract.methods.setMessage("Hello, world!").send({ from: (await web3.eth.getAccounts())[0] });
getMessage();
};
return (
<div>
<h1>Message</h1>
<p>{message}</p>
<button onClick={getMessage}>Get Message</button>
<button onClick={setMessageValue}>Set Message</button>
</div>
);
};
export default Message;
In this component, we initialize the web3 instance and contract instance
using the getWeb3
and getContract
functions. We then define two functions:
getMessage
and setMessageValue
. The getMessage
function retrieves the message
from the contract and sets it in the message
state. The setMessageValue
function sets a new message value in the contract and retrieves the updated
message value.
Conclusion
In this tutorial, we learned how to build web3 applications with NextJS, Solidity, and Truffle. We covered the basics of creating a Solidity smart contract, compiling and deploying the contract with Truffle, integrating the contract with a web3 application using the web3.js library, and creating a component that interacts with the contract. With these tools and techniques, you can build powerful decentralized applications that interact with the Ethereum blockchain.
Web3 development is a rapidly evolving field, and there are many exciting developments on the horizon. As blockchain technology continues to mature, we can expect to see more sophisticated and powerful web3 applications being built.