Metamask replacement for your E2E tests.

Overview

Headless Web3 Provider

Playwright Tests

Metamask replacement for your E2E tests. Why "headless"? Because it doesn't have a visual interface, reject (or accept) transactions direcly from your code!

Installation

npm i -D headless-web3-provider

About

The library emulates a Web3 wallet behaviour like Metamask. It is useful for E2E testing if your application sends transactions or uses ethereum authentication. The library allows to programatically accept or decline operations (switching a network, connecting a wallet, sending a transaction).

Supported methods

Method Confirmable
eth_getBlockByNumber No
eth_requestAccounts Yes
eth_accounts Yes
eth_chainId No
net_version No
eth_sendTransaction Yes
wallet_addEthereumChain Yes
wallet_switchEthereumChain Yes

Examples

Playwright

Below given a simple example. More complex scenarios you can find in tests/e2e folder.

Setup (add a fixture):

// tests/fixtures.js
import { test as base } from '@playwright/test'
import { injectHeadlessWeb3Provider } from 'headless-web3-provider'

export const test = base.extend({
  signers: [process.env.PRIVATE_KEY],
  
  injectWeb3Provider: async ({ page, signers }, use) => {
    await use((privateKeys = signers) => (
      injectHeadlessWeb3Provider(
        page,
        privateKeys,            // Private keys that you want to use in tests
        1337,                   // Chain ID - 1337 is local dev chain id
        'http://localhost:8545' // RPC URL - all requests are sent to this endpoint
      )
    ))
  },
})

Usage:

// tests/e2e/example.spec.js
import { test } from '../fixtures'

test('connect the wallet', async ({ page, injectWeb3Provider }) => {
  // Inject window.ethereum instance
  const wallet = await injectWeb3Provider()
  
  await page.goto('https://metamask.github.io/test-dapp/')

  // Request connecting the wallet
  await page.locator('text=Connect').click()

  // You can either authorize or reject the request
  await wallet.authorize(Web3RequestKind.RequestAccounts)

  // Verify if the wallet is really connected
  await test.expect(page.locator('text=Connected')).toBeVisible()
  await test.expect(page.locator('text=0x8b3a08b22d25c60e4b2bfd984e331568eca4c299')).toBeVisible()
})

Jest

Add a helper script for injecting the ethereum provider instance.

// tests/web3-helper.ts
import { Wallet } from 'ethers'
import { makeHeadlessWeb3Provider, Web3ProviderBackend } from 'headless-web3-provider'

export function injectWeb3Provider(): [[Wallet, ...Wallet[]], Web3ProviderBackend] {

  // Dynamically preconfigure the wallets that will be used in tests
  const wallets = Array(2).fill(0).map(() => Wallet.createRandom()) as [Wallet, Wallet]

  // Create the instance
  let web3Manager: Web3ProviderBackend = makeHeadlessWeb3Provider(
    wallets.map((wallet) => wallet.privateKey),
    1337,                   // Chain ID - 1337 is local dev chain id
    'http://localhost:8545' // RPC URL - all requests are sent to this endpoint
  )

  // Expose the instance
  // @ts-ignore-error
  window.ethereum = web3Manager

  // Make it usable in tests
  return [wallets, web3Manager]
}
// AccountConnect.test.ts
import { act, render, screen } from '@testing-library/react'
import type { Wallet } from 'ethers'
import { Web3ProviderBackend, Web3RequestKind } from 'headless-web3-provider'
import userEvent from '@testing-library/user-event'
import { injectWeb3Provider } from 'tests/web3-helper' // Our just created helper script
import AccountConnect from './AccountConnect'

describe('<AccountConnect />', () => {
  let wallets: [Wallet, ...Wallet[]]
  let web3Manager: Web3ProviderBackend

  beforeEach(() => {
    // Inject window.ethereum instance
    ;[wallets, web3Manager] = injectWeb3Provider()
  })

  it('renders user address after connecting', async () => {
    render(<AccountConnect />)

    // Request connecting the wallet
    await userEvent.click(screen.getByRole('button', { name: /connect wallet/i }))


    // Verify if the wallet is NOT yet connected
    expect(screen.queryByText(wallets[0].address)).not.toBeInTheDocument()
    
    await act(async () => {
      // You can either authorize or reject the request
      await web3Manager.authorize(Web3RequestKind.RequestAccounts)
    })

    // Verify if the wallet is connected
    expect(screen.getByText(wallets[0].address)).toBeInTheDocument()
  })
})

References

You might also like...

Pagina web com conexão a vossa carteira metamask

Pagina web com conexão a vossa carteira metamask

Conexão com a metamask e envio de transações ! Pagina web com conexão a vossa carteira metamask. Para conseguirmos colocar isto a funcionar basta segu

Jan 25, 2022

enables communication between command-line or desktop applications and browser-based Ethereum wallets such as Metamask.

@securerpc/walletbus @securerpc/walletbus Abstract Quickstart Installation Usage Ethers.js Web3.js Configuration options Logging Development Automated

Dec 27, 2022

A js program generate random 12 words metamask mnemonic and check the balance in the account.

Metamask-Mnemonic-Brute-Force A js program random generate 12 words metamask mnemonic and check the balance in the account. Requirement ethers web3 bi

Dec 25, 2022

This is a Blockchain contract app built with solidity, ethersjs, nodejs, and the hardhart library. Connects to metamask as well.

This is a Blockchain contract app built with solidity, ethersjs, nodejs, and the hardhart library. Connects to metamask as well.

Dribble - Hardtjs, Etherjs, Metamask Project About Dribble is my first blockchain, web 3.0 application that you could use to deposit ethereum into a w

Jun 17, 2022

This is a Blockchain contract app built with solidity, ethersjs, nodejs, and the hardhart library. Connects to metamask as well.

This is a Blockchain contract app built with solidity, ethersjs, nodejs, and the hardhart library. Connects to metamask as well.

Dribble - Hardtjs, Etherjs, Metamask Project About Dribble is my first blockchain, web 3.0 application that you could use to deposit ethereum into a w

May 9, 2022

💥 Snapy Recovery: Social recovery for MetaMask wallets

💥 Snapy Recovery: Social recovery for MetaMask wallets

💥 Snappy Recovery Social Recovery for MetaMask wallets using "Snaps", sandboxed JS plugins for MetaMask. Watch the demo on YouTube: How it works, vis

Nov 12, 2022

Decentralized Social Media. Built using Next.js. Web3 integration with Moralis, Metamask and Ethers.js. Also uses Lens Protofcol to get the profile data.

DecentraGram Decentralized Social Media. Built using Next.js. Web3 integration with Moralis, Metamask and Ethers.js. Also uses Lens Protofcol to get t

Dec 20, 2022

A Cypress plugin that generates test scripts from your interactions, a replacement Cypress Studio for Cypress v10 🖱 ⌨

A Cypress plugin that generates test scripts from your interactions, a replacement Cypress Studio for Cypress v10 🖱 ⌨

DeploySentinel Cypress Recorder Plugin Create Cypress tests scripts within the Cypress test browser by simply interacting with your application, simil

Dec 15, 2022

This package is a replacement for superjson to use in your Remix app

This package is a replacement for superjson to use in your Remix app

This package is a replacement for superjson to use in your Remix app. It handles a subset of types that superjson supports, but is faster and smaller.

Jan 3, 2023
Owner
Emil Ibatullin
Front End Software Engineer
Emil Ibatullin
Hemsida för personer i Sverige som kan och vill erbjuda boende till människor på flykt

Getting Started with Create React App This project was bootstrapped with Create React App. Available Scripts In the project directory, you can run: np

null 4 May 3, 2022
Kurs-repo för kursen Webbserver och Databaser

Webbserver och databaser This repository is meant for CME students to access exercises and codealongs that happen throughout the course. I hope you wi

null 14 Jan 3, 2023
SAP Community Code Challenge: This repository contains an empty OpenUI5 application and end-to-end tests written with wdi5. Take part in the challenge and develop an app that passes the tests.

SAP Community Code Challenge - UI5 The change log describes notable changes in this package. Description This repository is the starting point for the

SAP Samples 8 Oct 24, 2022
A demo for E2E build piplelines in Design Systems using monorepo's and automation :zap:.

Design System Pipelines demo What is it? A working demonstration for end-to-end build piplelines in Design Systems using Primer Primitives, Primer CSS

Rez 7 Oct 20, 2022
Next.js website for E2E

Prérequis git (obviously) node >= 14 avec npm Sur MacOS ou Linux, je suggère fortement d'utiliser Node.js Version Manager afin de simplifier l'install

null 2 Feb 15, 2022
A small utility server to exchange data and messages between clients. Comes complete with E2E public key encryption

Zenotta Intercom A small utility server to exchange arbitrary data between clients. Comes complete with E2E public key encryption Official documentati

Zenotta AG 7 Oct 2, 2022
A testing focused Remix Stack, that integrates E2E & Unit testing with Playwright, Vitest, MSW and Testing Library. Driven by Prisma ORM. Deploys to Fly.io

Live Demo · Twitter A testing focused Remix Stack, that integrates E2E & Unit testing with Playwright, Vitest, MSW and Testing Library. Driven by Pris

Remix Stacks 18 Oct 31, 2022
Web3-citizens-app - React application based on smart contract using web3 and MetaMask extention.

Citizens App (web3-react-redux) React application based on smart contract using web3 and MetaMask extention. Start the applicarion Recomend to install

Denys Voloshyn 3 Aug 25, 2022
This Project is made with HTML5, CSS3, ReactJS, Axios, MetaMask, thirdweb, Rinkeby Test Network, Web 3.0 Technologies, and OpenSea API.

Abstract Collections This Project is made with HTML5, CSS3, ReactJS, Axios, MetaMask, thirdweb, Rinkeby Test Network, Web 3.0 Technologies, and OpenSe

Shobhit Gupta 34 Jan 4, 2023