Search code examples
solidityweb3jsmetamask

Problems with metamask/web3 connection


I want to understand how front-end of smart contracts works. I'm trying to run this code on my computer but metamask is constantly undefined.

Could you please explain why it happens in details. Why it does not connect to metamask provider?

        <script>
            $(".sendButton").click(function(){
                let Web3 = require('web3');
                if (typeof web3 !== 'undefined'){
                    web3 = new Web3(web3.currentProvider);
                }
                else {
                    alert('You have to install MetaMask !');
                }
                const abi = some abi
                const contractAddress = "some contract";
                let MyContract = web3.eth.contract(abi);
                let myContractInstance = MyContract.at(contractAddress);
                let functionData = myContractInstance.setMessage.getData($('#inputString').val());
                web3.eth.sendTransaction({
                        to:contractAddress,
                        from:web3.eth.accounts[0],
                        data: functionData,
                    },
                    function(error, response){
                        console.log(response);
                    });
            });
        </script>
    </body>
</html>

Solution

  • If you're locally serving an HTML file, MetaMask will not be able to communicate with your DApp. A web server is required. From the MetaMask Developer Docs:

    Due to browser security restrictions, we can't communicate with dapps running on file://. Please use a local server for development.

    Also, please note the MetaMask breaking change which will no longer automatically inject web3 into the browser. Instead users must grant the DApp access to their accounts via accepting a prompt dialog created by window.ethereum.enable(). See the below code for handling MetaMask in both modern DApp browsers as well as legacy DApp browsers.

    // Modern DApp Browsers
    if (window.ethereum) {
       web3 = new Web3(window.ethereum);
       try { 
          window.ethereum.enable().then(function() {
              // User has allowed account access to DApp...
          });
       } catch(e) {
          // User has denied account access to DApp...
       }
    }
    // Legacy DApp Browsers
    else if (window.web3) {
        web3 = new Web3(web3.currentProvider);
    }
    // Non-DApp Browsers
    else {
        alert('You have to install MetaMask !');
    }