How to connect ethers.js with metamask?

25,287

Solution 1

Using ethers.js to interact with Metamask

const provider = new ethers.providers.Web3Provider(window.ethereum, "any");
// Prompt user for account connections
await provider.send("eth_requestAccounts", []);
const signer = provider.getSigner();
console.log("Account:", await signer.getAddress());

Solution 2

I too have found this confusing. According to the ethers.js documentation for Metamask the following is required:

const provider = new ethers.providers.Web3Provider(web3.currentProvider);
const signer = provider.getSigner();

But this causes an error: specifically the web3.currentProvider not being recognised.

The Ethers.js github issue log has a similar complaint at Issue #433. Using this as a guide I've therefore used window.ethereum in place of web3.currentProvider and also included the .enable() beforehand:

await window.ethereum.enable()
const provider = new ethers.providers.Web3Provider(window.ethereum);
const signer = provider.getSigner();

Or alternatively (outside of an async function):

let provider;
window.ethereum.enable().then(provider = new ethers.providers.Web3Provider(window.ethereum));
const signer = provider.getSigner();

This clears the error, and ensures that Metamask asks for permission prior to connecting to the browser/DApp.

Solution 3

window.ethereum.enable() is deprecated.

You should use:

ethereum.request({ method: 'eth_requestAccounts' })
Share:
25,287
Admin
Author by

Admin

Updated on November 21, 2021

Comments

  • Admin
    Admin over 2 years

    I am using the ethers.js documentation: https://docs.ethers.io/ethers.js/html/cookbook-providers.html . I am getting the error when setting up the provider -: Uncaught ReferenceError: web3 is not defined I want to connect my Decentralized Application with the metamask. For that I am trying to connect the metamask with ethers.js by setting the provider as per the documentation. I have used provider = new ethers.providers.Web3Provider(web3.currentProvider). But it throws error for the web3 object in the code. This code is exactly as per the documentation. But still isn't working.

            //let provider = new ethers.getDefaultProvider('rinkeby');
            let provider = new ethers.providers.Web3Provider(web3.currentProvider);
            let contract;
            let wallet;
            let abi = [
        {
            "anonymous": false,
            "inputs": [
                {
                    "indexed": true,
                    "internalType": "address",
                    "name": "account",
                    "type": "address"
                },
                {
                    "indexed": false,
                    "internalType": "string",
                    "name": "pwd",
                    "type": "string"
                }
            ],
            "name": "Pwd_Assigned",
            "type": "event"
        },
        {
            "inputs": [
                {
                    "internalType": "string",
                    "name": "_passwd",
                    "type": "string"
                }
            ],
            "name": "setPwd",
            "outputs": [
                {
                    "internalType": "bool",
                    "name": "success",
                    "type": "bool"
                }
            ],
            "stateMutability": "nonpayable",
            "type": "function"
        },
        {
            "inputs": [
                {
                    "internalType": "string",
                    "name": "_uname",
                    "type": "string"
                }
            ],
            "name": "setUname",
            "outputs": [
                {
                    "internalType": "bool",
                    "name": "success",
                    "type": "bool"
                }
            ],
            "stateMutability": "nonpayable",
            "type": "function"
        },
        {
            "inputs": [
                {
                    "internalType": "string",
                    "name": "_uType",
                    "type": "string"
                }
            ],
            "name": "setUtype",
            "outputs": [
                {
                    "internalType": "bool",
                    "name": "success",
                    "type": "bool"
                }
            ],
            "stateMutability": "nonpayable",
            "type": "function"
        },
        {
            "anonymous": false,
            "inputs": [
                {
                    "indexed": true,
                    "internalType": "address",
                    "name": "account",
                    "type": "address"
                },
                {
                    "indexed": false,
                    "internalType": "string",
                    "name": "utype",
                    "type": "string"
                }
            ],
            "name": "Type_Assigned",
            "type": "event"
        },
        {
            "anonymous": false,
            "inputs": [
                {
                    "indexed": true,
                    "internalType": "address",
                    "name": "account",
                    "type": "address"
                },
                {
                    "indexed": false,
                    "internalType": "string",
                    "name": "uname",
                    "type": "string"
                }
            ],
            "name": "Username_Assigned",
            "type": "event"
        },
        {
            "inputs": [],
            "name": "getContractName",
            "outputs": [
                {
                    "internalType": "string",
                    "name": "_name",
                    "type": "string"
                }
            ],
            "stateMutability": "view",
            "type": "function"
        },
        {
            "inputs": [],
            "name": "name",
            "outputs": [
                {
                    "internalType": "string",
                    "name": "",
                    "type": "string"
                }
            ],
            "stateMutability": "view",
            "type": "function"
        },
        {
            "inputs": [
                {
                    "internalType": "address",
                    "name": "",
                    "type": "address"
                }
            ],
            "name": "pwd",
            "outputs": [
                {
                    "internalType": "string",
                    "name": "",
                    "type": "string"
                }
            ],
            "stateMutability": "view",
            "type": "function"
        },
        {
            "inputs": [],
            "name": "symbol",
            "outputs": [
                {
                    "internalType": "string",
                    "name": "",
                    "type": "string"
                }
            ],
            "stateMutability": "view",
            "type": "function"
        },
        {
            "inputs": [
                {
                    "internalType": "address",
                    "name": "",
                    "type": "address"
                }
            ],
            "name": "uname",
            "outputs": [
                {
                    "internalType": "string",
                    "name": "",
                    "type": "string"
                }
            ],
            "stateMutability": "view",
            "type": "function"
        },
        {
            "inputs": [
                {
                    "internalType": "address",
                    "name": "",
                    "type": "address"
                }
            ],
            "name": "uType",
            "outputs": [
                {
                    "internalType": "string",
                    "name": "",
                    "type": "string"
                }
            ],
            "stateMutability": "view",
            "type": "function"
        }
    ];
            let contractAddress = "0xECFFa8439Fa4DC64388227fA43a420449E895c3f"; // for rinkeby
            let AidTokenAbi = [
                {
                    "inputs": [
                        {
                            "internalType": "uint256",
                            "name": "_initialSupply",
                            "type": "uint256"
                        }
                    ],
                    "stateMutability": "nonpayable",
                    "type": "constructor"
                },
                {
                    "anonymous": false,
                    "inputs": [
                        {
                            "indexed": true,
                            "internalType": "address",
                            "name": "_owner",
                            "type": "address"
                        },
                        {
                            "indexed": true,
                            "internalType": "address",
                            "name": "_spender",
                            "type": "address"
                        },
                        {
                            "indexed": false,
                            "internalType": "uint256",
                            "name": "_value",
                            "type": "uint256"
                        }
                    ],
                    "name": "Approval",
                    "type": "event"
                },
                {
                    "inputs": [
                        {
                            "internalType": "address",
                            "name": "_spender",
                            "type": "address"
                        },
                        {
                            "internalType": "uint256",
                            "name": "_value",
                            "type": "uint256"
                        }
                    ],
                    "name": "approve",
                    "outputs": [
                        {
                            "internalType": "bool",
                            "name": "success",
                            "type": "bool"
                        }
                    ],
                    "stateMutability": "payable",
                    "type": "function"
                },
                {
                    "inputs": [
                        {
                            "internalType": "address",
                            "name": "_to",
                            "type": "address"
                        },
                        {
                            "internalType": "uint256",
                            "name": "_value",
                            "type": "uint256"
                        }
                    ],
                    "name": "transfer",
                    "outputs": [
                        {
                            "internalType": "bool",
                            "name": "success",
                            "type": "bool"
                        }
                    ],
                    "stateMutability": "payable",
                    "type": "function"
                },
                {
                    "anonymous": false,
                    "inputs": [
                        {
                            "indexed": true,
                            "internalType": "address",
                            "name": "_from",
                            "type": "address"
                        },
                        {
                            "indexed": true,
                            "internalType": "address",
                            "name": "_to",
                            "type": "address"
                        },
                        {
                            "indexed": false,
                            "internalType": "uint256",
                            "name": "_value",
                            "type": "uint256"
                        }
                    ],
                    "name": "Transfer",
                    "type": "event"
                },
                {
                    "inputs": [
                        {
                            "internalType": "address",
                            "name": "_from",
                            "type": "address"
                        },
                        {
                            "internalType": "address",
                            "name": "_to",
                            "type": "address"
                        },
                        {
                            "internalType": "uint256",
                            "name": "_value",
                            "type": "uint256"
                        }
                    ],
                    "name": "transferFrom",
                    "outputs": [
                        {
                            "internalType": "bool",
                            "name": "success",
                            "type": "bool"
                        }
                    ],
                    "stateMutability": "payable",
                    "type": "function"
                },
                {
                    "inputs": [
                        {
                            "internalType": "address",
                            "name": "",
                            "type": "address"
                        },
                        {
                            "internalType": "address",
                            "name": "",
                            "type": "address"
                        }
                    ],
                    "name": "allowance",
                    "outputs": [
                        {
                            "internalType": "uint256",
                            "name": "",
                            "type": "uint256"
                        }
                    ],
                    "stateMutability": "view",
                    "type": "function"
                },
                {
                    "inputs": [
                        {
                            "internalType": "address",
                            "name": "",
                            "type": "address"
                        }
                    ],
                    "name": "balanceOf",
                    "outputs": [
                        {
                            "internalType": "uint256",
                            "name": "",
                            "type": "uint256"
                        }
                    ],
                    "stateMutability": "view",
                    "type": "function"
                },
                {
                    "inputs": [],
                    "name": "name",
                    "outputs": [
                        {
                            "internalType": "string",
                            "name": "",
                            "type": "string"
                        }
                    ],
                    "stateMutability": "view",
                    "type": "function"
                },
                {
                    "inputs": [],
                    "name": "standard",
                    "outputs": [
                        {
                            "internalType": "string",
                            "name": "",
                            "type": "string"
                        }
                    ],
                    "stateMutability": "view",
                    "type": "function"
                },
                {
                    "inputs": [],
                    "name": "symbol",
                    "outputs": [
                        {
                            "internalType": "string",
                            "name": "",
                            "type": "string"
                        }
                    ],
                    "stateMutability": "view",
                    "type": "function"
                },
                {
                    "inputs": [],
                    "name": "tokensSold",
                    "outputs": [
                        {
                            "internalType": "uint256",
                            "name": "",
                            "type": "uint256"
                        }
                    ],
                    "stateMutability": "view",
                    "type": "function"
                },
                {
                    "inputs": [],
                    "name": "totalSupply",
                    "outputs": [
                        {
                            "internalType": "uint256",
                            "name": "",
                            "type": "uint256"
                        }
                    ],
                    "stateMutability": "view",
                    "type": "function"
                }
            ];
            let AidtokenAddress = "0x17b0e97DF8217a984294De6bDbbb9D7020190479";
            let AidTokenContract;
            let signer = provider.getSigner();
            let usr_account;
    
            function loadWallet(){
                signer.getAddress().then(async(res)=>{
                    usr_account = res;
                    await console.log(usr_account);
                });
            }
    
            // async function setProvider(){
            //   provider = await new ethers.providers.JsonRpcProvider('http://127.0.0.1:8545');
            // }
    
            function getContract(){
                contract = new ethers.Contract(contractAddress,abi, signer);
                console.log(contract.functions);
            }
            
            function getTokenContract(){
                AidTokenContract = new ethers.Contract(AidtokenAddress,AidTokenAbi, signer);
            }
            
            async function getName(){
                // var name = await contract.functions.getContractName();
                // console.log(name);
                await contract.name().then(async (res)=>{
                  await console.log(res);
                });
            }
    
            async function setInfo(event){
                event.preventDefault();
                loadWallet();
                getContract();
                var uname = document.getElementById('uname').value;
                var pwd = document.getElementById('psw').value;
                var utype = document.getElementById('utype').value;
                await contract.functions.setUname(uname).then(async(res)=>{
                    console.log(res);
                });
                await contract.functions.setUtype(utype).then(async(res)=>{
                    console.log(res);
                });
                await contract.functions.setPwd(pwd).then(async(res)=>{
                    console.log(res);
                });
                //getInfo();
            }
    
            async function getInfo(event){
              event.preventDefault();
                var uname;
                var utype;
                var pwd;
                loadWallet();
                getContract();
                await contract.functions.uname(usr_account).then(async(res)=>{
                    uname=res;
                    console.log(res);
                });
                await contract.functions.uType(usr_account).then(async(res)=>{
                    utype = res;
                    console.log(res);
                });
                await contract.functions.pwd(usr_account).then(async(res)=>{
                    pwd=res
                    console.log(res);
                });
            }
    
            async function transfer(event){
                event.preventDefault();
                loadWallet();
                getTokenContract();
                await console.log(".....");
                var numberOfTokens = document.getElementById('numberOfTokens').value;
                await AidTokenContract.functions.transfer(numberOfTokens,{
                    from: usr_account,
                    gasLimit: 500000
                });
            }
    
            //setProvider();
            loadWallet();
            getContract();
            //getName();
    
            // setInfo();
            //getInfo();
            
    <html>
      <head>
        <script src="https://cdnjs.cloudflare.com/ajax/libs/qrcode-generator/1.4.3/qrcode.min.js"></script>
        <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.5.2/jquery.min.js"></script>
        <!-- <script src="js/web3.min.js"></script> -->
        <script charset="utf-8"
                src="https://cdn.ethers.io/scripts/ethers-v4.min.js" type="text/javascript">
            </script>
        <script src="https://cdnjs.cloudflare.com/ajax/libs/require.js/2.3.6/require.js"></script>
      </head>
      <body>
    
        <form onsubmit="setInfo(event)">
            <div>
                      <h1>Register</h1>
                      <p>Please fill in this form to create an account.</p>
                      <hr>
                    <br>
                      <label for="uname"><b>User Name</b></label>
                      <input type="text" placeholder="Enter Username" id="uname" required>
                    <br>
                      <label for="utype">Choose a User type:</label>
                      <select id="utype" name="utype">
                            <option value="Donor">Donor</option>
                            <option value="NGO">NGO</option>
                            <option value="Government">Government</option>
                      </select>
                  <br>
                      <label for="psw"><b>Password</b></label>
                      <input type="password" placeholder="Enter Password" id="psw" required>
                  
                      <!-- <label for="psw-repeat"><b>Repeat Password</b></label>
                      <input type="password" placeholder="Repeat Password" name="psw-repeat" required>
                      <hr> -->
                  
                      <p>By creating an account you agree to our <a href="#">Terms & Privacy</a>.</p>
                      <button type="submit" id="registerbtn">Register</button>
            </div>
                  
                    <div class="container signin">
                      <p>Already have an account? <a href="#">Sign in</a>.</p>
                    </div>
        </form>
    <br><br>
        <form onsubmit="getInfo(event)">
            <button type="submit" >Get Info</button>
        </form>
    
        <form onsubmit="transfer(event)">
          <input id="numberOfTokens" type="number" name="number" value="1" min="1" pattern="[0-9]">
          <button type="submit" >Donate</button>
      </form>
      <!-- <script src="https://cdn.jsdelivr.net/gh/ethereum/web3.js/dist/web3.min.js"></script> -->
      
        
        <script src="js/app.js"></script>
    
      </body>
    </html>

    Getting this error while setting the provider-Uncaught ReferenceError: web3js is not defined

  • Thomas Fox
    Thomas Fox almost 3 years
    The method "ethereum.enable()" has now been deprecated in place of "ethereum.send('eth_requestAccounts')". As per the following 'eips.ethereum.org/EIPS/eip-1102'
  • user2342558
    user2342558 over 2 years
    Thanks, can you share the doc url for that?
  • whileone
    whileone over 2 years
    Note that you also need to call window. ethereum.enable() first.
  • user2342558
    user2342558 over 2 years
    @whileone why does it is needed?
  • Do Async
    Do Async over 2 years
    The method ethereum.enable() was deprecated in place of .send('eth_requestAccounts'), as per eips.ethereum.org/EIPS/eip-1102
  • Do Async
    Do Async over 2 years
    Ethers docs for Metamask should be updated
  • Admin
    Admin over 2 years
    Your answer could be improved with additional supporting information. Please edit to add further details, such as citations or documentation, so that others can confirm that your answer is correct. You can find more information on how to write good answers in the help center.