-
-
Notifications
You must be signed in to change notification settings - Fork 1k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
docs: ethers adapters reference implementation (#2563)
* docs: ethers adapters reference implementation * trigger * docs: update
- Loading branch information
Showing
5 changed files
with
349 additions
and
3 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,168 @@ | ||
--- | ||
title: 'Ethers.js Adapters' | ||
description: 'Adapters for ethers.js' | ||
--- | ||
|
||
import { Tabs, Tab } from 'nextra-theme-docs' | ||
|
||
# Ethers.js Adapters | ||
|
||
It is recommended for projects to migrate to [viem](https://viem.sh) when using wagmi, but there are some cases where you might still need to use [ethers.js](https://ethers.org/) in your project: | ||
|
||
- You may want to **incrementally migrate** ethers.js usage to viem | ||
- Some **third-party libraries & SDKs** may only support ethers.js | ||
|
||
We have provided reference implementations for viem → ethers.js adapters that you can copy + paste in your project. | ||
|
||
## Public Client → Provider | ||
|
||
### Reference Implementation | ||
|
||
Copy the following reference implementation into a file of your choice: | ||
|
||
<Tabs items={['ethers.js v5', 'ethers.js v6']}> | ||
<Tab> | ||
```ts filename="src/ethers.ts" | ||
import { type PublicClient, getPublicClient } from '@wagmi/core' | ||
import { providers } from 'ethers' | ||
import { type HttpTransport } from 'viem' | ||
|
||
export function publicClientToProvider(publicClient: PublicClient) { | ||
const { chain, transport } = publicClient | ||
const network = { | ||
chainId: chain.id, | ||
name: chain.name, | ||
ensAddress: chain.contracts?.ensRegistry?.address, | ||
} | ||
if (transport.type === 'fallback') | ||
return new providers.FallbackProvider( | ||
(transport.transports as ReturnType<HttpTransport>[]).map( | ||
({ value }) => new providers.JsonRpcProvider(value?.url, network), | ||
), | ||
) | ||
return new providers.JsonRpcProvider(transport.url, network) | ||
} | ||
|
||
/** Action to convert a viem Public Client to an ethers.js Provider. */ | ||
export function getEthersProvider({ chainId }: { chainId?: number } = {}) { | ||
const publicClient = getPublicClient({ chainId }) | ||
return publicClientToProvider(publicClient) | ||
} | ||
``` | ||
</Tab> | ||
<Tab> | ||
```ts filename="src/ethers.ts" | ||
import { type PublicClient, getPublicClient } from '@wagmi/core' | ||
import { FallbackProvider, JsonRpcProvider } from 'ethers' | ||
import { type HttpTransport } from 'viem' | ||
|
||
export function publicClientToProvider(publicClient: PublicClient) { | ||
const { chain, transport } = publicClient | ||
const network = { | ||
chainId: chain.id, | ||
name: chain.name, | ||
ensAddress: chain.contracts?.ensRegistry?.address, | ||
} | ||
if (transport.type === 'fallback') { | ||
const providers = (transport.transports as ReturnType<HttpTransport>[]).map( | ||
({ value }) => new JsonRpcProvider(value?.url, network), | ||
) | ||
if (providers.length === 1) return providers[0] | ||
return new FallbackProvider(providers) | ||
} | ||
return new JsonRpcProvider(transport.url, network) | ||
} | ||
|
||
/** Action to convert a viem Public Client to an ethers.js Provider. */ | ||
export function getEthersProvider({ chainId }: { chainId?: number } = {}) { | ||
const publicClient = getPublicClient({ chainId }) | ||
return publicClientToProvider(publicClient) | ||
} | ||
``` | ||
</Tab> | ||
</Tabs> | ||
|
||
### Usage | ||
|
||
Now you can use the `useEthersProvider` Hook in your components: | ||
|
||
```ts filename="src/example.ts" | ||
import { getEthersProvider } from './ethers' | ||
|
||
function example() { | ||
const provider = getEthersProvider() | ||
... | ||
} | ||
``` | ||
|
||
## Wallet Client → Signer | ||
|
||
### Reference Implementation | ||
|
||
Copy the following reference implementation into a file of your choice: | ||
|
||
<Tabs items={['ethers.js v5', 'ethers.js v6']}> | ||
<Tab> | ||
```ts filename="src/ethers.ts" | ||
import { type WalletClient, getWalletClient } from '@wagmi/core' | ||
import { providers } from 'ethers' | ||
|
||
export function walletClientToSigner(walletClient: WalletClient) { | ||
const { account, chain, transport } = walletClient | ||
const network = { | ||
chainId: chain.id, | ||
name: chain.name, | ||
ensAddress: chain.contracts?.ensRegistry?.address, | ||
} | ||
const provider = new providers.Web3Provider(transport, network) | ||
const signer = provider.getSigner(account.address) | ||
return signer | ||
} | ||
|
||
/** Action to convert a viem Wallet Client to an ethers.js Signer. */ | ||
export async function getEthersSigner({ chainId }: { chainId?: number } = {}) { | ||
const walletClient = await getWalletClient({ chainId }) | ||
if (!walletClient) return undefined | ||
return walletClientToSigner(walletClient) | ||
} | ||
``` | ||
</Tab> | ||
<Tab> | ||
```ts filename="src/ethers.ts" | ||
import { type WalletClient, useWalletClient } from 'wagmi' | ||
import { BrowserProvider, JsonRpcSigner } from 'ethers' | ||
|
||
export function walletClientToSigner(walletClient: WalletClient) { | ||
const { account, chain, transport } = walletClient | ||
const network = { | ||
chainId: chain.id, | ||
name: chain.name, | ||
ensAddress: chain.contracts?.ensRegistry?.address, | ||
} | ||
const provider = new BrowserProvider(transport, network) | ||
const signer = new JsonRpcSigner(provider, account.address) | ||
return signer | ||
} | ||
|
||
/** Action to convert a viem Wallet Client to an ethers.js Signer. */ | ||
export async function getEthersSigner({ chainId }: { chainId?: number } = {}) { | ||
const walletClient = await getWalletClient({ chainId }) | ||
if (!walletClient) return undefined | ||
return walletClientToSigner(walletClient) | ||
} | ||
``` | ||
</Tab> | ||
</Tabs> | ||
|
||
### Usage | ||
|
||
Now you can use the `useEthersSigner` Hook in your components: | ||
|
||
```ts filename="src/example.ts" | ||
import { getEthersSigner } from './ethers' | ||
|
||
function example() { | ||
const signer = getEthersSigner() | ||
... | ||
} | ||
``` |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,176 @@ | ||
--- | ||
title: 'Ethers.js Adapters' | ||
description: 'Adapters for ethers.js' | ||
--- | ||
|
||
import { Tabs, Tab } from 'nextra-theme-docs' | ||
|
||
# Ethers.js Adapters | ||
|
||
It is recommended for projects to migrate to [viem](https://viem.sh) when using wagmi, but there are some cases where you might still need to use [ethers.js](https://ethers.org/) in your project: | ||
|
||
- You may want to **incrementally migrate** ethers.js usage to viem | ||
- Some **third-party libraries & SDKs** may only support ethers.js | ||
|
||
We have provided reference implementations for viem → ethers.js adapters that you can copy + paste in your project. | ||
|
||
## Public Client → Provider | ||
|
||
### Reference Implementation | ||
|
||
Copy the following reference implementation into a file of your choice: | ||
|
||
<Tabs items={['ethers.js v5', 'ethers.js v6']}> | ||
<Tab> | ||
```ts filename="src/ethers.ts" | ||
import * as React from 'react' | ||
import { type PublicClient, usePublicClient } from 'wagmi' | ||
import { providers } from 'ethers' | ||
import { type HttpTransport } from 'viem' | ||
|
||
export function publicClientToProvider(publicClient: PublicClient) { | ||
const { chain, transport } = publicClient | ||
const network = { | ||
chainId: chain.id, | ||
name: chain.name, | ||
ensAddress: chain.contracts?.ensRegistry?.address, | ||
} | ||
if (transport.type === 'fallback') | ||
return new providers.FallbackProvider( | ||
(transport.transports as ReturnType<HttpTransport>[]).map( | ||
({ value }) => new providers.JsonRpcProvider(value?.url, network), | ||
), | ||
) | ||
return new providers.JsonRpcProvider(transport.url, network) | ||
} | ||
|
||
/** Hook to convert a viem Public Client to an ethers.js Provider. */ | ||
export function useEthersProvider({ chainId }: { chainId?: number } = {}) { | ||
const publicClient = usePublicClient({ chainId }) | ||
return React.useMemo(() => publicClientToProvider(publicClient), [publicClient]) | ||
} | ||
``` | ||
</Tab> | ||
<Tab> | ||
```ts filename="src/ethers.ts" | ||
import * as React from 'react' | ||
import { type PublicClient, usePublicClient } from 'wagmi' | ||
import { FallbackProvider, JsonRpcProvider } from 'ethers' | ||
import { type HttpTransport } from 'viem' | ||
|
||
export function publicClientToProvider(publicClient: PublicClient) { | ||
const { chain, transport } = publicClient | ||
const network = { | ||
chainId: chain.id, | ||
name: chain.name, | ||
ensAddress: chain.contracts?.ensRegistry?.address, | ||
} | ||
if (transport.type === 'fallback') { | ||
const providers = (transport.transports as ReturnType<HttpTransport>[]).map( | ||
({ value }) => new JsonRpcProvider(value?.url, network), | ||
) | ||
if (providers.length === 1) return providers[0] | ||
return new FallbackProvider(providers) | ||
} | ||
return new JsonRpcProvider(transport.url, network) | ||
} | ||
|
||
/** Hook to convert a viem Public Client to an ethers.js Provider. */ | ||
export function useEthersProvider({ chainId }: { chainId?: number } = {}) { | ||
const publicClient = usePublicClient({ chainId }) | ||
return React.useMemo(() => publicClientToProvider(publicClient), [publicClient]) | ||
} | ||
``` | ||
</Tab> | ||
</Tabs> | ||
|
||
### Usage | ||
|
||
Now you can use the `useEthersProvider` Hook in your components: | ||
|
||
```ts filename="src/Example.ts" | ||
import { useEthersProvider } from './ethers' | ||
|
||
function Example() { | ||
const provider = useEthersProvider() | ||
... | ||
} | ||
``` | ||
|
||
## Wallet Client → Signer | ||
|
||
### Reference Implementation | ||
|
||
Copy the following reference implementation into a file of your choice: | ||
|
||
<Tabs items={['ethers.js v5', 'ethers.js v6']}> | ||
<Tab> | ||
```ts filename="src/ethers.ts" | ||
import * as React from 'react' | ||
import { type WalletClient, useWalletClient } from 'wagmi' | ||
import { providers } from 'ethers' | ||
|
||
export function walletClientToSigner(walletClient: WalletClient) { | ||
const { account, chain, transport } = walletClient | ||
const network = { | ||
chainId: chain.id, | ||
name: chain.name, | ||
ensAddress: chain.contracts?.ensRegistry?.address, | ||
} | ||
const provider = new providers.Web3Provider(transport, network) | ||
const signer = provider.getSigner(account.address) | ||
return signer | ||
} | ||
|
||
/** Hook to convert a viem Wallet Client to an ethers.js Signer. */ | ||
export function useEthersSigner({ chainId }: { chainId?: number } = {}) { | ||
const { data: walletClient } = useWalletClient({ chainId }) | ||
return React.useMemo( | ||
() => (walletClient ? walletClientToSigner(walletClient) : undefined), | ||
[walletClient], | ||
) | ||
} | ||
``` | ||
</Tab> | ||
<Tab> | ||
```ts filename="src/ethers.ts" | ||
import * as React from 'react' | ||
import { type WalletClient, useWalletClient } from 'wagmi' | ||
import { BrowserProvider, JsonRpcSigner } from 'ethers' | ||
|
||
export function walletClientToSigner(walletClient: WalletClient) { | ||
const { account, chain, transport } = walletClient | ||
const network = { | ||
chainId: chain.id, | ||
name: chain.name, | ||
ensAddress: chain.contracts?.ensRegistry?.address, | ||
} | ||
const provider = new BrowserProvider(transport, network) | ||
const signer = new JsonRpcSigner(provider, account.address) | ||
return signer | ||
} | ||
|
||
/** Hook to convert a viem Wallet Client to an ethers.js Signer. */ | ||
export function useEthersSigner({ chainId }: { chainId?: number } = {}) { | ||
const { data: walletClient } = useWalletClient({ chainId }) | ||
return React.useMemo( | ||
() => (walletClient ? walletClientToSigner(walletClient) : undefined), | ||
[walletClient], | ||
) | ||
} | ||
``` | ||
</Tab> | ||
</Tabs> | ||
|
||
### Usage | ||
|
||
Now you can use the `useEthersSigner` Hook in your components: | ||
|
||
```ts filename="src/Example.ts" | ||
import { useEthersSigner } from './ethers' | ||
|
||
function Example() { | ||
const signer = useEthersSigner() | ||
... | ||
} | ||
``` |
912adb2
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Successfully deployed to the following URLs:
wagmi – ./docs
wagmi-xyz.vercel.app
wagmi-dev.vercel.app
0.10.x.wagmi.sh
wagmi-wagmi-dev.vercel.app
wagmi.sh
wagmi-git-main-wagmi-dev.vercel.app
www.wagmi.sh