1

How to (in Drizzle) get the account currently selected in Metamask?

I have a function to call a method set of the smart contract, but currently account is "hardcoded":

  setValue = value => {
    const { drizzle, drizzleState } = this.props;
    const contract = drizzle.contracts.PartProduction;

    // let drizzle know we want to call the `set` method with `value`
    const stackId = contract.methods["set"].cacheSend(value, {
      from: drizzleState.accounts[0]
    });

    // save the `stackId` for later reference
    this.setState({ stackId });
  };

i.e. in: from: drizzleState.accounts[0].

How to change the from: field to use the account selected in Metamask?

TylerH
  • 20,799
  • 66
  • 75
  • 101
shogitai
  • 1,823
  • 1
  • 23
  • 50

3 Answers3

1

drizzleState.accounts[0] itself signifies the account selected in Metamask as the default account. If you select some other account in Metamask, the value of drizzleState.accounts[0] changes with it automatically.

TylerH
  • 20,799
  • 66
  • 75
  • 101
Kombo
  • 274
  • 1
  • 5
  • 16
  • 1
    I've been able to reproduce the problem. If I switch accounts in metamask, drizzleState.accounts and drizzleState.accountBalances stay the same. – Jorge M. Londoño P. May 05 '20 at 18:59
  • @JorgeM.LondoñoP. have you setup the problem set correctly? make sure you have setup the web3 attribute of drizzleOptions correctly, with a fallback value as well.. and also setup the account "polls" to a certain value (like 1500). – Kombo Jul 20 '20 at 05:26
  • I'm testing it and yet `drizzleState` does not change. – SalahAdDin Sep 01 '20 at 19:37
  • how are you injecting the drizzle object? use DrizzleProvider to inject drizzle and also to subscribe to changes in current block and account changes? – Kombo Sep 02 '20 at 05:52
0

I wrote an example Component that demonstrates the problem with both, the AccountData component, and the account information in drizzleState. I also provide a workaround using the web3 API directly.

import React, { useState, useEffect } from "react";
import { newContextComponents } from "@drizzle/react-components";

const { AccountData } = newContextComponents;

const AccountChangeDetection = ({ drizzle, drizzleState }) => {

  const [ drizzleAcc, setDrizzleAcc ] = useState(drizzleState.accounts[0]);
  const [ drizzleBal, setDrizzleBal ] = useState(drizzleState.accountBalances[drizzleState.accounts[0]]);

  const [ web3Acc, setWeb3Acc ] = useState(null);
  const [ web3Bal, setWeb3Bal ] = useState(null);


  useEffect(() => {

    function loadWeb3Data(web3) {
      web3.eth.getAccounts()
      .then( accounts => {
        setWeb3Acc(accounts[0]);
        web3.eth.getBalance(accounts[0])
        .then(setWeb3Bal);
      } );
    }

    async function listenMMAccount() {
      window.ethereum.on("accountsChanged", async function () {
        // console.log("Account changed");
        // console.log(drizzleState.accountBalances[drizzleState.accounts[0]]);
        setDrizzleAcc(drizzleState.accounts[0]);
        setDrizzleBal(drizzleState.accountBalances[drizzleState.accounts[0]]);
        loadWeb3Data(drizzle.web3);
      });
    }

    loadWeb3Data(drizzle.web3);
    listenMMAccount();
  });

  return (
    <div>

      <strong>AccountData</strong>
      <AccountData
        drizzle={drizzle}
        drizzleState={drizzleState}
        accountIndex={0}
        units="ether"
        precision={3}
      />

      <table>
        <tbody>
          <tr>
            <td>Drizzle</td>
            <td>{drizzleAcc}</td>
            <td>{drizzleBal}</td>
          </tr>
          <tr>
            <td>Web3</td>
            <td>{web3Acc}</td>
            <td>{web3Bal}</td>
          </tr>
        </tbody>
      </table>
    </div>
  );
};

export default AccountChangeDetection;
0

The best way is to add an option for the drizzle option so that it can detect web3 objects in the browser.

Edit the drizzle option code to below

  web3: {
    block: false,
    customProvider: new Web3(Web3.givenProvider || "ws://localhost:8545"),
    // customProvider: new Web3("wss://kovan.infura.io/ws/v3/5b2a79e624554c8ab922b9a84b076645"),

  },