Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: added switch network method #22

Merged
merged 7 commits into from
Jan 20, 2022
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions index.d.ts
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
declare module 'eth-provider';
declare module '@myetherwallet/mewconnect-web-client';
10 changes: 6 additions & 4 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -28,21 +28,23 @@
"@lingui/react": "^3.13.0",
"@mui/icons-material": "latest",
"@mui/material": "latest",
"@myetherwallet/mewconnect-web-client": "^2.2.0-beta.16",
Copy link
Collaborator

@sakulstra sakulstra Jan 20, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🤔
This package increases bundle size quite a bit, has no types & broken dependencies ... it's just a mess:
MyEtherWallet/MEWconnect-web-client#106

as long as there isn't put more effort in maintaining the lib i think it should not be supported as is decreases the experience for all other users

"@toruslabs/torus-embed": "^1.19.0",
"@walletconnect/web3-provider": "^1.7.1",
"axios": "^0.25.0",
"eth-provider": "^0.10.0",
"ethereum-blockies-base64": "^1.0.2",
"react-intl": "^5.24.3",
"walletlink": "^2.4.0",
"web3modal": "^1.9.5",
"ethers": "^5.5.3",
"graphql": "^16.2.0",
"graphql-ws": "^5.5.5",
"next": "latest",
"react": "latest",
"react-dom": "latest",
"react-intl": "^5.24.3",
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

react-intl is not needed anymore, please delete this dependency

"reflect-metadata": "^0.1.13",
"subscriptions-transport-ws": "^0.11.0"
"subscriptions-transport-ws": "^0.11.0",
"walletlink": "^2.4.0",
"web3modal": "^1.9.5"
},
"devDependencies": {
"@babel/core": "^7.16.7",
Expand Down
15 changes: 14 additions & 1 deletion src/layouts/WalletWidget.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,8 @@ import { getNetworkConfig } from 'src/utils/marketsAndNetworksConfig';
import { ColorModeContext } from './MainLayout';

export default function WalletWidget() {
const { connectWallet, disconnectWallet, currentAccount, connected, chainId } = useWeb3Context();
const { connectWallet, disconnectWallet, currentAccount, connected, chainId, switchNetwork } =
useWeb3Context();

const { name: ensName, avatar: ensAvatar } = useGetEns(currentAccount);
const ensNameAbbreviated = ensName
Expand Down Expand Up @@ -72,6 +73,11 @@ export default function WalletWidget() {
setAnchorEl(null);
};

const handleSwitchNetwork = () => {
switchNetwork(137);
setAnchorEl(null);
};

return (
<div>
<Button
Expand Down Expand Up @@ -144,6 +150,13 @@ export default function WalletWidget() {
</ListItemIcon>
<ListItemText>Disconnect Wallet</ListItemText>
</MenuItem>
<Divider />
<MenuItem onClick={handleSwitchNetwork}>
<ListItemIcon>
<RemoveCircleOutlineRoundedIcon fontSize="small" />
</ListItemIcon>
<ListItemText>SwitchNetwork</ListItemText>
</MenuItem>
</Menu>
</div>
);
Expand Down
44 changes: 44 additions & 0 deletions src/libs/web3-data-provider/Web3ContextProvider.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { JsonRpcProvider, Network, Web3Provider } from '@ethersproject/providers';
import { providers } from 'ethers';
import React, { ReactElement, useCallback, useContext, useEffect, useMemo, useState } from 'react';
import { getNetworkConfig } from 'src/utils/marketsAndNetworksConfig';
import Web3Modal from 'web3modal';

export type Web3Data = {
Expand All @@ -11,6 +12,7 @@ export type Web3Data = {
provider: JsonRpcProvider | undefined;
web3Modal: Web3Modal;
chainId: number;
switchNetwork: (chainId: number) => Promise<void>;
};

export type Web3ContextData = {
Expand Down Expand Up @@ -39,6 +41,7 @@ export const Web3ContextProvider: React.FC<{ children: ReactElement }> = ({ chil
const [connected, setConnected] = useState(false);
const [chainId, setChainId] = useState(1);
const [currentAccount, setCurrentAccount] = useState('');
const [web3Provider, setWeb3Provider] = useState(null as any);

const [web3Modal, setWeb3Modal] = useState<Web3Modal>(undefined as unknown as Web3Modal);

Expand Down Expand Up @@ -75,6 +78,7 @@ export const Web3ContextProvider: React.FC<{ children: ReactElement }> = ({ chil
// web 3 modal
const connectWallet = useCallback(async () => {
const providerInstance = await web3Modal.connect();
setWeb3Provider(providerInstance);
await initSubscriptions(providerInstance);

const ethProvider = new providers.Web3Provider(providerInstance);
Expand All @@ -97,8 +101,47 @@ export const Web3ContextProvider: React.FC<{ children: ReactElement }> = ({ chil
web3Modal.clearCachedProvider();
setConnected(false);
setCurrentAccount('');
if (web3Provider) {
if (web3Provider.close) {
await web3Provider.close();
} else if (web3Provider.disconnect) {
web3Provider.disconnect();
} else {
console.log('provider: ', web3Provider)
}
}
}, [provider, web3Modal, connected]);

const switchNetwork = async (newChainId: number) => {
if (provider) {
try {
await provider.send('wallet_switchEthereumChain', [
{ chainId: `0x${newChainId.toString(16)}` },
]);
} catch (switchError) {
console.log(switchError);
const networkInfo = getNetworkConfig(newChainId);
// @ts-expect-error to correctly type we should add a conditional here to check instanceof Error
if (switchError.code === 4902) {
try {
await provider.send('wallet_addEthereumChain', [
{
chainId: `0x${newChainId.toString(16)}`,
chainName: networkInfo.name,
nativeCurrency: networkInfo.baseAssetSymbol,
rpcUrls: [...networkInfo.publicJsonRPCUrl, networkInfo.publicJsonRPCWSUrl],
blockExplorerUrls: networkInfo.explorerLink,
},
]);
} catch (addError) {
console.log(addError);
// TODO: handle error somehow
}
}
}
}
};

const web3ProviderData = useMemo(
() => ({
connectWallet,
Expand All @@ -108,6 +151,7 @@ export const Web3ContextProvider: React.FC<{ children: ReactElement }> = ({ chil
currentAccount,
web3Modal,
chainId,
switchNetwork,
}),
[connectWallet, disconnectWallet, provider, connected, currentAccount, web3Modal, chainId]
);
Expand Down
17 changes: 16 additions & 1 deletion src/libs/web3-data-provider/modalOptions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import ethProvider from 'eth-provider';
import { getNetworkConfig, getSupportedChainIds } from 'src/utils/marketsAndNetworksConfig';
import WalletLink from 'walletlink';
import Web3Modal from 'web3modal';
import MewConnect from '@myetherwallet/mewconnect-web-client';

const POLLING_INTERVAL = 12000;
const APP_NAME = 'Aave';
Expand Down Expand Up @@ -36,12 +37,26 @@ export const getWeb3Modal = (networkId: number) => {
options: {
appName: APP_NAME,
appLogoUrl: APP_LOGO_URL,
url: networkConfig.privateJsonRPCUrl || networkConfig.publicJsonRPCUrl[0],
rpc: supportedChainIds.reduce((acc, network) => {
const config = getNetworkConfig(network);
acc[network] = config.privateJsonRPCUrl || config.publicJsonRPCUrl[0];
return acc;
}, {} as { [networkId: number]: string }),
},
},
frame: {
package: ethProvider, // required
},
mewconnect: {
package: MewConnect, // required
options: {
rpc: supportedChainIds.reduce((acc, network) => {
const config = getNetworkConfig(network);
acc[network] = config.privateJsonRPCUrl || config.publicJsonRPCUrl[0];
return acc;
}, {} as { [networkId: number]: string }),
},
},
},
});
};
Loading