remix-project mirror
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
remix-project/apps/walletconnect/src/services/WalletConnectRemixClient.ts

135 lines
4.3 KiB

import { PluginClient } from '@remixproject/plugin'
import { createClient } from '@remixproject/plugin-webview'
import { createWeb3Modal, defaultConfig } from '@web3modal/ethers5/react'
import { constants } from '../utils/constants'
import EventManager from 'events'
import { PROJECT_ID as projectId, METADATA as metadata } from './constant'
import { Chain, RequestArguments } from '../types'
export class WalletConnectRemixClient extends PluginClient {
web3modal: ReturnType<typeof createWeb3Modal>
ethersConfig: ReturnType<typeof defaultConfig>
chains: Chain[]
currentChain: number
internalEvents: EventManager
currentAccount: string
constructor() {
super()
createClient(this)
this.internalEvents = new EventManager()
this.methods = ['sendAsync', 'init', 'deactivate']
this.onload()
}
onActivation() {
this.subscribeToEvents()
this.call('theme', 'currentTheme').then((theme: any) => {
this.internalEvents.emit('themeChanged', theme.quality.toLowerCase())
})
}
init() {
console.log('initializing walletconnect plugin...')
}
initClient() {
try {
const ethersConfig = defaultConfig({
metadata,
rpcUrl: 'https://cloudflare-eth.com'
})
this.web3modal = createWeb3Modal({ projectId, chains: constants.chains, metadata, ethersConfig })
this.ethersConfig = ethersConfig
this.chains = constants.chains
} catch (e) {
return console.error('Could not get a wallet connection', e)
}
}
subscribeToEvents() {
this.web3modal.subscribeProvider(({ address, isConnected, chainId })=>{
if (isConnected){
if (address !== this.currentAccount) {
this.currentAccount = address
this.emit('accountsChanged', [address])
}
if (this.currentChain !== chainId) {
this.currentChain = chainId
this.emit('chainChanged', chainId)
}
} else {
this.emit('accountsChanged', [])
this.currentAccount = ''
this.emit('chainChanged', 0)
this.currentChain = 0
}
},)
this.on('theme', 'themeChanged', (theme: any) => {
this.web3modal.setThemeMode(theme.quality)
})
}
async sendAsync(data: RequestArguments) {
const address = this.web3modal.getAddress()
const provider = this.web3modal.getWalletProvider()
if (address && provider) {
if (data.method === 'eth_accounts') {
return {
jsonrpc: '2.0',
result: [address],
id: data.id
}
} else {
//@ts-expect-error this flag does not correspond to EIP-1193 but was introduced by MetaMask
if (provider.isMetamask && provider.sendAsync) {
return new Promise((resolve) => {
//@ts-expect-error sendAsync is a legacy function we know MetaMask supports it
provider.sendAsync(data, (error, response) => {
if (error) {
if (error.data && error.data.originalError && error.data.originalError.data) {
resolve({
jsonrpc: '2.0',
error: error.data.originalError,
id: data.id
})
} else if (error.data && error.data.message) {
resolve({
jsonrpc: '2.0',
error: error.data && error.data,
id: data.id
})
} else {
resolve({
jsonrpc: '2.0',
error,
id: data.id
})
}
}
return resolve(response)
})
})
} else {
try {
const message = await provider.request(data)
return { jsonrpc: '2.0', result: message, id: data.id }
} catch (e) {
return { jsonrpc: '2.0', error: { message: e.message, code: -32603 }, id: data.id }
}
}
}
} else {
const err = `Cannot make ${data.method} request. Remix client is not connected to walletconnect client`
console.error(err)
return { jsonrpc: '2.0', error: { message: err, code: -32603 }, id: data.id }
}
}
async deactivate() {
console.log('deactivating walletconnect plugin...')
await this.web3modal.disconnect()
}
}