33
loading...
This website collects cookies to deliver better user experience
Since the backend code(smart contracts) of a dApp is on a decentralized network, the dApp is free from control and can not be modified/removed by a centralized source. Developers and creators can trust the underlying infrastructure without worrying about being terminated or censored.
Once a smart contract is deployed to the Ethereum network, no one can change it. Therefore, users can trust how it will work since even the person deploying the contract can't change it.
All the smart contracts on Ethereum are public and accessible; it's an open-source ecosystem. This open-source nature allows for composability, so this means that you can re-use parts of the codes from others. You can look at all the smart contracts from Etherscan; here is an example smart contract.
The backend of the dApp is the smart contract. Smart contracts are self-executing computer programs stored inside the blockchain, on Ethereum they are all open and accessible. You can look at them from Etherscan; here is an example of a smart contract. Another important note on smart contracts is that no one can change it once a smart contract is changed. Solidity is one of the most popular smart contract languages for Ethereum.
The frontend of the dApp can be written in any language that can talk to the backend. The frontend can then be hosted on a centralized service or a decentralized service.
Create a project folder and setup a react app
npx create-react-app edas-dapp
cd edas-dapp
npm start
Install the ethers.js libary
with npm:
npm install ethers
with yarn:
yarn add ethers
The following code creates a button that the user can click which will prompt the user to connect to Metamask wallet. I have added the comments to explain what's going on. Add the following code to App.js.
import './App.css';
import { useEffect, useState } from 'react';
const App = () => {
//state variable to store user's public wallet
const [currentAccount, setCurrentAccount] = useState("");
// check wallet connection when the page loads
const checkIfWalletIsConnected = async () => {
// access to window.ethereum
const {ethereum} = window;
//check if user has metamask
if(!ethereum) {
alert("Make sure you have metamask");
return;
}
//get the wallet account
const accounts = await ethereum.request({method: 'eth_accounts'});
//get the first account
if(accounts.length !== 0){
const account = accounts[0];
console.log("Found account:", account);
//set the account as a state
setCurrentAccount(account);
}
else{
console.log("No account");
}
}
// connect to wallet
const connectWallet = async () => {
try {
// get the wallet
const {ethereum} = window;
// there is no wallet extension
if(!ethereum) {
alert("Opps, looks like there is no wallet!");
return;
}
const currentNetwork = ethereum.networkVersion;
console.log("Current network", currentNetwork);
// request access to account
const accounts = await ethereum.request({ method: "eth_requestAccounts"});
//set the account in the state
setCurrentAccount(accounts[0]);
}
catch( error){
console.log(error);
}
}
//run function checkIfWalletIsConnected when the page loads
useEffect(()=> {
checkIfWalletIsConnected();
}, []);
//connect to wallet
const walletNotConnected = () => (
<button onClick={connectWallet} className="connect-to-wallet-button">
Connect to Wallet
</button>
);
//wallet connected
const walletConnected = () => (
<div>
<p>Connected to the wallet</p>
</div>
);
return (
<div className="App">
<div style={{display: 'flex', justifyContent:'center', height: '50px'}}>
{currentAccount === "" ? walletNotConnected() : walletConnected()}
<br />
</div>
</div>
);
};
export default App;
Now the following code will connect to the latest active network. So if the user was on the Ethereum Mainnet it will connect to Ethereum, if the user was on the Rinkeby Test Network it will connect to that. However, in many cases we need to the user to connect to a certain network.
You can check to see which network the user is connected to and prompt the user with a message to change the network they are on. Modify connectWallet in App.js as below.
const connectWallet = async () => {
try {
const {ethereum} = window;
if(!ethereum) {
alert("Opps, looks like there is no wallet!");
return;
}
const currentNetwork = ethereum.networkVersion;
console.log("Current network", currentNetwork);
//check which network the wallet is connected on
if(currentNetwork != 4){
// prompt user with a message to switch to network 4 which is the rinkeby network on metamask
alert("Opps, only works on Rinkeby! Please change your //network :)");
return;
};
const accounts = await ethereum.request({ method: "eth_requestAccounts"});
setCurrentAccount(accounts[0]);
}
catch( error){
console.log(error);
}
}
A better way to do this is to directly prompt the user with the request to switch the network. Instead of asking the user to change the network they are connected on. Change the if statement with the following lines.
// request to switch the network
const tx = await ethereum.request({method: 'wallet_switchEthereumChain', params:[{chainId:
'0x4'}]}).catch()
if (tx) {
console.log(tx)
}
By default Chain 4 is already defined in Metamask. You can also prompt the user to add a new network which is not already defined. Here is how you can add the Avalanche network. Add the following piece of code just before requesting access to the account.
// define avax network values
const avax_mainnet = [{
chainId: '0xA86A',
chainName: 'Avalanche Mainnet C-Chain',
nativeCurrency: {
name: 'Avalanche',
symbol: 'AVAX',
decimals: 18
},
rpcUrls: ['https://api.avax.network/ext/bc/C/rpc'],
blockExplorerUrls: ['https://snowtrace.io/']
}]
// request to add the new network
const tx = await ethereum.request({method: 'wallet_addEthereumChain', params:avax_mainnet}).catch()
if (tx) {
console.log(tx)
}