Skip to content

Commit

Permalink
Simplify and fix useSessions
Browse files Browse the repository at this point in the history
  • Loading branch information
katspaugh committed Sep 23, 2023
1 parent 569df38 commit a8b6d0c
Show file tree
Hide file tree
Showing 7 changed files with 63 additions and 58 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -27,4 +27,4 @@
.alert {
width: 100%;
text-align: left;
}
}
2 changes: 1 addition & 1 deletion src/components/walletconnect/SessionList/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import { Button, Typography } from '@mui/material'
import type { SessionTypes } from '@walletconnect/types'

type SesstionListProps = {
sessions: Record<string, SessionTypes.Struct>
sessions: SessionTypes.Struct[]
onDisconnect: (session: SessionTypes.Struct) => void
}

Expand Down
4 changes: 2 additions & 2 deletions src/components/walletconnect/SessionManager/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,18 +4,18 @@ import type { SessionTypes } from '@walletconnect/types'

import useSafeInfo from '@/hooks/useSafeInfo'
import { WalletConnectContext } from '@/services/walletconnect/WalletConnectContext'
import useWalletConnectSessions from '@/services/walletconnect/useWalletConnectSessions'
import { asError } from '@/services/exceptions/utils'
import ProposalForm from '../ProposalForm'
import WcInput from '../WcInput'
import ErrorMessage from '@/components/tx/ErrorMessage'
import SessionList from '../SessionList'
import { useSessions } from './useSessions'

const SessionManager = () => {
const { safe, safeAddress } = useSafeInfo()
const { chainId } = safe
const { walletConnect, error: walletConnectError } = useContext(WalletConnectContext)
const sessions = useSessions()
const sessions = useWalletConnectSessions()
const [proposal, setProposal] = useState<Web3WalletTypes.SessionProposal>()
const [error, setError] = useState<Error>()

Expand Down
48 changes: 0 additions & 48 deletions src/components/walletconnect/SessionManager/useSessions.ts

This file was deleted.

4 changes: 2 additions & 2 deletions src/services/walletconnect/WalletConnectContext.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -31,14 +31,14 @@ export const WalletConnectProvider = ({ children }: { children: ReactNode }) =>
// Update chainId
useEffect(() => {
if (chainId) {
walletConnect.chainChanged(chainId)
walletConnect.chainChanged(chainId).catch(setError)
}
}, [chainId])

// Update accounts
useEffect(() => {
if (safeAddress && chainId) {
walletConnect.accountsChanged(chainId, safeAddress)
walletConnect.accountsChanged(chainId, safeAddress).catch(setError)
}
}, [chainId, safeAddress])

Expand Down
33 changes: 29 additions & 4 deletions src/services/walletconnect/WalletConnectWallet.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,10 +12,17 @@ import { invariant } from '@/utils/helpers'
import { getEip155ChainId } from './utils'
import type { Eip155ChainId } from './utils'

const SESSION_ADD_EVENT = 'session_add' as 'session_delete' // Workaround: WalletConnect doesn't emit session_add event

function assertWeb3Wallet<T extends Web3WalletType | null>(web3Wallet: T): asserts web3Wallet {
return invariant(web3Wallet, 'WalletConnect not initialized')
}

/**
* An abstraction over the WalletConnect SDK to simplify event subscriptions
* and add workarounds for dapps requesting wrong required chains.
* Should be kept stateless exept for the web3Wallet instance.
*/
class WalletConnectWallet {
private web3Wallet: Web3WalletType | null = null

Expand Down Expand Up @@ -52,7 +59,7 @@ class WalletConnectWallet {
const eipChainId = getEip155ChainId(chainId)

await Promise.all(
Object.keys(sessions).map((topic) => {
sessions.map(({ topic }) => {
return this.web3Wallet?.emitSessionEvent({
topic,
event: {
Expand All @@ -70,7 +77,7 @@ class WalletConnectWallet {
const eipChainId = getEip155ChainId(chainId)

await Promise.all(
Object.keys(sessions).map((topic) => {
sessions.map(({ topic }) => {
return this.web3Wallet?.emitSessionEvent({
topic,
event: {
Expand Down Expand Up @@ -132,6 +139,9 @@ class WalletConnectWallet {
// Ignore
}

// Workaround: WalletConnect doesn't have a session_add event
this.web3Wallet?.events.emit(SESSION_ADD_EVENT, session)

return session
}
}
Expand All @@ -158,6 +168,17 @@ class WalletConnectWallet {
}
}

/**
* Subscribe to session add
*/
public onSessionAdd(handler: () => void) {
this.web3Wallet?.on(SESSION_ADD_EVENT, handler)

return () => {
this.web3Wallet?.off(SESSION_ADD_EVENT, handler)
}
}

/**
* Subscribe to session delete
*/
Expand All @@ -179,13 +200,17 @@ class WalletConnectWallet {
topic: session.topic,
reason: getSdkError('USER_DISCONNECTED'),
})

// Workaround: WalletConnect doesn't emit session_approve event
this.web3Wallet?.events.emit('session_delete', session)
}

/**
* Get active sessions
*/
public getActiveSessions() {
return this.web3Wallet?.getActiveSessions() || {}
public getActiveSessions(): SessionTypes.Struct[] {
const sessionsMap = this.web3Wallet?.getActiveSessions() || {}
return Object.values(sessionsMap)
}

/**
Expand Down
28 changes: 28 additions & 0 deletions src/services/walletconnect/useWalletConnectSessions.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
import { useContext, useEffect, useCallback, useState } from 'react'
import type { SessionTypes } from '@walletconnect/types'
import { WalletConnectContext } from '@/services/walletconnect/WalletConnectContext'

function useWalletConnectSessions(): SessionTypes.Struct[] {
const { walletConnect } = useContext(WalletConnectContext)
const [sessions, setSessions] = useState<SessionTypes.Struct[]>([])

const updateSessions = useCallback(() => {
setSessions(walletConnect.getActiveSessions())
}, [walletConnect])

useEffect(() => {
walletConnect.init().then(updateSessions)
}, [walletConnect, updateSessions])

useEffect(() => {
return walletConnect.onSessionAdd(updateSessions)
}, [walletConnect])

useEffect(() => {
return walletConnect.onSessionDelete(updateSessions)
}, [walletConnect])

return sessions
}

export default useWalletConnectSessions

0 comments on commit a8b6d0c

Please sign in to comment.