TransWikia.com

Unhandled Rejection (TypeError): this.web3.eth is undefined

Ethereum Asked by Chan Austin on November 29, 2020

My getWeb3.js file:

import Web3 from 'web3'

export default async () => {
    var web3Provider = null;
    if (typeof window.ethereum !== "undefined") {
        web3 = new Web3(window.ethereum)
        try {
            // Request account access if needed
            await window.ethereum.enable()
            // Acccounts now exposed
        } catch (error) {
            // User denied account access...
            console.log("MetaMask cannot be enabled!")
        }
    }
    // Legacy dapp browsers...
    else if (window.web3) {
        web3Provider = new Web3(window.web3.currentProvider);
    }
    // Non-dapp browsers...we use ganache
    else {
        console.log('Non-Ethereum browser detected. You should consider trying MetaMask!');
        web3Provider = new Web3.providers.HttpProvider('http://localhost:7545');
        console.log("ganache")
    }
    return web3
}

Here is how I call getWeb3, it always complain on this var accounts = await this.web3.eth.getAccounts(), saying this.web3.eth is undefined

export default class PaypalContract {
  constructor() {
    console.log(instance)
    if (!instance) {
      

```
  instance = this
  this.web3 = getWeb3()
  console.log("web3 init:",this.web3)
  this.contract = contract(PaypalContractMeta)
  this.contract.setProvider(this.web3)
  this.usdtcontract = contract(usdtContractMeta)
  this.usdtcontract.setProvider(this.web3)
}

return instance
```

  }

  async payToContract(coin_address,recipient,price,order_id) {
    //const { eth: { accounts: [ account ] } } = this.web3

```
var accounts = await this.web3.eth.getAccounts()
var account = accounts[0]
console.log('account:',account)
console.log("coin address:",coin_address)
const coincontractInstance = await this.usdtcontract.at(coin_address)
const contractInstance = await this.contract.deployed()
var priceUnit = this.web3.utils.toBN(price).mul(this.web3.utils.toBN(this.web3.utils.toWei("1")))
await coincontractInstance.approve(contractInstance.address,priceUnit,{from: account})
await contractInstance.deposit(coin_address,recipient,priceUnit,order_id,{ from: account })
await contractInstance.setExpiryDate(order_id,0,{ from: account })
```

  }

2 Answers

This is solved.

I should not use async mode and await in getWeb3, removal of them can solve the problem.

Correct answer by Chan Austin on November 29, 2020

  1. You are using poor naming conventions. The provider in Web3 is what you use to build a Web3 instance, such as window.web3.currentProvider or window.ethereum.
  2. window.ethereum is not a Web3 instance, it is a Web3 provider. So you have to do: web3Provider = new Web3(window.ethereum);.
  3. When you have a contract, you need to tell it to use the Web3 instance of your choice this.contract.setProvider(this.web3);.
  4. You ought to test if (typeof window.ethereum !== "undefined") { instead.
  5. Also don't ethereum.enable() immediately, but instead do it after your user has done an action that warrants it like "login" or "send a tx". Just loading your page does not warrant it.
  6. Instead of using 10**18, you can use web3.utils.toWei(1).
  7. Don't use Javascript numbers but BN big numbers so that all digits are preserved: var priceUnit = web3.utils.toBN(price).mul(web3.utils.toBN(web3.utils.toWei("1")));.
  8. When you await a contract action like await coincontractInstance.approve(, look into the object that is returned, and in particular the receipt.status to make sure it went through before blindly following on with the next tx.

Cheers

Answered by Xavier Leprêtre B9lab on November 29, 2020

Add your own answers!

Ask a Question

Get help from others!

© 2024 TransWikia.com. All rights reserved. Sites we Love: PCI Database, UKBizDB, Menu Kuliner, Sharing RPP