22

Except for one unanswered question from last November, I cannot find anything . . . .

I am revamping some typescript code (in Visual Studio) for the Metamask January change. Previously, I was using web3. Now I am just trying to use window.ethereum.

I cannot find a DefinitelyTyped (or any other types) file with type declarations.

I fear that this is really something simple/stupid but I'm totally at a loss.

2
  • any solution, my window is null Jun 12, 2021 at 3:24
  • 1
    Where did you get the type EthereumProvider in the first place?
    – Qwerty
    May 19, 2022 at 0:40

9 Answers 9

11

If you're doing this in React with CRA or ViteJS or even Remix-Run:

File: src/vite-env.d.ts

/// <reference types="vite/client" />

interface Window {
  ethereum: any;
}

File: src/react-app-env.d.ts

/// <reference types="react-scripts" />

interface Window {
  ethereum: any;
}

File: /remix.env.d.ts

/// <reference types="@remix-run/dev" />
/// <reference types="@remix-run/node" />

interface Window {
  ethereum: any;
}

In case you are using ethers.js, you should consider using the type import('ethers').Eip1193Provider instead of any

8

You can create a global.d.ts file at the root level of your project & type window.ethereum this way instead of using any.

declare global {
  interface Window {
    ethereum?: import('ethers').providers.ExternalProvider;
  }
}

If you're using ethers v6, then your type definitions would be

declare global {
  interface Window {
    ethereum?: import('ethers').Eip1193Provider
  }
}

Note the use of the optional type ?, forcing you to check if the browser indeed has metamask.

5

Use (window as any).ethereum.request to get around type checking.

4

You can try adding the following line at the beginning:

declare let window: any;

Then, you can do stuff like this:

import Web3 from 'web3';

//...

   let web3: Web3;
   if (window.ethereum) {
      web3 = new Web3(window.ethereum);
      // Ask User permission to connect to Metamask
      await window.ethereum.enable();
   };
3

The answers thus far have been for ethers v5, here is how you do it for v6...

import { ethers } from "ethers";
import { BrowserProvider, Eip1193Provider } from "ethers/types/providers";

declare global {
  interface Window {
    ethereum: Eip1193Provider & BrowserProvider;
  }
}
0

Guys if you are using React with TypeScript just do this and everything goes right! Trust me :)

  1. create global.d.ts in the root of your project and put this code

     declare global {
         interface Window {
             ethereum: import('ethers').providers.ExternalProvider;
         }
     }
     
  2. Then in react-app-env.d.ts put this code

     interface Window {
         ethereum: any;
     }
     

Now you have the code snippet and no error!

0

try with this.

interface CustomWindow extends Window {
  ethereum?: any;
}

declare const window: CustomWindow;
0

Apparently, the desired type lives in @metamask/providers NPM library . I've solved the type issue by installing this lib in devDependencies:

npm i -D @metamask/providers

and extended a global Window interface

import { MetaMaskInpageProvider } from '@metamask/providers';

declare global {
  interface Window {
    ethereum?: MetaMaskInpageProvider;
  }
}

in globals.d.ts.

0

If you use Viem with Hardhat it might help if you create:

src/types/index.d.ts file:

export {}

type EthereumProvider = { request(...args: any): Promise<any> };

declare global {
    interface Window {
        ethereum?: EthereumProvider;
    }
}

Make sure to include export {} otherwise it wouldn't seem to work for me. Here's an article that could be helpful when debugging types: https://bobbyhadz.com/blog/typescript-property-does-not-exist-on-type-window.

The definition of EthereumProvider is actually copied directly from Viem source code:

type EthereumProvider = { request(...args: any): Promise<any> }

// ...

export type CustomTransport = Transport<
  'custom',
  {},
  EthereumProvider['request']
>

Source: viem/clients/transports/custom.ts.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.