diff --git a/packages/bridge-ui/package.json b/packages/bridge-ui/package.json index 8369a198bd7..3be25e62701 100644 --- a/packages/bridge-ui/package.json +++ b/packages/bridge-ui/package.json @@ -22,6 +22,7 @@ "@babel/preset-env": "^7.16.0", "@sveltejs/vite-plugin-svelte": "^1.0.1", "@tsconfig/svelte": "^3.0.0", + "@types/debug": "^4.1.7", "@types/eslint": "^8.2.1", "@types/estree": "^0.0.50", "@types/jest": "^27.0.2", @@ -75,6 +76,7 @@ "@wagmi/core": "^0.8.0", "axios": "^1.2.0", "buffer": "^6.0.3", + "debug": "^4.3.4", "ethers": "^5.7.1", "identicon.js": "^2.3.3", "svelte-i18n": "^3.5.1", diff --git a/packages/bridge-ui/src/components/ChainDropdown.svelte b/packages/bridge-ui/src/components/ChainDropdown.svelte index 0dc68cbaa35..32b033adc5f 100644 --- a/packages/bridge-ui/src/components/ChainDropdown.svelte +++ b/packages/bridge-ui/src/components/ChainDropdown.svelte @@ -1,26 +1,25 @@ @@ -50,9 +49,7 @@
  • @@ -60,9 +57,7 @@
  • diff --git a/packages/bridge-ui/src/components/Transactions/Transaction.svelte b/packages/bridge-ui/src/components/Transactions/Transaction.svelte index dc4c95fcbc1..02ad8590198 100644 --- a/packages/bridge-ui/src/components/Transactions/Transaction.svelte +++ b/packages/bridge-ui/src/components/Transactions/Transaction.svelte @@ -25,7 +25,7 @@ import { tokenVaults } from '../../vault/tokenVaults'; import { isOnCorrectChain } from '../../utils/isOnCorrectChain'; import Button from '../buttons/Button.svelte'; - import { switchChainAndSetSigner } from '../../utils/switchChainAndSetSigner'; + import { selectChain } from '../../utils/selectChain'; import type { NoticeOpenArgs } from '../../domain/modal'; export let transaction: BridgeTransaction; @@ -81,7 +81,7 @@ // to the right network. if ($fromChain.id !== bridgeTx.toChainId) { const chain = chains[bridgeTx.toChainId]; - await switchChainAndSetSigner(chain); + await selectChain(chain); } // confirm after switch chain that it worked. @@ -133,7 +133,7 @@ loading = true; if (txFromChain.id !== bridgeTx.fromChainId) { const chain = chains[bridgeTx.fromChainId]; - await switchChainAndSetSigner(chain); + await selectChain(chain); } // confirm after switch chain that it worked. diff --git a/packages/bridge-ui/src/components/form/SelectChain.svelte b/packages/bridge-ui/src/components/form/SelectChain.svelte index a98f4cc96af..e9e40f14742 100644 --- a/packages/bridge-ui/src/components/form/SelectChain.svelte +++ b/packages/bridge-ui/src/components/form/SelectChain.svelte @@ -3,9 +3,9 @@ import { ArrowRight } from 'svelte-heros-v2'; import { fromChain, toChain } from '../../store/chain'; import { signer } from '../../store/signer'; - import { ethers } from 'ethers'; import { mainnetChain, taikoChain } from '../../chain/chains'; import { errorToast, successToast } from '../Toast.svelte'; + import { selectChain } from '../../utils/selectChain'; const toggleChains = async () => { if (!$signer) { @@ -13,21 +13,10 @@ return; } - try { - const chain = $fromChain === mainnetChain ? taikoChain : mainnetChain; - await switchNetwork({ - chainId: chain.id, - }); - const provider = new ethers.providers.Web3Provider( - window.ethereum, - 'any', - ); - await provider.send('eth_requestAccounts', []); - - fromChain.set(chain); - toChain.set(chain === mainnetChain ? taikoChain : mainnetChain); + const chain = $fromChain === mainnetChain ? taikoChain : mainnetChain; - signer.set(provider.getSigner()); + try { + await selectChain(chain); successToast('Successfully changed chain'); } catch (e) { console.error(e); diff --git a/packages/bridge-ui/src/proof/ProofService.spec.ts b/packages/bridge-ui/src/proof/ProofService.spec.ts index 438d1e126d8..3aa6f5a4ebe 100644 --- a/packages/bridge-ui/src/proof/ProofService.spec.ts +++ b/packages/bridge-ui/src/proof/ProofService.spec.ts @@ -1,4 +1,4 @@ -import { BigNumber, ethers } from 'ethers'; +import { ethers } from 'ethers'; import type { EthGetProofResponse } from '../domain/proof'; import { ProofService } from './ProofService'; diff --git a/packages/bridge-ui/src/utils/logger.ts b/packages/bridge-ui/src/utils/logger.ts new file mode 100644 index 00000000000..fa4b5eebc6a --- /dev/null +++ b/packages/bridge-ui/src/utils/logger.ts @@ -0,0 +1,5 @@ +import debug from 'debug'; + +export function getLogger(namesapce: string) { + return debug(`bridge:${namesapce}`); +} diff --git a/packages/bridge-ui/src/utils/selectChain.spec.ts b/packages/bridge-ui/src/utils/selectChain.spec.ts new file mode 100644 index 00000000000..98c2440a22b --- /dev/null +++ b/packages/bridge-ui/src/utils/selectChain.spec.ts @@ -0,0 +1,74 @@ +import { switchNetwork } from '@wagmi/core'; +import { Signer, ethers } from 'ethers'; +import { fromChain, toChain } from '../store/chain'; +import { signer } from '../store/signer'; +import { mainnetChain, taikoChain } from '../chain/chains'; +import { selectChain } from './selectChain'; + +jest.mock('../constants/envVars'); + +jest.mock('@wagmi/core', () => ({ + switchNetwork: jest.fn(), +})); + +jest.mock('ethers', () => { + const Web3Provider = jest.fn(); + Web3Provider.prototype = { + getSigner: jest.fn(), + send: jest.fn(), + }; + return { + ethers: { + providers: { + Web3Provider, + }, + }, + }; +}); + +jest.mock('../store/chain', () => ({ + fromChain: { + set: jest.fn(), + }, + toChain: { + set: jest.fn(), + }, +})); + +jest.mock('../store/signer', () => ({ + signer: { + set: jest.fn(), + }, +})); + +describe('selectChain', () => { + it('should select chain', async () => { + const mockSigner = {} as ethers.providers.JsonRpcSigner; + jest + .mocked(ethers.providers.Web3Provider.prototype.getSigner) + .mockReturnValue(mockSigner); + + await selectChain(mainnetChain); + + expect(switchNetwork).toHaveBeenCalledWith({ chainId: mainnetChain.id }); + expect(fromChain.set).toHaveBeenCalledWith(mainnetChain); + expect(toChain.set).toHaveBeenCalledWith(taikoChain); + expect(signer.set).toHaveBeenCalled(); + + expect(ethers.providers.Web3Provider.prototype.send).toHaveBeenCalledWith( + 'eth_requestAccounts', + [], + ); + + expect( + ethers.providers.Web3Provider.prototype.getSigner, + ).toHaveBeenCalled(); + + expect(signer.set).toHaveBeenCalledWith(mockSigner); + + // Select the other chain now + await selectChain(taikoChain); + + expect(switchNetwork).toHaveBeenCalledWith({ chainId: taikoChain.id }); + }); +}); diff --git a/packages/bridge-ui/src/utils/switchChainAndSetSigner.ts b/packages/bridge-ui/src/utils/selectChain.ts similarity index 55% rename from packages/bridge-ui/src/utils/switchChainAndSetSigner.ts rename to packages/bridge-ui/src/utils/selectChain.ts index 09d87cdc5b7..3fe6ed87df8 100644 --- a/packages/bridge-ui/src/utils/switchChainAndSetSigner.ts +++ b/packages/bridge-ui/src/utils/selectChain.ts @@ -1,11 +1,14 @@ -import { fetchSigner, switchNetwork } from '@wagmi/core'; +import { switchNetwork } from '@wagmi/core'; import { ethers } from 'ethers'; import { fromChain, toChain } from '../store/chain'; import type { Chain } from '../domain/chain'; import { mainnetChain, taikoChain } from '../chain/chains'; import { signer } from '../store/signer'; +import { getLogger } from '../utils/logger'; -export async function switchChainAndSetSigner(chain: Chain) { +const log = getLogger('selectChain'); + +export async function selectChain(chain: Chain) { const chainId = chain.id; await switchNetwork({ chainId }); @@ -14,7 +17,11 @@ export async function switchChainAndSetSigner(chain: Chain) { globalThis.ethereum, 'any', ); - await provider.send('eth_requestAccounts', []); + + // Requires requesting permission to connect users accounts + const accounts = await provider.send('eth_requestAccounts', []); + + log('accounts', accounts); fromChain.set(chain); if (chain.id === mainnetChain.id) { @@ -23,7 +30,9 @@ export async function switchChainAndSetSigner(chain: Chain) { toChain.set(mainnetChain); } - const wagmiSigner = await fetchSigner({ chainId }); + const _signer = provider.getSigner(); + + log('signer', _signer); - signer.set(wagmiSigner); + signer.set(_signer); } diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index aceb1220721..466d1e2f93e 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -26,16 +26,19 @@ importers: version: 1.6.0 '@wagmi/connectors': specifier: ^0.1.1 - version: 0.1.1(@wagmi/core@0.8.4)(ethers@5.7.2)(typescript@4.9.3) + version: 0.1.1(@wagmi/core@0.8.4)(debug@4.3.4)(ethers@5.7.2)(typescript@4.9.3) '@wagmi/core': specifier: ^0.8.0 - version: 0.8.4(@coinbase/wallet-sdk@3.6.3)(ethers@5.7.2)(typescript@4.9.3) + version: 0.8.4(@coinbase/wallet-sdk@3.6.3)(debug@4.3.4)(ethers@5.7.2)(typescript@4.9.3) axios: specifier: ^1.2.0 - version: 1.2.0 + version: 1.2.0(debug@4.3.4) buffer: specifier: ^6.0.3 version: 6.0.3 + debug: + specifier: ^4.3.4 + version: 4.3.4 ethers: specifier: ^5.7.1 version: 5.7.2 @@ -58,6 +61,9 @@ importers: '@tsconfig/svelte': specifier: ^3.0.0 version: 3.0.0 + '@types/debug': + specifier: ^4.1.7 + version: 4.1.7 '@types/eslint': specifier: ^8.2.1 version: 8.4.10 @@ -2948,6 +2954,20 @@ packages: - bufferutil - debug - utf-8-validate + dev: false + + /@json-rpc-tools/provider@1.7.6(debug@4.3.4): + resolution: {integrity: sha512-z7D3xvJ33UfCGv77n40lbzOYjZKVM3k2+5cV7xS8G6SCvKTzMkhkUYuD/qzQUNT4cG/lv0e9mRToweEEVLVVmA==} + deprecated: Package no longer supported. Contact Support at https://www.npmjs.com/support for more info. + dependencies: + '@json-rpc-tools/utils': 1.7.6 + axios: 0.21.4(debug@4.3.4) + safe-json-utils: 1.1.1 + ws: 7.5.9 + transitivePeerDependencies: + - bufferutil + - debug + - utf-8-validate /@json-rpc-tools/types@1.7.6: resolution: {integrity: sha512-nDSqmyRNEqEK9TZHtM15uNnDljczhCUdBmRhpNZ95bIPKEDQ+nTDmGMFd2lLin3upc5h2VVVd9tkTDdbXUhDIQ==} @@ -4267,7 +4287,6 @@ packages: resolution: {integrity: sha512-9AonUzyTjXXhEOa0DnqpzZi6VHlqKMswga9EXjpXnnqxwLtdvPPtlO8evrI5D9S6asFRCQ6v+wpiUKbw+vKqyg==} dependencies: '@types/ms': 0.7.31 - dev: false /@types/eslint-scope@3.7.4: resolution: {integrity: sha512-9K4zoImiZc3HlIp6AVUDE4CWYx22a+lhSZMYNpbjW04+YF0KWj4pJXnEMjdnFTiQibFFmElcsasJXDbdI/EPhA==} @@ -4453,7 +4472,6 @@ packages: /@types/ms@0.7.31: resolution: {integrity: sha512-iiUgKzV9AuaEkZqkOLDIvlQiL6ltuZd9tGcW3gwpnX8JbuiuhFlEGmmFXEXkN50Cvq7Os88IY2v0dkDqXYWVgA==} - dev: false /@types/node-fetch@2.6.3: resolution: {integrity: sha512-ETTL1mOEdq/sxUtgtOhKjyB2Irra4cjxksvcMUR5Zr4n+PxVhsCD9WS46oPbHL3et9Zde7CNRr+WUNlcHvsX+w==} @@ -5064,7 +5082,7 @@ packages: optional: true dependencies: '@wagmi/chains': 0.2.22(typescript@4.9.3) - '@wagmi/core': 0.8.4(@coinbase/wallet-sdk@3.6.3)(ethers@5.7.2)(typescript@4.9.3) + '@wagmi/core': 0.8.4(@coinbase/wallet-sdk@3.6.3)(debug@4.3.4)(ethers@5.7.2)(typescript@4.9.3) abitype: 0.8.1(typescript@4.9.3)(zod@3.21.4) abort-controller: 3.0.0 bundle-require: 3.1.2(esbuild@0.15.13) @@ -5093,6 +5111,31 @@ packages: - utf-8-validate dev: true + /@wagmi/connectors@0.1.1(@wagmi/core@0.8.4)(debug@4.3.4)(ethers@5.7.2)(typescript@4.9.3): + resolution: {integrity: sha512-W9w73o9HCYzuBsDHuujwBT/nGGIu5qLBSqVqslXf/S1Q9OiWoudmuIs3opuYqxgw5MpWbMqhq6QaxA7Qcd6NrA==} + peerDependencies: + '@wagmi/core': 0.8.x + ethers: ^5.0.0 + peerDependenciesMeta: + '@wagmi/core': + optional: true + dependencies: + '@coinbase/wallet-sdk': 3.6.3 + '@ledgerhq/connect-kit-loader': 1.0.1 + '@wagmi/core': 0.8.4(@coinbase/wallet-sdk@3.6.3)(debug@4.3.4)(ethers@5.7.2)(typescript@4.9.3) + '@walletconnect/ethereum-provider': 1.8.0(debug@4.3.4) + abitype: 0.1.8(typescript@4.9.3) + ethers: 5.7.2 + eventemitter3: 4.0.7 + transitivePeerDependencies: + - '@babel/core' + - bufferutil + - debug + - encoding + - supports-color + - typescript + - utf-8-validate + /@wagmi/connectors@0.1.1(@wagmi/core@0.8.4)(ethers@5.7.2)(typescript@4.9.3): resolution: {integrity: sha512-W9w73o9HCYzuBsDHuujwBT/nGGIu5qLBSqVqslXf/S1Q9OiWoudmuIs3opuYqxgw5MpWbMqhq6QaxA7Qcd6NrA==} peerDependencies: @@ -5117,6 +5160,7 @@ packages: - supports-color - typescript - utf-8-validate + dev: false /@wagmi/connectors@0.1.1(@wagmi/core@0.8.4)(ethers@5.7.2)(typescript@4.9.5): resolution: {integrity: sha512-W9w73o9HCYzuBsDHuujwBT/nGGIu5qLBSqVqslXf/S1Q9OiWoudmuIs3opuYqxgw5MpWbMqhq6QaxA7Qcd6NrA==} @@ -5144,6 +5188,37 @@ packages: - utf-8-validate dev: false + /@wagmi/core@0.8.4(@coinbase/wallet-sdk@3.6.3)(debug@4.3.4)(ethers@5.7.2)(typescript@4.9.3): + resolution: {integrity: sha512-orFRGOei+ixH8fIU9DitjKFSnv7sEv4j0A32gin2aADLuyBsAqG7xD+5LzfVD8EarHzU98Mk9d4hmmIkMg8bXw==} + peerDependencies: + '@coinbase/wallet-sdk': '>=3.6.0' + '@walletconnect/ethereum-provider': '>=1.7.5' + ethers: '>=5.5.1' + peerDependenciesMeta: + '@coinbase/wallet-sdk': + optional: true + '@walletconnect/ethereum-provider': + optional: true + dependencies: + '@coinbase/wallet-sdk': 3.6.3 + '@wagmi/chains': 0.1.3 + '@wagmi/connectors': 0.1.1(@wagmi/core@0.8.4)(debug@4.3.4)(ethers@5.7.2)(typescript@4.9.3) + abitype: 0.2.5(typescript@4.9.3) + ethers: 5.7.2 + eventemitter3: 4.0.7 + zustand: 4.1.4 + transitivePeerDependencies: + - '@babel/core' + - bufferutil + - debug + - encoding + - immer + - react + - supports-color + - typescript + - utf-8-validate + - zod + /@wagmi/core@0.8.4(@coinbase/wallet-sdk@3.6.3)(ethers@5.7.2)(typescript@4.9.3): resolution: {integrity: sha512-orFRGOei+ixH8fIU9DitjKFSnv7sEv4j0A32gin2aADLuyBsAqG7xD+5LzfVD8EarHzU98Mk9d4hmmIkMg8bXw==} peerDependencies: @@ -5174,6 +5249,7 @@ packages: - typescript - utf-8-validate - zod + dev: false /@wagmi/core@0.8.4(@coinbase/wallet-sdk@3.6.3)(ethers@5.7.2)(typescript@4.9.5): resolution: {integrity: sha512-orFRGOei+ixH8fIU9DitjKFSnv7sEv4j0A32gin2aADLuyBsAqG7xD+5LzfVD8EarHzU98Mk9d4hmmIkMg8bXw==} @@ -5276,6 +5352,24 @@ packages: - debug - encoding - utf-8-validate + dev: false + + /@walletconnect/ethereum-provider@1.8.0(debug@4.3.4): + resolution: {integrity: sha512-Nq9m+oo5P0F+njsROHw9KMWdoc/8iGHYzQdkjJN/1C7DtsqFRg5k5a3hd9rzCLpbPsOC1q8Z5lRs6JQgDvPm6Q==} + dependencies: + '@walletconnect/client': 1.8.0 + '@walletconnect/jsonrpc-http-connection': 1.0.4 + '@walletconnect/jsonrpc-provider': 1.0.6 + '@walletconnect/signer-connection': 1.8.0 + '@walletconnect/types': 1.8.0 + '@walletconnect/utils': 1.8.0 + eip1193-provider: 1.0.1(debug@4.3.4) + eventemitter3: 4.0.7 + transitivePeerDependencies: + - bufferutil + - debug + - encoding + - utf-8-validate /@walletconnect/iso-crypto@1.8.0: resolution: {integrity: sha512-pWy19KCyitpfXb70hA73r9FcvklS+FvO9QUIttp3c2mfW8frxgYeRXfxLRCIQTkaYueRKvdqPjbyhPLam508XQ==} @@ -6239,6 +6333,14 @@ packages: follow-redirects: 1.15.2 transitivePeerDependencies: - debug + dev: false + + /axios@0.21.4(debug@4.3.4): + resolution: {integrity: sha512-ut5vewkiu8jjGBdqpM44XxjuCjq9LAKeHVmoVfHVzy8eHgxxq8SbAVQNovDA8mVi05kP0Ea/n/UzcSHcTJQfNg==} + dependencies: + follow-redirects: 1.15.2 + transitivePeerDependencies: + - debug /axios@1.2.0: resolution: {integrity: sha512-zT7wZyNYu3N5Bu0wuZ6QccIf93Qk1eV8LOewxgjOZFd2DenOs98cJ7+Y6703d0wkaXGY6/nZd4EweJaHz9uzQw==} @@ -6250,6 +6352,16 @@ packages: - debug dev: false + /axios@1.2.0(debug@4.3.4): + resolution: {integrity: sha512-zT7wZyNYu3N5Bu0wuZ6QccIf93Qk1eV8LOewxgjOZFd2DenOs98cJ7+Y6703d0wkaXGY6/nZd4EweJaHz9uzQw==} + dependencies: + follow-redirects: 1.15.2 + form-data: 4.0.0 + proxy-from-env: 1.1.0 + transitivePeerDependencies: + - debug + dev: false + /babel-code-frame@6.26.0: resolution: {integrity: sha512-XqYMR2dfdGMW+hd0IUZ2PwK+fGeFkOxZJ0wY+JaQAHzt1Zx8LcvpiZD2NiGkEG8qx0CfkAOr5xt76d1e8vG90g==} dependencies: @@ -9113,6 +9225,16 @@ packages: - bufferutil - debug - utf-8-validate + dev: false + + /eip1193-provider@1.0.1(debug@4.3.4): + resolution: {integrity: sha512-kSuqwQ26d7CzuS/t3yRXo2Su2cVH0QfvyKbr2H7Be7O5YDyIq4hQGCNTo5wRdP07bt+E2R/8nPCzey4ojBHf7g==} + dependencies: + '@json-rpc-tools/provider': 1.7.6(debug@4.3.4) + transitivePeerDependencies: + - bufferutil + - debug + - utf-8-validate /electron-to-chromium@1.4.284: resolution: {integrity: sha512-M8WEXFuKXMYMVr45fo8mq0wUrrJHheiKZf6BArTKk9ZBYCKJEOU5H8cdWgDT+qCVZf7Na4lVUaZsA+h6uA9+PA==}