From 7bfef504153dd8cdab34f4f8f067f6dd123a551e Mon Sep 17 00:00:00 2001 From: Daniel Izdebski Date: Wed, 15 Nov 2023 02:21:05 +0100 Subject: [PATCH] =?UTF-8?q?=E2=9C=A8=20feat(metamask):=20Add=20support=20f?= =?UTF-8?q?or=20adding/switching=20networks?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .github/workflows/test.yml | 7 +++ wallets/metamask/src/metamask.ts | 32 ++++++++++++++ .../pages/NotificationPage/actions/index.ts | 1 + .../pages/NotificationPage/actions/network.ts | 25 +++++++++++ .../src/pages/NotificationPage/page.ts | 26 ++++++++++- .../pages/NotificationPage/selectors/index.ts | 4 +- .../NotificationPage/selectors/networkPage.ts | 14 ++++++ .../e2e/metamask/approveNewNetwork.spec.ts | 23 ++++++++++ .../e2e/metamask/approveSwitchNetwork.spec.ts | 44 +++++++++++++++++++ .../e2e/metamask/rejectAddNetwork.spec.ts | 22 ++++++++++ .../e2e/metamask/rejectSwitchNetwork.spec.ts | 44 +++++++++++++++++++ 11 files changed, 240 insertions(+), 2 deletions(-) create mode 100644 wallets/metamask/src/pages/NotificationPage/actions/network.ts create mode 100644 wallets/metamask/src/pages/NotificationPage/selectors/networkPage.ts create mode 100644 wallets/metamask/test/e2e/metamask/approveNewNetwork.spec.ts create mode 100644 wallets/metamask/test/e2e/metamask/approveSwitchNetwork.spec.ts create mode 100644 wallets/metamask/test/e2e/metamask/rejectAddNetwork.spec.ts create mode 100644 wallets/metamask/test/e2e/metamask/rejectSwitchNetwork.spec.ts diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 422edb3e4..94272b83c 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -31,6 +31,9 @@ jobs: - name: Setup Node & Install dependencies uses: ./.github/actions/setup + - name: Install Foundry + uses: foundry-rs/foundry-toolchain@v1 + # For now, we only need Chromium. - name: Install browsers for Playwright run: pnpm dlx playwright install chromium @@ -50,6 +53,10 @@ jobs: run: | xvfb-run pnpm run build:cache + - name: Start anvil node + run: | + anvil --port 8546 --chain-id 1338 & + - name: Run E2E tests (headful) run: | xvfb-run pnpm run test:e2e:headful diff --git a/wallets/metamask/src/metamask.ts b/wallets/metamask/src/metamask.ts index 9a91c2125..003044f61 100644 --- a/wallets/metamask/src/metamask.ts +++ b/wallets/metamask/src/metamask.ts @@ -59,4 +59,36 @@ export class MetaMask { await this.notificationPage.rejectMessage(this.extensionId) } + + async approveNewNetwork() { + if (!this.extensionId) { + throw NO_EXTENSION_ID_ERROR + } + + await this.notificationPage.approveNewNetwork(this.extensionId) + } + + async rejectNewNetwork() { + if (!this.extensionId) { + throw NO_EXTENSION_ID_ERROR + } + + await this.notificationPage.rejectNewNetwork(this.extensionId) + } + + async approveSwitchNetwork() { + if (!this.extensionId) { + throw NO_EXTENSION_ID_ERROR + } + + await this.notificationPage.approveSwitchNetwork(this.extensionId) + } + + async rejectSwitchNetwork() { + if (!this.extensionId) { + throw NO_EXTENSION_ID_ERROR + } + + await this.notificationPage.rejectSwitchNetwork(this.extensionId) + } } diff --git a/wallets/metamask/src/pages/NotificationPage/actions/index.ts b/wallets/metamask/src/pages/NotificationPage/actions/index.ts index 6ffeabc33..49ed51555 100644 --- a/wallets/metamask/src/pages/NotificationPage/actions/index.ts +++ b/wallets/metamask/src/pages/NotificationPage/actions/index.ts @@ -1,3 +1,4 @@ export * from './connectToDapp' export * from './signSimpleMessage' export * from './signStructuredMessage' +export * from './network' diff --git a/wallets/metamask/src/pages/NotificationPage/actions/network.ts b/wallets/metamask/src/pages/NotificationPage/actions/network.ts new file mode 100644 index 000000000..de65c8e1e --- /dev/null +++ b/wallets/metamask/src/pages/NotificationPage/actions/network.ts @@ -0,0 +1,25 @@ +import type { Page } from '@playwright/test' +import Selectors from '../selectors' + +const approveNewNetwork = async (notificationPage: Page) => { + await notificationPage.locator(Selectors.NetworkPage.addNetwork.approveButton).click() +} + +const rejectNewNetwork = async (notificationPage: Page) => { + await notificationPage.locator(Selectors.NetworkPage.addNetwork.cancelButton).click() +} + +const approveSwitchNetwork = async (notificationPage: Page) => { + await notificationPage.locator(Selectors.NetworkPage.switchNetwork.switchNetworkButton).click() +} + +const rejectSwitchNetwork = async (notificationPage: Page) => { + await notificationPage.locator(Selectors.NetworkPage.switchNetwork.cancelButton).click() +} + +export const network = { + approveNewNetwork, + rejectNewNetwork, + approveSwitchNetwork, + rejectSwitchNetwork +} diff --git a/wallets/metamask/src/pages/NotificationPage/page.ts b/wallets/metamask/src/pages/NotificationPage/page.ts index c8b057377..7fe05a2ac 100644 --- a/wallets/metamask/src/pages/NotificationPage/page.ts +++ b/wallets/metamask/src/pages/NotificationPage/page.ts @@ -1,7 +1,7 @@ import type { Page } from '@playwright/test' import { getNotificationPageAndWaitForLoad } from '../../utils/getNotificationPageAndWaitForLoad' import { waitFor } from '../../utils/waitFor' -import { connectToDapp, signSimpleMessage, signStructuredMessage } from './actions' +import { connectToDapp, network, signSimpleMessage, signStructuredMessage } from './actions' import Selectors from './selectors' export class NotificationPage { @@ -55,4 +55,28 @@ export class NotificationPage { await signSimpleMessage.reject(notificationPage) } } + + async approveNewNetwork(extensionId: string) { + const notificationPage = await getNotificationPageAndWaitForLoad(this.page.context(), extensionId) + + await network.approveNewNetwork(notificationPage) + } + + async rejectNewNetwork(extensionId: string) { + const notificationPage = await getNotificationPageAndWaitForLoad(this.page.context(), extensionId) + + await network.rejectNewNetwork(notificationPage) + } + + async approveSwitchNetwork(extensionId: string) { + const notificationPage = await getNotificationPageAndWaitForLoad(this.page.context(), extensionId) + + await network.approveSwitchNetwork(notificationPage) + } + + async rejectSwitchNetwork(extensionId: string) { + const notificationPage = await getNotificationPageAndWaitForLoad(this.page.context(), extensionId) + + await network.rejectSwitchNetwork(notificationPage) + } } diff --git a/wallets/metamask/src/pages/NotificationPage/selectors/index.ts b/wallets/metamask/src/pages/NotificationPage/selectors/index.ts index b04852dc5..6d6a32587 100644 --- a/wallets/metamask/src/pages/NotificationPage/selectors/index.ts +++ b/wallets/metamask/src/pages/NotificationPage/selectors/index.ts @@ -1,5 +1,7 @@ +import NetworkPage from './networkPage' import SignaturePage from './signaturePage' export default { - SignaturePage + SignaturePage, + NetworkPage } diff --git a/wallets/metamask/src/pages/NotificationPage/selectors/networkPage.ts b/wallets/metamask/src/pages/NotificationPage/selectors/networkPage.ts new file mode 100644 index 000000000..ec13d78ac --- /dev/null +++ b/wallets/metamask/src/pages/NotificationPage/selectors/networkPage.ts @@ -0,0 +1,14 @@ +const addNetwork = { + approveButton: '.confirmation-footer__actions button.btn-primary', + cancelButton: '.confirmation-footer__actions button.btn-secondary' +} + +const switchNetwork = { + switchNetworkButton: '.confirmation-footer__actions button.btn-primary', + cancelButton: '.confirmation-footer__actions button.btn-secondary' +} + +export default { + addNetwork, + switchNetwork +} diff --git a/wallets/metamask/test/e2e/metamask/approveNewNetwork.spec.ts b/wallets/metamask/test/e2e/metamask/approveNewNetwork.spec.ts new file mode 100644 index 000000000..ec67ee7fb --- /dev/null +++ b/wallets/metamask/test/e2e/metamask/approveNewNetwork.spec.ts @@ -0,0 +1,23 @@ +import { testWithSynpress } from 'fixtures' +import { MetaMask, unlockForFixture } from '../../../src' + +import connectedSetup from '../wallet-setup/connected.setup' + +const test = testWithSynpress(connectedSetup, unlockForFixture) + +const { expect } = test + +test('should add a new network', async ({ context, metamaskPage, page, extensionId }) => { + const metamask = new MetaMask(context, metamaskPage, connectedSetup.walletPassword, extensionId) + + await page.goto('https://metamask.github.io/test-dapp/') + + await expect(page.locator('#chainId')).toHaveText('0x1') + + await page.locator('#addEthereumChain').click() + + await metamask.approveNewNetwork() + await metamask.approveSwitchNetwork() + + await expect(page.locator('#chainId')).toHaveText('0x53a') +}) diff --git a/wallets/metamask/test/e2e/metamask/approveSwitchNetwork.spec.ts b/wallets/metamask/test/e2e/metamask/approveSwitchNetwork.spec.ts new file mode 100644 index 000000000..257d9bb85 --- /dev/null +++ b/wallets/metamask/test/e2e/metamask/approveSwitchNetwork.spec.ts @@ -0,0 +1,44 @@ +import { testWithSynpress } from 'fixtures' +import { MetaMask, unlockForFixture } from '../../../src' + +import connectedSetup from '../wallet-setup/connected.setup' + +const test = testWithSynpress(connectedSetup, unlockForFixture) + +const { expect, describe } = test + +describe('when adding a new network', () => { + test('should switch to the new network', async ({ context, metamaskPage, page, extensionId }) => { + const metamask = new MetaMask(context, metamaskPage, connectedSetup.walletPassword, extensionId) + + await page.goto('https://metamask.github.io/test-dapp/') + + await expect(page.locator('#chainId')).toHaveText('0x1') + + await page.locator('#addEthereumChain').click() + + await metamask.approveNewNetwork() + await metamask.approveSwitchNetwork() + + await expect(page.locator('#chainId')).toHaveText('0x53a') + }) +}) + +test('should switch to the requested network', async ({ context, metamaskPage, page, extensionId }) => { + const metamask = new MetaMask(context, metamaskPage, connectedSetup.walletPassword, extensionId) + + await page.goto('https://metamask.github.io/test-dapp/') + + await page.locator('#addEthereumChain').click() + + await metamask.approveNewNetwork() + await metamask.rejectSwitchNetwork() + + await expect(page.locator('#chainId')).toHaveText('0x1') + + await page.locator('#switchEthereumChain').click() + + await metamask.approveSwitchNetwork() + + await expect(page.locator('#chainId')).toHaveText('0x53a') +}) diff --git a/wallets/metamask/test/e2e/metamask/rejectAddNetwork.spec.ts b/wallets/metamask/test/e2e/metamask/rejectAddNetwork.spec.ts new file mode 100644 index 000000000..08e9be1d0 --- /dev/null +++ b/wallets/metamask/test/e2e/metamask/rejectAddNetwork.spec.ts @@ -0,0 +1,22 @@ +import { testWithSynpress } from 'fixtures' +import { MetaMask, unlockForFixture } from '../../../src' + +import connectedSetup from '../wallet-setup/connected.setup' + +const test = testWithSynpress(connectedSetup, unlockForFixture) + +const { expect } = test + +test('should reject new network request', async ({ context, metamaskPage, page, extensionId }) => { + const metamask = new MetaMask(context, metamaskPage, connectedSetup.walletPassword, extensionId) + + await page.goto('https://metamask.github.io/test-dapp/') + + await expect(page.locator('#chainId')).toHaveText('0x1') + + await page.locator('#addEthereumChain').click() + + await metamask.rejectNewNetwork() + + await expect(page.locator('#chainId')).toHaveText('0x1') +}) diff --git a/wallets/metamask/test/e2e/metamask/rejectSwitchNetwork.spec.ts b/wallets/metamask/test/e2e/metamask/rejectSwitchNetwork.spec.ts new file mode 100644 index 000000000..7862a21a9 --- /dev/null +++ b/wallets/metamask/test/e2e/metamask/rejectSwitchNetwork.spec.ts @@ -0,0 +1,44 @@ +import { testWithSynpress } from 'fixtures' +import { MetaMask, unlockForFixture } from '../../../src' + +import connectedSetup from '../wallet-setup/connected.setup' + +const test = testWithSynpress(connectedSetup, unlockForFixture) + +const { expect, describe } = test + +describe('when adding a new network', () => { + test('should reject switch network request', async ({ context, metamaskPage, page, extensionId }) => { + const metamask = new MetaMask(context, metamaskPage, connectedSetup.walletPassword, extensionId) + + await page.goto('https://metamask.github.io/test-dapp/') + + await expect(page.locator('#chainId')).toHaveText('0x1') + + await page.locator('#addEthereumChain').click() + + await metamask.approveNewNetwork() + await metamask.rejectSwitchNetwork() + + await expect(page.locator('#chainId')).toHaveText('0x1') + }) +}) + +test('should reject switch network request', async ({ context, metamaskPage, page, extensionId }) => { + const metamask = new MetaMask(context, metamaskPage, connectedSetup.walletPassword, extensionId) + + await page.goto('https://metamask.github.io/test-dapp/') + + await page.locator('#addEthereumChain').click() + + await metamask.approveNewNetwork() + await metamask.rejectSwitchNetwork() + + await expect(page.locator('#chainId')).toHaveText('0x1') + + await page.locator('#switchEthereumChain').click() + + await metamask.rejectSwitchNetwork() + + await expect(page.locator('#chainId')).toHaveText('0x1') +})