Skip to Content
dAppsWagmi

React + wagmi

This guide shows a minimal, EIP‑1193‑based way to connect OneKey from React apps using wagmi. Use OneKey’s dedicated provider (window.$onekey.ethereum) so a button labeled OneKey connects to OneKey.

Install

npm i wagmi@^2 viem@^2 @tanstack/react-query@^5

wagmi v2 is built on viem. This guide uses the Injected connector to work with injected wallets (OneKey / other EIP‑1193 providers).

Create a OneKey injected connector

Prefer OneKey’s dedicated injection to avoid ambiguity when multiple wallets are installed.

// onekeyConnector.ts import { createConfig, http } from 'wagmi' import { mainnet, polygon, arbitrum, base, optimism } from 'wagmi/chains' import { injected } from 'wagmi/connectors' import type { EIP1193Provider } from 'viem' function getOneKeyProvider(): EIP1193Provider | undefined { if (typeof window === 'undefined') return undefined const walletWindow = window as Window & { $onekey?: { ethereum?: EIP1193Provider } } return walletWindow.$onekey?.ethereum } export const config = createConfig({ chains: [mainnet, polygon, arbitrum, base, optimism], connectors: [ injected({ target() { return { id: 'onekey', name: 'OneKey', provider: getOneKeyProvider(), } }, shimDisconnect: true, }), ], transports: { [mainnet.id]: http(), [polygon.id]: http(), [arbitrum.id]: http(), [base.id]: http(), [optimism.id]: http(), }, })

Notes

  • Prefer window.$onekey.ethereum to keep behavior deterministic in multi‑wallet environments.
  • If OneKey is unavailable, show an install or retry option. Other wallets discovered by wagmi keep their own names.
  • Trigger eth_requestAccounts on a user gesture and handle 4001 (user rejected), without retrying automatically.

App setup

// main.tsx import React from 'react' import ReactDOM from 'react-dom/client' import { WagmiProvider } from 'wagmi' import { QueryClient, QueryClientProvider } from '@tanstack/react-query' import { config } from './onekeyConnector' import App from './App' const queryClient = new QueryClient() ReactDOM.createRoot(document.getElementById('root')!).render( <React.StrictMode> <WagmiProvider config={config}> <QueryClientProvider client={queryClient}> <App /> </QueryClientProvider> </WagmiProvider> </React.StrictMode>, )

Connect and read account

// App.tsx import { useAccount, useConnect, useDisconnect } from 'wagmi' export default function App() { const { address, isConnected } = useAccount() const { connect, connectors, isPending, error } = useConnect() const { disconnect } = useDisconnect() if (isConnected) { return ( <div> <p>Connected: {address}</p> <button onClick={() => disconnect()}>Disconnect</button> </div> ) } return ( <div> {error && <p role="alert">{error.message}</p>} {connectors.map((c) => ( <button key={c.uid} disabled={isPending} onClick={() => connect({ connector: c })}> Connect with {c.name} </button> ))} </div> ) }

Sign and send

Use the active wagmi connection for signing. Run wallet requests from user actions and display rejected requests in your UI.

import { useState } from 'react' import { useWalletClient } from 'wagmi' function SignMessageButton() { const { data: walletClient } = useWalletClient() const [result, setResult] = useState('') const [pending, setPending] = useState(false) async function sign() { if (!walletClient) return setPending(true) try { const signature = await walletClient.signMessage({ message: 'Hello from my dApp' }) setResult(signature) } catch (error) { setResult(error instanceof Error ? error.message : 'Signature request failed') } finally { setPending(false) } } return <> <button disabled={!walletClient || pending} onClick={sign}>Sign message</button> <p role="status">{result}</p> </> }

For transactions, use wagmi’s useSendTransaction with a validated recipient, amount, and selected chain. A returned transaction hash means it was submitted; wait for a receipt to determine execution success. See Sending transactions.

Events and network

  • Listen to accountsChanged / chainChanged and refresh session state accordingly.
  • Network switching/adding: wallet_switchEthereumChain and wallet_addEthereumChain.

Mobile and discovery

For mobile wallets outside an injected browser, use a WalletConnect connector or wallet UI library. A deep link opens the wallet; the WalletConnect session establishes the connection.

wagmi can discover EIP-6963 wallets through createConfig’s multiInjectedProviderDiscovery option. For a direct implementation, see Provider discovery.

Troubleshooting

  • If the provider is missing, verify that OneKey is installed and enabled for this site, then retry from the Connect button.
  • Handle user rejection (4001) by allowing another user-initiated attempt.
  • Run browser provider access on the client. The typeof window guard above prevents server-side rendering errors.
  • A simulated disconnect clears wagmi’s connection state; it does not necessarily revoke permissions in the wallet.

Resources

Last updated on