---
name: Privy
description: Use when building authentication systems, creating embedded wallets, managing wallet controls and policies, handling user onboarding, integrating wallet transactions, or managing multi-chain wallet infrastructure. Agents should reach for this skill when implementing user authentication, wallet creation, transaction signing, policy enforcement, or wallet access controls.
metadata:
    mintlify-proj: privy
    version: "1.0"
---

# Privy Skill Reference

## Product summary

Privy is an authentication and wallet infrastructure platform that enables developers to onboard users with wallets, create self-custodial embedded wallets, and securely sign transactions. It provides three interconnected layers: **authentication** (email, social, passkeys, wallets), **wallets** (embedded or external, cross-chain), and **controls** (owners, signers, policies).

**Key files and concepts:**
- App ID and App Secret: Found in Privy Dashboard > App Settings > Basics
- User object: Unified identity with linked accounts (email, phone, wallets, socials)
- Wallet object: Embedded or external wallet with owner, signers, and policies
- Authorization keys: P-256 keypairs for server-side wallet control
- Policies: Rules that constrain wallet actions (transaction limits, recipient allowlists, contract restrictions)

**Primary SDKs:** React (`@privy-io/react-auth`), React Native (`@privy-io/expo`), Node.js (`@privy-io/node`), Swift, Android, Java, Go, Rust, Python, Flutter, Unity

**REST API:** `https://api.privy.io/v1/` with Basic Auth (app ID:app secret) and `privy-app-id` header

**Primary docs:** https://docs.privy.io

---

## When to use

Reach for this skill when:

- **Building authentication flows**: Implementing email, SMS, social login, passkeys, wallet-based auth, or integrating with existing JWT/OIDC providers
- **Creating wallets**: Provisioning embedded wallets for users (Ethereum, Solana, 50+ chains), importing wallets, or managing wallet fleets
- **Controlling wallet access**: Setting up owners, signers, policies, key quorums, or multi-sig approvals
- **Signing transactions**: Requesting user signatures, server-side signing, or batch operations
- **Managing users**: Creating users, linking accounts, custom metadata, allowlists/denylists
- **Handling wallet events**: Setting up webhooks for transaction status, deposits, withdrawals, user events
- **Implementing security**: Configuring MFA, authorization signatures, policy enforcement, secure enclaves
- **Multi-chain operations**: Supporting Ethereum, Solana, Bitcoin, Tron, Sui, and other chains simultaneously

---

## Quick reference

### SDK initialization (React)

```tsx
import {PrivyProvider} from '@privy-io/react-auth';

<PrivyProvider
  appId="your-privy-app-id"
  clientId="your-app-client-id"
  config={{
    embeddedWallets: {
      ethereum: {createOnLogin: 'users-without-wallets'}
    }
  }}
>
  {children}
</PrivyProvider>
```

### REST API authentication

```bash
curl -u "app-id:app-secret" \
  -H "privy-app-id: app-id" \
  -H "Content-Type: application/json" \
  https://api.privy.io/v1/wallets
```

### Core API endpoints

| Task | Endpoint | Method |
|------|----------|--------|
| Create wallet | `/v1/wallets` | POST |
| Get wallet | `/v1/wallets/{id}` | GET |
| Sign transaction | `/v1/wallets/{id}/ethereum/eth_sendTransaction` | POST |
| Create user | `/v1/users` | POST |
| Get user | `/v1/users/{id}` | GET |
| Create policy | `/v1/policies` | POST |
| Create authorization key | Dashboard or SDK | - |

### Wallet ownership models

| Model | Owner | Use case |
|-------|-------|----------|
| User-owned | User ID | Self-custodial consumer wallets |
| User + server | User ID + signer | Automated trading, limit orders |
| App-owned | Authorization key | Treasury, trading bots, agents |
| Custodial | Licensed custodian | FBO banking-like models |

### Login methods

Email, SMS, WhatsApp, Google, Apple, Discord, Twitter, GitHub, LinkedIn, Spotify, Instagram, TikTok, Passkeys, Wallets (SIWE/SIWS), Farcaster, Telegram, Custom OAuth

### Policy field sources (Ethereum)

| Source | Fields | Example |
|--------|--------|---------|
| `ethereum_transaction` | `to`, `value`, `chain_id` | Restrict recipient or amount |
| `ethereum_calldata` | `function_name`, `function_name.param` | Allow specific contract calls |
| `ethereum_typed_data_domain` | `chainId`, `verifyingContract` | Restrict signing domain |
| `system` | `current_unix_timestamp` | Time-based restrictions |

---

## Decision guidance

### When to use embedded vs external wallets

| Scenario | Embedded | External |
|----------|----------|----------|
| New users, no crypto experience | ✓ | - |
| Users have existing wallets | - | ✓ |
| Need key export/self-custody | ✓ | ✓ |
| Seamless UX, no wallet client | ✓ | - |
| Power users, familiar with MetaMask | - | ✓ |
| Cross-chain support needed | ✓ | ✓ |

### When to use Privy auth vs custom auth

| Scenario | Privy auth | Custom auth |
|----------|-----------|------------|
| No existing auth system | ✓ | - |
| Multiple login methods needed | ✓ | - |
| Already have JWT/OIDC provider | - | ✓ |
| Want full control over auth | - | ✓ |
| Need MFA, passkeys, socials | ✓ | - |

### When to use policies vs signers

| Scenario | Policies | Signers |
|----------|----------|---------|
| Restrict transaction amounts | ✓ | - |
| Restrict recipient addresses | ✓ | - |
| Give scoped permissions to third-party | - | ✓ |
| Require multiple approvals | ✓ | ✓ |
| Delegate server automation | - | ✓ |
| Enforce smart contract restrictions | ✓ | - |

---

## Workflow

### 1. Set up your Privy app

1. Create app in Privy Dashboard
2. Copy App ID and App Secret from App Settings > Basics
3. Configure login methods in Authentication tab
4. Set up app clients for different environments (optional)
5. Configure webhook endpoint (optional, for events)

### 2. Initialize SDK in your application

1. Install SDK: `npm install @privy-io/react-auth` (or appropriate SDK)
2. Wrap app with `PrivyProvider` at root level
3. Pass `appId` and optional `clientId`
4. Configure wallet creation: `embeddedWallets.ethereum.createOnLogin`
5. Check `ready` flag before using Privy hooks

### 3. Implement user authentication

1. Use `usePrivy()` hook to access login/logout
2. Call `login()` to show login modal or use direct methods (`loginWithEmail`, `loginWithOAuth`)
3. Access authenticated user via `user` object
4. Store user ID for backend operations
5. Handle logout with `logout()`

### 4. Create and manage wallets

1. For automatic creation: Set `createOnLogin: 'users-without-wallets'` in config
2. For manual creation: Call `createWallet()` from `useCreateWallet` hook
3. Access wallet via `useWallets()` hook
4. Get wallet address from `wallet.address`
5. For server-side: Create authorization key, then create wallet with key as owner

### 5. Sign transactions and messages

1. Get wallet from `useWallets()` or API
2. For Ethereum: Call `signMessage()`, `signTransaction()`, or `sendTransaction()`
3. For Solana: Call `signMessage()`, `signTransaction()`, or `signAndSendTransaction()`
4. Pass transaction/message data and optional authorization context
5. Handle response or error

### 6. Set up policies and controls

1. Create policy in Dashboard or via API with rules for each RPC method
2. Define conditions (amount limits, recipient allowlists, contract restrictions)
3. Attach policy to wallet at creation or via update
4. For signers: Create authorization key, add as signer with policy override
5. Test policy enforcement with sample transactions

### 7. Monitor events with webhooks

1. Configure webhook endpoint in Dashboard > Webhooks
2. Subscribe to event types (user, wallet, transaction, intent)
3. Implement webhook handler to verify signature and process events
4. Store event data for audit trail
5. Retry failed webhook deliveries

### 8. Verify and test

1. Check user object has correct linked accounts
2. Verify wallet address matches block explorer
3. Test transaction signing with small amounts
4. Confirm policy blocks unauthorized transactions
5. Validate webhook events are received

---

## Common gotchas

- **Missing `ready` flag**: Always check `usePrivy().ready` before accessing user or wallet state. Privy initializes asynchronously.
- **Wallet not created on login**: Set `createOnLogin: 'users-without-wallets'` explicitly. Default is `'off'`.
- **Policy denies all transactions**: Policies default to `DENY`. Include an "allow all" rule or explicitly allowlist each RPC method.
- **Authorization signature errors**: Ensure you're signing the correct payload (request body + headers). Use `AuthorizationContext` in Node.js SDK to auto-sign.
- **User session keys expired**: User signing keys are time-bound. Request fresh keys via `/wallets/authenticate` before making API calls.
- **Insufficient funds error**: Check wallet balance on correct chain. For gas sponsorship, verify credits in Dashboard > Gas Sponsorship.
- **Policy violation on valid transaction**: Review policy conditions. Amounts are in smallest units (wei for ETH, lamports for SOL). Recipient must be allowlisted if policy restricts.
- **Webhook signature verification**: Always verify webhook signature using your app secret before processing. Privy signs with HMAC-SHA256.
- **Multiple wallets per user**: Set `createAdditional: true` to create additional HD wallets. Default is `false` (prevents accidental duplication).
- **External wallet not connecting**: Ensure wallet is installed and user has approved connection. Check `externalWallets` config includes desired wallet types.
- **Solana transaction policy fails**: Every instruction must pass policy. Use `solana_token_program_instruction` and `solana_system_program_instruction` field sources.
- **Idempotency key not working**: Include `idempotency_key` header on wallet creation. Same key + same request body = same response (no duplicate wallet).

---

## Verification checklist

Before submitting work with Privy:

- [ ] App ID and App Secret are stored securely (environment variables, not hardcoded)
- [ ] `PrivyProvider` wraps all components using Privy hooks
- [ ] `ready` flag is checked before accessing user/wallet state
- [ ] User authentication flow tested (login, logout, account linking)
- [ ] Wallet creation tested (automatic or manual)
- [ ] Transaction signing tested with small amounts
- [ ] Policies are correctly configured (rules for each RPC method, conditions match use case)
- [ ] Authorization signatures are properly signed (correct payload, valid keys)
- [ ] Webhook endpoint is configured and signature verification is implemented
- [ ] Error handling covers common cases (policy_violation, insufficient_funds, request_expired)
- [ ] Multi-chain support tested if applicable (Ethereum, Solana, etc.)
- [ ] User object contains expected linked accounts
- [ ] Wallet addresses match block explorer
- [ ] Gas sponsorship credits are available (if using gas sponsorship)
- [ ] Rate limits are handled (exponential backoff for 429 responses)

---

## Resources

**Comprehensive navigation:** https://docs.privy.io/llms.txt

**Critical documentation pages:**
1. [Key Concepts](https://docs.privy.io/basics/key-concepts) — Understand authentication, wallets, and controls
2. [API Reference](https://docs.privy.io/api-reference/introduction) — Complete REST API documentation with examples
3. [Policies Overview](https://docs.privy.io/controls/policies/overview) — Policy engine, rules, conditions, and field sources

---

> For additional documentation and navigation, see: https://docs.privy.io/llms.txt