forked from cerc-io/laconic-wallet
Support SIWE using selected account (#61)
* Sign in using selected address * Use optional namespace * Merge namespaces and use combined namespace * Add todo for lodash merge * Use walletConnect util buildApprovedNamespaces while approving sessions * Lint fixes --------- Co-authored-by: Adw8 <adwait@deepstacksoft.com> Co-authored-by: Nabarun <nabarun@deepstacksoft.com>
This commit is contained in:
parent
3a2087b389
commit
4eecdb7e4c
@ -89,7 +89,7 @@
|
||||
|
||||
5. Set up the Android device:
|
||||
|
||||
- For a physical device, refer to the [React Native documentation for running on a physical device]("https://reactnative.dev/docs/running-on-device)
|
||||
- For a physical device, refer to the [React Native documentation for running on a physical device](https://reactnative.dev/docs/running-on-device)
|
||||
|
||||
- For a virtual device, continue with the steps.
|
||||
|
||||
|
@ -7,7 +7,7 @@ import React from 'react';
|
||||
import App from '../src/App';
|
||||
|
||||
// Note: import explicitly to use the types shipped with jest.
|
||||
import {it} from '@jest/globals';
|
||||
import { it } from '@jest/globals';
|
||||
|
||||
// Note: test renderer must be required after react-native.
|
||||
import renderer from 'react-test-renderer';
|
||||
|
@ -1,4 +1,4 @@
|
||||
const {getDefaultConfig, mergeConfig} = require('@react-native/metro-config');
|
||||
const { getDefaultConfig, mergeConfig } = require('@react-native/metro-config');
|
||||
|
||||
/**
|
||||
* Metro configuration
|
||||
|
@ -26,6 +26,7 @@
|
||||
"cosmjs-types": "^0.9.0",
|
||||
"ethers": "5.7.2",
|
||||
"fast-text-encoding": "^1.0.6",
|
||||
"lodash": "^4.17.21",
|
||||
"metro-react-native-babel-preset": "^0.77.0",
|
||||
"patch-package": "^8.0.0",
|
||||
"postinstall-postinstall": "^2.1.0",
|
||||
@ -51,6 +52,7 @@
|
||||
"@react-native/eslint-config": "0.73.2",
|
||||
"@react-native/metro-config": "0.73.4",
|
||||
"@react-native/typescript-config": "0.73.1",
|
||||
"@types/lodash": "^4.17.0",
|
||||
"@types/react": "^18.2.6",
|
||||
"@types/react-native-vector-icons": "^6.4.18",
|
||||
"@types/react-test-renderer": "^18.0.0",
|
||||
|
@ -23,7 +23,7 @@ import AddSession from './screens/AddSession';
|
||||
import WalletConnect from './screens/WalletConnect';
|
||||
import { StackParamsList } from './types';
|
||||
import { web3wallet } from './utils/wallet-connect/WalletConnectUtils';
|
||||
import { EIP155_SIGNING_METHODS } from './utils/wallet-connect/EIP155Lib';
|
||||
import { EIP155_SIGNING_METHODS } from './utils/wallet-connect/EIP155Data';
|
||||
import { getSignParamsMessage } from './utils/wallet-connect/Helpers';
|
||||
import ApproveTransaction from './screens/ApproveTransaction';
|
||||
|
||||
|
@ -1,15 +1,17 @@
|
||||
import React, { useEffect, useState } from 'react';
|
||||
import React, { useEffect, useMemo, useState } from 'react';
|
||||
import { Image, View, Modal, ScrollView } from 'react-native';
|
||||
import { Button, Text } from 'react-native-paper';
|
||||
import mergeWith from 'lodash/mergeWith';
|
||||
|
||||
import { SessionTypes } from '@walletconnect/types';
|
||||
import { getSdkError } from '@walletconnect/utils';
|
||||
import { buildApprovedNamespaces, getSdkError } from '@walletconnect/utils';
|
||||
|
||||
import { PairingModalProps } from '../types';
|
||||
import { AccountsState, PairingModalProps } from '../types';
|
||||
import styles from '../styles/stylesheet';
|
||||
import { web3wallet } from '../utils/wallet-connect/WalletConnectUtils';
|
||||
import { useAccounts } from '../context/AccountsContext';
|
||||
import { useWalletConnect } from '../context/WalletConnectContext';
|
||||
import { EIP155_CHAINS } from '../utils/wallet-connect/EIP155Data';
|
||||
import { COSMOS_MAINNET_CHAINS } from '../utils/wallet-connect/COSMOSData';
|
||||
|
||||
const PairingModal = ({
|
||||
visible,
|
||||
@ -18,7 +20,7 @@ const PairingModal = ({
|
||||
setModalVisible,
|
||||
setToastVisible,
|
||||
}: PairingModalProps) => {
|
||||
const { accounts } = useAccounts();
|
||||
const { accounts, currentIndex } = useAccounts();
|
||||
|
||||
const url = currentProposal?.params?.proposer?.metadata.url;
|
||||
const icon = currentProposal?.params.proposer?.metadata.icons[0];
|
||||
@ -38,126 +40,147 @@ const PairingModal = ({
|
||||
return;
|
||||
}
|
||||
const { params } = currentProposal;
|
||||
const { requiredNamespaces } = params;
|
||||
const { requiredNamespaces, optionalNamespaces } = params;
|
||||
|
||||
setWalletConnectData({
|
||||
walletConnectMethods: [],
|
||||
walletConnectEvents: [],
|
||||
walletConnectChains: [],
|
||||
});
|
||||
Object.keys(requiredNamespaces).forEach(key => {
|
||||
switch (key) {
|
||||
case 'eip155':
|
||||
const {
|
||||
methods: ethMethods,
|
||||
events: ethEvents,
|
||||
chains: ethChains,
|
||||
} = currentProposal?.params?.requiredNamespaces.eip155;
|
||||
|
||||
setWalletConnectData(prevData => {
|
||||
return {
|
||||
walletConnectMethods: [
|
||||
...prevData.walletConnectMethods,
|
||||
...ethMethods,
|
||||
],
|
||||
walletConnectEvents: [
|
||||
...prevData.walletConnectEvents,
|
||||
...ethEvents,
|
||||
],
|
||||
walletConnectChains: ethChains
|
||||
? [...prevData.walletConnectChains, ...ethChains]
|
||||
: [...prevData.walletConnectChains],
|
||||
};
|
||||
});
|
||||
break;
|
||||
case 'cosmos':
|
||||
const {
|
||||
methods: cosmosMethods,
|
||||
events: cosmosEvents,
|
||||
chains: cosmosChains,
|
||||
} = currentProposal?.params?.requiredNamespaces.cosmos;
|
||||
const combinedNamespaces = mergeWith(
|
||||
requiredNamespaces,
|
||||
optionalNamespaces,
|
||||
(obj, src) =>
|
||||
Array.isArray(obj) && Array.isArray(src) ? [...src, ...obj] : undefined,
|
||||
);
|
||||
Object.keys(combinedNamespaces).forEach(key => {
|
||||
const { methods, events, chains } = combinedNamespaces[key];
|
||||
|
||||
setWalletConnectData(prevData => {
|
||||
return {
|
||||
walletConnectMethods: [
|
||||
...prevData.walletConnectMethods,
|
||||
...cosmosMethods,
|
||||
],
|
||||
walletConnectEvents: [
|
||||
...prevData.walletConnectEvents,
|
||||
...cosmosEvents,
|
||||
],
|
||||
walletConnectChains: cosmosChains
|
||||
? [...prevData.walletConnectChains, ...cosmosChains]
|
||||
: [...prevData.walletConnectChains],
|
||||
};
|
||||
});
|
||||
break;
|
||||
default:
|
||||
throw new Error(`${key} not supported`);
|
||||
}
|
||||
setWalletConnectData(prevData => {
|
||||
return {
|
||||
walletConnectMethods: [...prevData.walletConnectMethods, ...methods],
|
||||
walletConnectEvents: [...prevData.walletConnectEvents, ...events],
|
||||
walletConnectChains: chains
|
||||
? [...prevData.walletConnectChains, ...chains]
|
||||
: [...prevData.walletConnectChains],
|
||||
};
|
||||
});
|
||||
});
|
||||
}, [currentProposal]);
|
||||
|
||||
const { setActiveSessions } = useWalletConnect();
|
||||
|
||||
const handleAccept = async () => {
|
||||
if (currentProposal) {
|
||||
const { id, params } = currentProposal;
|
||||
const { requiredNamespaces, relays } = params;
|
||||
const namespaces: SessionTypes.Namespaces = {};
|
||||
const supportedNamespaces = useMemo(() => {
|
||||
if (!currentProposal) {
|
||||
return;
|
||||
}
|
||||
|
||||
Object.keys(requiredNamespaces).forEach(key => {
|
||||
let currentAddresses: string[];
|
||||
// eip155
|
||||
const eip155Chains = Object.keys(EIP155_CHAINS);
|
||||
|
||||
switch (key) {
|
||||
case 'eip155':
|
||||
if (accounts.ethAccounts.length > 0) {
|
||||
currentAddresses = accounts.ethAccounts.map(
|
||||
account => account.address,
|
||||
);
|
||||
}
|
||||
break;
|
||||
case 'cosmos':
|
||||
if (accounts.cosmosAccounts.length > 0) {
|
||||
currentAddresses = accounts.cosmosAccounts.map(
|
||||
account => account.address,
|
||||
);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
throw new Error(`${key} not supported`);
|
||||
// cosmos
|
||||
const cosmosChains = Object.keys(COSMOS_MAINNET_CHAINS);
|
||||
|
||||
// Set selected account as the first account in supported namespaces
|
||||
const sortedAccounts = Object.entries(accounts).reduce(
|
||||
(acc: AccountsState, [key, value]) => {
|
||||
let newValue = [...value];
|
||||
|
||||
// TODO: Implement selectedAccount instead of currentIndex in AccountsContext
|
||||
if (value.length > currentIndex) {
|
||||
const currentAccount = newValue[currentIndex];
|
||||
const remainingAccounts = newValue.filter(
|
||||
(_, index) => index !== currentIndex,
|
||||
);
|
||||
newValue = [currentAccount, ...remainingAccounts];
|
||||
}
|
||||
|
||||
const namespaceAccounts: string[] = [];
|
||||
requiredNamespaces[key].chains!.map((chain: string) => {
|
||||
currentAddresses.map(acc =>
|
||||
namespaceAccounts.push(`${chain}:${acc}`),
|
||||
);
|
||||
acc[key as 'ethAccounts' | 'cosmosAccounts'] = newValue;
|
||||
return acc;
|
||||
},
|
||||
{ ethAccounts: [], cosmosAccounts: [] },
|
||||
);
|
||||
|
||||
const { optionalNamespaces, requiredNamespaces } = currentProposal.params;
|
||||
|
||||
return {
|
||||
eip155: {
|
||||
chains: eip155Chains,
|
||||
// TODO: Debug optional namespace methods and events being required for approval
|
||||
methods: [
|
||||
...(optionalNamespaces.eip155?.methods ?? []),
|
||||
...(requiredNamespaces.eip155?.methods ?? []),
|
||||
],
|
||||
events: [
|
||||
...(optionalNamespaces.eip155?.events ?? []),
|
||||
...(requiredNamespaces.eip155?.events ?? []),
|
||||
],
|
||||
|
||||
accounts: eip155Chains
|
||||
.map(chain =>
|
||||
sortedAccounts.ethAccounts.map(
|
||||
account => `${chain}:${account.address}`,
|
||||
),
|
||||
)
|
||||
.flat(),
|
||||
},
|
||||
cosmos: {
|
||||
chains: cosmosChains,
|
||||
methods: [
|
||||
...(optionalNamespaces.cosmos?.methods ?? []),
|
||||
...(requiredNamespaces.cosmos?.methods ?? []),
|
||||
],
|
||||
events: [
|
||||
...(optionalNamespaces.cosmos?.events ?? []),
|
||||
...(requiredNamespaces.cosmos?.events ?? []),
|
||||
],
|
||||
accounts: cosmosChains
|
||||
.map(chain =>
|
||||
sortedAccounts.cosmosAccounts.map(
|
||||
account => `${chain}:${account.address}`,
|
||||
),
|
||||
)
|
||||
.flat(),
|
||||
},
|
||||
};
|
||||
}, [currentIndex, accounts, currentProposal]);
|
||||
|
||||
const namespaces = useMemo(() => {
|
||||
return (
|
||||
currentProposal &&
|
||||
supportedNamespaces &&
|
||||
buildApprovedNamespaces({
|
||||
proposal: currentProposal.params,
|
||||
supportedNamespaces,
|
||||
})
|
||||
);
|
||||
}, [currentProposal, supportedNamespaces]);
|
||||
|
||||
const handleAccept = async () => {
|
||||
try {
|
||||
if (currentProposal && namespaces) {
|
||||
const { id } = currentProposal;
|
||||
|
||||
await web3wallet!.approveSession({
|
||||
id,
|
||||
namespaces,
|
||||
});
|
||||
|
||||
namespaces[key] = {
|
||||
accounts: namespaceAccounts,
|
||||
methods: requiredNamespaces[key].methods,
|
||||
events: requiredNamespaces[key].events,
|
||||
};
|
||||
});
|
||||
|
||||
await web3wallet!.approveSession({
|
||||
id,
|
||||
relayProtocol: relays[0].protocol,
|
||||
namespaces,
|
||||
});
|
||||
|
||||
const sessions = web3wallet!.getActiveSessions();
|
||||
setActiveSessions(sessions);
|
||||
setModalVisible(false);
|
||||
setToastVisible(true);
|
||||
setCurrentProposal(undefined);
|
||||
setWalletConnectData({
|
||||
walletConnectMethods: [],
|
||||
walletConnectEvents: [],
|
||||
walletConnectChains: [],
|
||||
});
|
||||
const sessions = web3wallet!.getActiveSessions();
|
||||
setActiveSessions(sessions);
|
||||
setModalVisible(false);
|
||||
setToastVisible(true);
|
||||
setCurrentProposal(undefined);
|
||||
setWalletConnectData({
|
||||
walletConnectMethods: [],
|
||||
walletConnectEvents: [],
|
||||
walletConnectChains: [],
|
||||
});
|
||||
}
|
||||
} catch (error) {
|
||||
console.error('Error in approve session:', error);
|
||||
throw error;
|
||||
}
|
||||
};
|
||||
|
||||
@ -216,11 +239,11 @@ const PairingModal = ({
|
||||
</View>
|
||||
|
||||
<View style={styles.flexRow}>
|
||||
<Button mode="contained" onPress={() => handleAccept()}>
|
||||
<Button mode="contained" onPress={handleAccept}>
|
||||
Accept
|
||||
</Button>
|
||||
<View style={styles.space} />
|
||||
<Button mode="outlined" onPress={() => handleReject()}>
|
||||
<Button mode="outlined" onPress={handleReject}>
|
||||
Cancel
|
||||
</Button>
|
||||
</View>
|
||||
|
@ -5,9 +5,13 @@ import { AccountsState } from '../types';
|
||||
const AccountsContext = createContext<{
|
||||
accounts: AccountsState;
|
||||
setAccounts: (account: AccountsState) => void;
|
||||
currentIndex: number;
|
||||
setCurrentIndex: (index: number) => void;
|
||||
}>({
|
||||
accounts: { ethAccounts: [], cosmosAccounts: [] },
|
||||
setAccounts: () => {},
|
||||
currentIndex: 0,
|
||||
setCurrentIndex: () => {},
|
||||
});
|
||||
|
||||
const useAccounts = () => {
|
||||
@ -20,8 +24,10 @@ const AccountsProvider = ({ children }: { children: any }) => {
|
||||
ethAccounts: [],
|
||||
cosmosAccounts: [],
|
||||
});
|
||||
const [currentIndex, setCurrentIndex] = useState<number>(0);
|
||||
return (
|
||||
<AccountsContext.Provider value={{ accounts, setAccounts }}>
|
||||
<AccountsContext.Provider
|
||||
value={{ accounts, setAccounts, currentIndex, setCurrentIndex }}>
|
||||
{children}
|
||||
</AccountsContext.Provider>
|
||||
);
|
||||
|
@ -9,7 +9,7 @@ export default function useInitialization() {
|
||||
await createWeb3Wallet();
|
||||
setInitialized(true);
|
||||
} catch (err: unknown) {
|
||||
console.log('Error for initializing', err);
|
||||
console.error('Error for initializing', err);
|
||||
}
|
||||
}, []);
|
||||
|
||||
|
@ -1,7 +1,7 @@
|
||||
import React, { useEffect, useMemo, useState } from 'react';
|
||||
import React, { useCallback, useEffect, useMemo, useState } from 'react';
|
||||
import { Image, ScrollView, View } from 'react-native';
|
||||
import { ActivityIndicator, Button, Text, Appbar } from 'react-native-paper';
|
||||
import { PopulatedTransaction, providers, BigNumber } from 'ethers';
|
||||
import { providers, BigNumber } from 'ethers';
|
||||
|
||||
import { useNavigation } from '@react-navigation/native';
|
||||
import {
|
||||
@ -61,16 +61,22 @@ const ApproveTransaction = ({ route }: SignRequestProps) => {
|
||||
const navigation =
|
||||
useNavigation<NativeStackNavigationProp<StackParamsList>>();
|
||||
|
||||
const retrieveData = async (requestAddress: string) => {
|
||||
const requestAccount = await retrieveSingleAccount(network, requestAddress);
|
||||
if (!requestAccount) {
|
||||
navigation.navigate('InvalidPath');
|
||||
return;
|
||||
}
|
||||
const retrieveData = useCallback(
|
||||
async (requestAddress: string) => {
|
||||
const requestAccount = await retrieveSingleAccount(
|
||||
network,
|
||||
requestAddress,
|
||||
);
|
||||
if (!requestAccount) {
|
||||
navigation.navigate('InvalidPath');
|
||||
return;
|
||||
}
|
||||
|
||||
setAccount(requestAccount);
|
||||
setIsLoading(false);
|
||||
};
|
||||
setAccount(requestAccount);
|
||||
setIsLoading(false);
|
||||
},
|
||||
[navigation, network],
|
||||
);
|
||||
|
||||
const gasFees = useMemo(() => {
|
||||
if (network === 'eth') {
|
||||
@ -87,7 +93,7 @@ const ApproveTransaction = ({ route }: SignRequestProps) => {
|
||||
|
||||
useEffect(() => {
|
||||
retrieveData(transaction.from!);
|
||||
}, [route]);
|
||||
}, [retrieveData, transaction]);
|
||||
|
||||
const acceptRequestHandler = async () => {
|
||||
if (!account) {
|
||||
|
@ -28,7 +28,8 @@ const WCLogo = () => {
|
||||
};
|
||||
|
||||
const HomeScreen = () => {
|
||||
const { accounts, setAccounts } = useAccounts();
|
||||
const { accounts, setAccounts, currentIndex, setCurrentIndex } =
|
||||
useAccounts();
|
||||
const { setActiveSessions } = useWalletConnect();
|
||||
|
||||
const navigation =
|
||||
@ -54,7 +55,6 @@ const HomeScreen = () => {
|
||||
const [walletDialog, setWalletDialog] = useState<boolean>(false);
|
||||
const [resetWalletDialog, setResetWalletDialog] = useState<boolean>(false);
|
||||
const [network, setNetwork] = useState<string>('eth');
|
||||
const [currentIndex, setCurrentIndex] = useState<number>(0);
|
||||
const [isAccountsFetched, setIsAccountsFetched] = useState<boolean>(false);
|
||||
const [phrase, setPhrase] = useState('');
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
import React, { useEffect, useMemo, useState } from 'react';
|
||||
import React, { useCallback, useEffect, useMemo, useState } from 'react';
|
||||
import { Alert, Image, ScrollView, View } from 'react-native';
|
||||
import { ActivityIndicator, Button, Text, Appbar } from 'react-native-paper';
|
||||
|
||||
@ -60,48 +60,54 @@ const SignRequest = ({ route }: SignRequestProps) => {
|
||||
);
|
||||
}, [route.params]);
|
||||
|
||||
const retrieveData = async (
|
||||
requestNetwork: string,
|
||||
requestAddress: string,
|
||||
requestMessage: string,
|
||||
) => {
|
||||
const requestAccount = await retrieveSingleAccount(
|
||||
requestNetwork,
|
||||
requestAddress,
|
||||
);
|
||||
if (!requestAccount) {
|
||||
navigation.navigate('InvalidPath');
|
||||
return;
|
||||
}
|
||||
const retrieveData = useCallback(
|
||||
async (
|
||||
requestNetwork: string,
|
||||
requestAddress: string,
|
||||
requestMessage: string,
|
||||
) => {
|
||||
const requestAccount = await retrieveSingleAccount(
|
||||
requestNetwork,
|
||||
requestAddress,
|
||||
);
|
||||
if (!requestAccount) {
|
||||
navigation.navigate('InvalidPath');
|
||||
return;
|
||||
}
|
||||
|
||||
if (requestAccount !== account) {
|
||||
setAccount(requestAccount);
|
||||
}
|
||||
if (requestMessage !== message) {
|
||||
setMessage(decodeURIComponent(requestMessage));
|
||||
}
|
||||
if (requestNetwork !== network) {
|
||||
setNetwork(requestNetwork);
|
||||
}
|
||||
setIsLoading(false);
|
||||
};
|
||||
if (requestAccount !== account) {
|
||||
setAccount(requestAccount);
|
||||
}
|
||||
if (requestMessage !== message) {
|
||||
setMessage(decodeURIComponent(requestMessage));
|
||||
}
|
||||
if (requestNetwork !== network) {
|
||||
setNetwork(requestNetwork);
|
||||
}
|
||||
setIsLoading(false);
|
||||
},
|
||||
[account, message, navigation, network],
|
||||
);
|
||||
|
||||
const sanitizePath = (path: string) => {
|
||||
const regex = /^\/sign\/(eth|cosmos)\/(.+)\/(.+)$/;
|
||||
const match = path.match(regex);
|
||||
const sanitizePath = useCallback(
|
||||
(path: string) => {
|
||||
const regex = /^\/sign\/(eth|cosmos)\/(.+)\/(.+)$/;
|
||||
const match = path.match(regex);
|
||||
|
||||
if (match) {
|
||||
const [network, address, message] = match;
|
||||
return {
|
||||
network,
|
||||
address,
|
||||
message,
|
||||
};
|
||||
} else {
|
||||
navigation.navigate('InvalidPath');
|
||||
}
|
||||
return null;
|
||||
};
|
||||
if (match) {
|
||||
const [network, address, message] = match;
|
||||
return {
|
||||
network,
|
||||
address,
|
||||
message,
|
||||
};
|
||||
} else {
|
||||
navigation.navigate('InvalidPath');
|
||||
}
|
||||
return null;
|
||||
},
|
||||
[navigation],
|
||||
);
|
||||
|
||||
useEffect(() => {
|
||||
if (route.path) {
|
||||
@ -119,7 +125,7 @@ const SignRequest = ({ route }: SignRequestProps) => {
|
||||
route.params.address,
|
||||
route.params.message,
|
||||
);
|
||||
}, [route]);
|
||||
}, [retrieveData, sanitizePath, route]);
|
||||
|
||||
const handleWalletConnectRequest = async () => {
|
||||
const { requestEvent } = route.params;
|
||||
|
@ -12,7 +12,7 @@ export default function WalletConnect() {
|
||||
const { activeSessions, setActiveSessions } = useWalletConnect();
|
||||
|
||||
const disconnect = async (sessionId: string) => {
|
||||
await web3wallet.disconnectSession({
|
||||
await web3wallet!.disconnectSession({
|
||||
topic: sessionId,
|
||||
reason: getSdkError('USER_DISCONNECTED'),
|
||||
});
|
||||
@ -22,7 +22,7 @@ export default function WalletConnect() {
|
||||
};
|
||||
|
||||
useEffect(() => {
|
||||
const sessions = web3wallet.getActiveSessions();
|
||||
const sessions = web3wallet!.getActiveSessions();
|
||||
setActiveSessions(sessions);
|
||||
}, [setActiveSessions]);
|
||||
|
||||
|
@ -3,7 +3,7 @@
|
||||
/**
|
||||
* Types
|
||||
*/
|
||||
export type TCosmosChain = keyof typeof COSMOS_TESTNET_CHAINS;
|
||||
export type TCosmosChain = keyof typeof COSMOS_CHAINS;
|
||||
|
||||
/**
|
||||
* Chains
|
||||
@ -27,11 +27,31 @@ export const COSMOS_TESTNET_CHAINS: Record<
|
||||
},
|
||||
};
|
||||
|
||||
export const COSMOS_MAINNET_CHAINS = {
|
||||
'cosmos:cosmoshub-4': {
|
||||
chainId: 'cosmoshub-4',
|
||||
name: 'Cosmos Hub',
|
||||
logo: '/chain-logos/cosmos-cosmoshub-4.png',
|
||||
rgb: '107, 111, 147',
|
||||
rpc: '',
|
||||
namespace: 'cosmos',
|
||||
},
|
||||
};
|
||||
|
||||
export const COSMOS_CHAINS = {
|
||||
...COSMOS_MAINNET_CHAINS,
|
||||
...COSMOS_TESTNET_CHAINS,
|
||||
};
|
||||
|
||||
/**
|
||||
* Methods
|
||||
*/
|
||||
export const COSMOS_METHODS = {
|
||||
export const COSMOS_SIGNING_METHODS = {
|
||||
COSMOS_SIGN_DIRECT: 'cosmos_signDirect',
|
||||
COSMOS_SIGN_AMINO: 'cosmos_signAmino',
|
||||
};
|
||||
|
||||
export const COSMOS_METHODS = {
|
||||
...COSMOS_SIGNING_METHODS,
|
||||
COSMOS_SEND_TOKENS: 'cosmos_sendTokens', // Added for pay.laconic.com
|
||||
};
|
||||
|
@ -64,6 +64,16 @@ export const EIP155_MAINNET_CHAINS: Record<string, EIP155Chain> = {
|
||||
rpc: 'https://mainnet.era.zksync.io/',
|
||||
namespace: 'eip155',
|
||||
},
|
||||
|
||||
// Required chain by SIWE
|
||||
'eip155:42161': {
|
||||
chainId: 42161,
|
||||
name: 'Arbitrum One',
|
||||
logo: '',
|
||||
rgb: '242, 242, 242',
|
||||
rpc: 'https://arb1.arbitrum.io/rpc',
|
||||
namespace: 'eip155',
|
||||
},
|
||||
};
|
||||
|
||||
export const EIP155_TEST_CHAINS: Record<string, EIP155Chain> = {
|
||||
|
@ -51,97 +51,3 @@ export default class EIP155Lib {
|
||||
return this.wallet.signTransaction(transaction);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @desc Reference list of eip155 chains
|
||||
* @url https://chainlist.org
|
||||
*/
|
||||
|
||||
/**
|
||||
* Types
|
||||
*/
|
||||
export type TEIP155Chain = keyof typeof EIP155_CHAINS;
|
||||
|
||||
/**
|
||||
* Chains
|
||||
*/
|
||||
export const EIP155_MAINNET_CHAINS = {
|
||||
'eip155:1': {
|
||||
chainId: 1,
|
||||
name: 'Ethereum',
|
||||
logo: '/chain-logos/eip155-1.png',
|
||||
rgb: '99, 125, 234',
|
||||
rpc: 'https://cloudflare-eth.com/',
|
||||
},
|
||||
'eip155:43114': {
|
||||
chainId: 43114,
|
||||
name: 'Avalanche C-Chain',
|
||||
logo: '/chain-logos/eip155-43113.png',
|
||||
rgb: '232, 65, 66',
|
||||
rpc: 'https://api.avax.network/ext/bc/C/rpc',
|
||||
},
|
||||
'eip155:137': {
|
||||
chainId: 137,
|
||||
name: 'Polygon',
|
||||
logo: '/chain-logos/eip155-137.png',
|
||||
rgb: '130, 71, 229',
|
||||
rpc: 'https://polygon-rpc.com/',
|
||||
},
|
||||
'eip155:10': {
|
||||
chainId: 10,
|
||||
name: 'Optimism',
|
||||
logo: '/chain-logos/eip155-10.png',
|
||||
rgb: '235, 0, 25',
|
||||
rpc: 'https://mainnet.optimism.io',
|
||||
},
|
||||
};
|
||||
|
||||
export const EIP155_TEST_CHAINS = {
|
||||
'eip155:5': {
|
||||
chainId: 5,
|
||||
name: 'Ethereum Goerli',
|
||||
logo: '/chain-logos/eip155-1.png',
|
||||
rgb: '99, 125, 234',
|
||||
rpc: 'https://goerli.infura.io/v3/9aa3d95b3bc440fa88ea12eaa4456161',
|
||||
},
|
||||
'eip155:43113': {
|
||||
chainId: 43113,
|
||||
name: 'Avalanche Fuji',
|
||||
logo: '/chain-logos/eip155-43113.png',
|
||||
rgb: '232, 65, 66',
|
||||
rpc: 'https://api.avax-test.network/ext/bc/C/rpc',
|
||||
},
|
||||
'eip155:80001': {
|
||||
chainId: 80001,
|
||||
name: 'Polygon Mumbai',
|
||||
logo: '/chain-logos/eip155-137.png',
|
||||
rgb: '130, 71, 229',
|
||||
rpc: 'https://matic-mumbai.chainstacklabs.com',
|
||||
},
|
||||
'eip155:420': {
|
||||
chainId: 420,
|
||||
name: 'Optimism Goerli',
|
||||
logo: '/chain-logos/eip155-10.png',
|
||||
rgb: '235, 0, 25',
|
||||
rpc: 'https://goerli.optimism.io',
|
||||
},
|
||||
};
|
||||
|
||||
export const EIP155_CHAINS = {
|
||||
...EIP155_MAINNET_CHAINS,
|
||||
...EIP155_TEST_CHAINS,
|
||||
};
|
||||
|
||||
/**
|
||||
* Methods
|
||||
*/
|
||||
export const EIP155_SIGNING_METHODS = {
|
||||
PERSONAL_SIGN: 'personal_sign',
|
||||
ETH_SIGN: 'eth_sign',
|
||||
ETH_SIGN_TRANSACTION: 'eth_signTransaction',
|
||||
ETH_SIGN_TYPED_DATA: 'eth_signTypedData',
|
||||
ETH_SIGN_TYPED_DATA_V3: 'eth_signTypedData_v3',
|
||||
ETH_SIGN_TYPED_DATA_V4: 'eth_signTypedData_v4',
|
||||
ETH_SEND_RAW_TRANSACTION: 'eth_sendRawTransaction',
|
||||
ETH_SEND_TRANSACTION: 'eth_sendTransaction',
|
||||
};
|
||||
|
@ -3,7 +3,7 @@
|
||||
import { utils } from 'ethers';
|
||||
|
||||
import { Account } from '../../types';
|
||||
import { EIP155_CHAINS, TEIP155Chain } from './EIP155Lib';
|
||||
import { EIP155_CHAINS, TEIP155Chain } from './EIP155Data';
|
||||
|
||||
/**
|
||||
* Truncates string (in the middle) via given lenght value
|
||||
|
@ -11,7 +11,7 @@ import {
|
||||
calculateFee,
|
||||
} from '@cosmjs/stargate';
|
||||
|
||||
import { EIP155_SIGNING_METHODS } from './EIP155Lib';
|
||||
import { EIP155_SIGNING_METHODS } from './EIP155Data';
|
||||
import { signDirectMessage, signEthMessage } from '../sign-message';
|
||||
import { Account } from '../../types';
|
||||
import { getMnemonic, getPathKey } from '../misc';
|
||||
@ -60,9 +60,7 @@ export async function approveWalletConnectRequest(
|
||||
}
|
||||
|
||||
const ethSignature = await signEthMessage(message, account.counterId);
|
||||
return formatJsonRpcResult(id, {
|
||||
signature: ethSignature,
|
||||
});
|
||||
return formatJsonRpcResult(id, ethSignature);
|
||||
|
||||
case 'cosmos_signDirect':
|
||||
// Reference: https://github.com/confio/cosmjs-types/blob/66e52711914fccd2a9d1a03e392d3628fdf499e2/src/cosmos/tx/v1beta1/tx.ts#L51
|
||||
|
@ -2814,6 +2814,11 @@
|
||||
resolved "https://registry.yarnpkg.com/@types/long/-/long-4.0.2.tgz#b74129719fc8d11c01868010082d483b7545591a"
|
||||
integrity sha512-MqTGEo5bj5t157U6fA/BiDynNkn0YknVdh48CMPkTSpFTVmvao5UQmm7uEF6xBEo7qIMAlY/JSleYaE6VOdpaA==
|
||||
|
||||
"@types/lodash@^4.17.0":
|
||||
version "4.17.0"
|
||||
resolved "https://registry.yarnpkg.com/@types/lodash/-/lodash-4.17.0.tgz#d774355e41f372d5350a4d0714abb48194a489c3"
|
||||
integrity sha512-t7dhREVv6dbNj0q17X12j7yDG4bD/DHYX7o5/DbDxobP0HnGPgpRz2Ej77aL7TZT3DSw13fqUTj8J4mMnqa7WA==
|
||||
|
||||
"@types/node@*":
|
||||
version "20.11.16"
|
||||
resolved "https://registry.yarnpkg.com/@types/node/-/node-20.11.16.tgz#4411f79411514eb8e2926f036c86c9f0e4ec6708"
|
||||
|
Loading…
Reference in New Issue
Block a user