npm package: @liberfi.io/wallet-connector-privy
Description: Privy wallet connector for Liberfi React SDK
Latest version: 0.1.147

# @liberfi.io/wallet-connector-privy

Privy-based implementation of the Liberfi wallet connector. This package wraps [@privy-io/react-auth](https://docs.privy.io/) and bridges Privy's authentication and multi-chain wallet management into the `@liberfi.io/wallet-connector` provider interfaces (`WalletConnectorProvider` and `AuthProvider`). It exposes EVM and Solana wallet adapters that conform to the shared `WalletAdapter` / `EvmWalletAdapter` interfaces, so consumers can interact with wallets through a single, provider-agnostic API.

## Design Philosophy

- **Adapter pattern** — Privy-specific types and hooks are fully encapsulated; consumers only interact with the `@liberfi.io/wallet-connector` API (`useWalletConnector`, `useAuth`, `WalletAdapter`).
- **Composable providers** — `PrivyWalletConnectorProvider` handles wallet connection; `PrivyAuthProvider` handles authentication and token exchange. They compose in a specific parent-child order, giving the consumer control over where each concern sits in the component tree.
- **Inversion of control** — Side effects (e.g. custom access-token exchange) are injected via callbacks. Privy SDK behavior is customizable through `privyClientConfig`. The package does not hardcode toast/navigation/analytics.
- **Minimal public API** — Only two provider components and a version string are exported. Internal adapters and wiring are kept private.

## Installation

```bash
pnpm add @liberfi.io/wallet-connector-privy
```

### Peer Dependencies

The consumer must provide:

| Package                        | Version       |
| ------------------------------ | ------------- |
| `@liberfi.io/wallet-connector` | `workspace:*` |
| `@privy-io/react-auth`         | `^3.0.1`      |
| `@solana/web3.js`              | `^1.98.4`     |
| `ethers`                       | `^6.15.0`     |
| `react`                        | `>=18`        |
| `react-dom`                    | `>=18`        |

## API Reference

### Components

#### `PrivyWalletConnectorProvider`

Top-level provider that wraps Privy's `PrivyProvider` and an internal `WalletConnectorAdapter`. Must be an ancestor of any component that uses `useWalletConnector` or `PrivyAuthProvider`.

| Prop                | Type                | Required | Description                                                                                                                                                          |
| ------------------- | ------------------- | -------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `privyAppId`        | `string`            | Yes      | Your Privy application ID from the [Privy Dashboard](https://dashboard.privy.io/) (App Settings > Basics).                                                           |
| `privyClientId`     | `string`            | No       | Your app client ID from the [Privy Dashboard](https://dashboard.privy.io/) (App Settings > Clients).                                                                 |
| `privyClientConfig` | `PrivyClientConfig` | No       | Configuration for the Privy SDK ([docs](https://docs.privy.io/basics/react/setup)). Merged with internal defaults (e.g. Solana wallet connectors with auto-connect). |
| `children`          | `ReactNode`         | —        | Child components.                                                                                                                                                    |

#### `PrivyAuthProvider`

Authentication provider that maps Privy auth state into `AuthProvider` from `@liberfi.io/wallet-connector`. **Must be a child of `PrivyWalletConnectorProvider`.**

| Prop                  | Type                                                                                   | Required | Description                                                                                                                                         |
| --------------------- | -------------------------------------------------------------------------------------- | -------- | --------------------------------------------------------------------------------------------------------------------------------------------------- |
| `exchangeAccessToken` | `(accessToken: string, identityToken: string) => Promise<string \| undefined \| null>` | No       | Callback to exchange Privy's access token and identity token for a custom access token. If not provided, Privy's own access token is used directly. |
| `children`            | `ReactNode`                                                                            | —        | Child components.                                                                                                                                   |

### Constants

#### `version`

```typescript
import { version } from "@liberfi.io/wallet-connector-privy";

// "0.1.23"
```

Current package version string. Also registered on `window.__LIBERFI_VERSION__` at import time.

### Internal Architecture (not exported)

| Module                     | Role                                                                                                                                                                      |
| -------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `WalletConnectorAdapter`   | React component that consumes Privy hooks, builds `WalletAdapter[]` from linked accounts, maps Privy status to connector status, and feeds `WalletConnectorProvider`.     |
| `PrivyEvmWalletAdapter`    | Implements `EvmWalletAdapter` — wraps Privy's EVM sign/send hooks. Supports `signMessage`, `signTransaction`, `sendTransaction`, `getEip1193Provider`, and `switchChain`. |
| `PrivySolanaWalletAdapter` | Implements `WalletAdapter` — wraps Privy's Solana sign/send hooks. Supports `signMessage`, `signTransaction`, and `sendTransaction`.                                      |

## Usage Examples

### Basic Setup

```tsx
import {
  PrivyWalletConnectorProvider,
  PrivyAuthProvider,
} from "@liberfi.io/wallet-connector-privy";

function App() {
  return (
    <PrivyWalletConnectorProvider
      privyAppId="your-privy-app-id"
      privyClientConfig={{
        appearance: {
          theme: "dark",
          accentColor: "#BCFF2E",
          walletList: [
            "phantom",
            "metamask",
            "okx_wallet",
            "wallet_connect",
            "detected_ethereum_wallets",
            "detected_solana_wallets",
          ],
          walletChainType: "ethereum-and-solana",
        },
        loginMethods: ["email", "wallet", "google"],
        embeddedWallets: {
          ethereum: { createOnLogin: "users-without-wallets" },
          solana: { createOnLogin: "users-without-wallets" },
        },
      }}
    >
      <PrivyAuthProvider>
        <YourApp />
      </PrivyAuthProvider>
    </PrivyWalletConnectorProvider>
  );
}
```

### With Custom Access Token Exchange

```tsx
import {
  PrivyWalletConnectorProvider,
  PrivyAuthProvider,
} from "@liberfi.io/wallet-connector-privy";

async function exchangeToken(accessToken: string, identityToken: string) {
  const res = await fetch("/api/auth/exchange", {
    method: "POST",
    headers: { "Content-Type": "application/json" },
    body: JSON.stringify({ accessToken, identityToken }),
  });
  const { token } = await res.json();
  return token;
}

function App() {
  return (
    <PrivyWalletConnectorProvider privyAppId="your-privy-app-id">
      <PrivyAuthProvider exchangeAccessToken={exchangeToken}>
        <YourApp />
      </PrivyAuthProvider>
    </PrivyWalletConnectorProvider>
  );
}
```

### Using the Wallet Connector Hooks

Once the providers are in place, use hooks from `@liberfi.io/wallet-connector`:

```tsx
import { useWalletConnector, useAuth } from "@liberfi.io/wallet-connector";

function ConnectButton() {
  const { status, connect, disconnect } = useWalletConnector();
  const { status: authStatus, signIn, signOut, user } = useAuth();

  return (
    <div>
      <button onClick={status === "connected" ? disconnect : connect}>
        {status === "connected" ? "Disconnect" : "Connect Wallet"}
      </button>

      {user?.wallets.map((wallet) => (
        <div key={wallet.address}>
          {wallet.connector} — {wallet.address} ({wallet.chain ?? "unknown"})
        </div>
      ))}
    </div>
  );
}
```

## Future Improvements

- **Remove unused dependencies** — `package.json` lists five unused `dependencies` (`@ethereumjs/tx`, `@solana-program/memo`, `@solana-program/system`, `@solana-program/token`, `@solana/kit`) and `tsup.config.ts` has an unused `jotai` external. Remove them to reduce install size.
- **Error surfacing** — Add optional `onError` callbacks to both providers so callers can react to connection, auth, and token-exchange failures instead of relying on `console.error`. Also add a `.catch()` to the `getAccessToken()` call in `PrivyAuthProvider` to avoid unhandled Promise rejections.
- **Observable signIn/signOut status** — `login()` and `logout()` from Privy are synchronous modal openers, so the current `isSigningIn`/`isSigningOut` state flips back immediately and the `connecting`/`disconnecting` status is never observable. Use Privy's `onSuccess`/`onError` callbacks or derive status from `ready`/`authenticated` transitions instead.
- **Logout async behavior** — `logout()` is currently fire-and-forget due to a Privy SDK issue (`await logout` hangs). Revisit when Privy fixes the upstream behavior.
- **Status `useMemo` dependencies** — The `status` memo in `WalletConnectorAdapter` includes `user?.linkedAccounts` in deps but doesn't read it; align deps with actual usage.
- **Deduplicate EVM tx parsing** — `PrivyEvmWalletAdapter.signTransaction` and `sendTransaction` share near-identical deserialization logic; extract a private helper method.
- **Tests** — Add unit tests for `PrivyEvmWalletAdapter` and `PrivySolanaWalletAdapter` with mocked Privy functions; consider integration tests for the adapter component.
- **JSDoc** — Add JSDoc to `PrivyWalletConnectorProvider` and `PrivyWalletConnectorProviderProps` for IDE hover documentation.

## Related Packages

- [`@liberfi.io/wallet-connector`](../wallet-connector/DESIGN-REVIEW.md) — Base wallet connector interfaces, providers, and hooks.
- [`@liberfi.io/types`](../types/README.md) — Shared types (`Chain`, `ChainNamespace`).