Skip to main content

Best Practices

The purpose of this guide is to show the best practices in regards of the WalletKit client usage. The goal is to provide the best user experience that just works in every circumstances.

note

In order to ensure the best user experience and flawless connection flow, please make sure that WalletKit is initialized immediately after your app launch, especially if launched via a WalletConnect Deep Link. It guarantees that websocket connection is opened immediately and all requests are received by your wallet

Pairing

A pairing is a connection between a wallet and a dapp that has fixed permissions to only allow a dapp to propose a session through it. Dapp can propose infinite number of sessions on one pairing. Wallet must use a pair method from WalletKit client to pair with dapp.

val pairingParams = Wallet.Params.Pair(pairingUri)
Web3Wallet.pair(pairingParams,
onSuccess = {
//Subscribed on the pairing topic successfully. Wallet should await for a session proposal
},
onError = { error ->
//Some error happens while pairing - check Expected errors section
}
}

Pairing State

A pairing state is a primitive exposed by the WalletKit client for a wallet to indicate whether it should await a session proposal. The pairing state is true when a wallet scans a QR and awaits a session proposal. Once the session proposal is received by the wallet, the pairing state is changed to false. When true wallet should show a loading indicator awaiting a session proposal, when changed to false a proposal dialog should be displayed.

val coreDelegate = object : CoreClient.CoreDelegate {
override fun onPairingState(pairingState: Core.Model.PairingState) {
//Here a pairing state is triggered
}
...other callbacks
}

CoreClient.setDelegate(coreDelegate)

Pairing Expiry

A pairing expiry event is triggered whenever a pairing is expired. The expiry for inactive pairing is 5 mins, whereas for active pairing is 30 days. A pairing becomes active when a session proposal is received and user successfully approves it. This event helps to know when given pairing expires and update UI accordingly.

val coreDelegate = object : CoreClient.CoreDelegate {
override fun onPairingExpired(expiredPairing: Core.Model.ExpiredPairing) {
//Here a pairing expiry is triggered
}
...other callbacks
}

CoreClient.setDelegate(coreDelegate)

Expected User flow

Pairing Flow

Pairing Error

Expected Errors

While pairing the following errors might occur:

  • No Internet connection error or pairing timeout when scanning QR with no Internet connection
    • User should pair again with Internet connection
  • Pairing expired error when scanning a QR code with expired pairing
    • User should refresh a QR code and scan again
  • Pairing with existing pairing is not allowed
    • User should refresh a QR code and scan again. I usually happens when user scans an already paired QR code.

Session Proposal

A session proposal is a handshake sent by a dapp and it's purpose is to define a session rules. Whenever a user wants to establish a connection between a wallet and a dapp, one should approve a session proposal.

User Action Feedback

Whenever user approves or rejects a session proposal, wallet should show loading indicators in a moment of the button press until Relay acknowledgement is received for any of this actions.

Session approve

 Web3Wallet.approveSession(approveProposal,
onSuccess = {
//Session approval response was sent successfully - update your UI
}
onError = { error ->
//Error while sending session approval - update your UI
})

Session reject

 Web3Wallet.rejectSession(reject,
onSuccess = {
//Session rejection response was sent successfully - update your UI
},
onError = { error ->
//Error while sending session rejection - update your UI
})

Session Proposal Expiry

A session proposal expiry is 5 mins. It means a given proposal is stored for 5 mins in the SDK storage and user has 5 mins for approval or rejection decision. After that time the below event is emitted and proposal modal should be removed from the app's UI.

val walletDelegate = object : Web3Wallet.WalletDelegate {
override fun onProposalExpired(proposal: Wallet.Model.ExpiredProposal) {
//Here this event is triggered when a proposal expires - update your UI
}
...other callbacks
}
Web3Wallet.setWalletDelegate(walletDelegate)

Expected User flow

Approve or Reject Session Proposal

Error Handling

Expected Errors

While approving or rejecting a session proposal the following errors might occurs:

  • No Internet connection
    • It happens when a user tries to approve or reject session proposal with no Internet connection
  • Session proposal expired
    • It happens when users tries to approve or reject expired session proposal
  • Invalid namespaces
    • It happens when a validation of session namespaces fails
  • Timeout
    • It happens when Relay doesn't acknowledge session settle publish within 10s

Session Request

A session request represents the request sent by a dapp to a wallet.

User Action Feedback

Whenever user approves or rejects a session request, wallet should show loading indicators in a moment of the button press until Relay acknowledgement is received for any of this actions.

Web3Wallet.respondSessionRequest(Wallet.Params.SessionRequestResponse,
onSuccess = {
//Session request response was sent successfully - update your UI
},
onError = { error ->
//Error while sending session response - update your UI
})

Session Request Expiry

A session request expiry is defined by a dapp. It's value must be between now() + 5mins and now() + 7 days. After the session request expires the below event is emitted and session request modal should be removed from the app's UI.

val walletDelegate = object : Web3Wallet.WalletDelegate {
override fun onRequestExpired(request: Wallet.Model.ExpiredRequest) {
//Here this event is triggered when a session request expires - update your UI
}
...other callbacks
}
Web3Wallet.setWalletDelegate(walletDelegate)

Expected User flow

Approve or Reject Session Proposal

Error Handling

Expected Errors

While approving or rejecting a session request the following error might occur:

  • Invalid session
    • This error might happen when user approves or rejects a session request on expired session
  • Session request expired
    • This error might happen when user approves or rejects a session request that already expires
  • Timeout
    • It happens when Relay doesn't acknowledge session settle publish within 10s

Web Socket Connection State

The Web Socket connection state tracks the connection with the relay server, event is emitted whenever a connection state changes.

val walletDelegate = object : Web3Wallet.WalletDelegate {
override fun onConnectionStateChange(state: Wallet.Model.ConnectionState) {
//Here this event is triggered when a connection state has changed
}
...other callbacks
}
Web3Wallet.setWalletDelegate(walletDelegate)

Expected User flow

Connection State