useWallet
The useWallet hook generates and manages facilitator wallets from user authentication entropy. These wallets are used for private transaction routing in Silent Swap.
Import
import { useWallet, useAuth } from '@silentswap/react';
import { useAccount, useWalletClient } from 'wagmi';Basic Usage
import { useWallet, useAuth, useSilentClient } from '@silentswap/react';
import { useAccount, useWalletClient } from 'wagmi';
import { ENVIRONMENT } from '@silentswap/sdk';
function WalletComponent() {
const { address } = useAccount();
const { data: walletClient } = useWalletClient();
const { connector } = useAccount();
const { client } = useSilentClient({
config: {
environment: ENVIRONMENT.MAINNET,
},
});
const { auth } = useAuth({
client,
address: address!,
walletClient: walletClient as any,
autoAuthenticate: true,
});
const {
wallet,
generateWallet,
isLoading,
error,
} = useWallet({
address: address!,
auth: auth || undefined,
walletClient: walletClient as any,
connector,
});
// Auto-generate wallet when authenticated
useEffect(() => {
if (auth && walletClient && !wallet && !isLoading) {
generateWallet();
}
}, [auth, walletClient, wallet, isLoading, generateWallet]);
if (isLoading) {
return <div>Generating wallet...</div>;
}
if (error) {
return <div>Error: {error.message}</div>;
}
if (wallet) {
return (
<div>
<p>Wallet ready with {wallet.accounts.length} accounts</p>
</div>
);
}
return <div>Waiting for authentication...</div>;
}API Reference
Options
interface useWalletOptions {
/** The user's EVM address */
address: `0x${string}`;
/** Authentication response from SIWE */
auth?: AuthResponse;
/** Wallet client for signing operations */
walletClient?: WalletClient;
/** Wagmi connector */
connector?: Connector;
/** Whether to generate all deposit accounts or just the latest */
allDeposits?: boolean;
}Return Value
interface useWalletReturn {
// State
wallet: SilentSwapWallet | null;
isLoading: boolean;
error: Error | null;
// Methods
generateWallet: () => Promise<void>;
getCachedWallet: () => SilentSwapWallet | null;
clearWallet: () => void;
refreshWallet: () => Promise<void>;
}
interface SilentSwapWallet {
entropy: Uint8Array;
accounts: FacilitatorAccount[];
}
interface FacilitatorAccount {
group: () => Promise<HdFacilitatorGroup>;
nonce: number;
}Wallet Generation Flow
- Check Cache - Look for cached wallet in sessionStorage
- Query Deposit Count - Get current deposit count from blockchain
- Generate Entropy - Sign EIP-712 document to generate entropy
- Create Accounts - Generate facilitator accounts based on deposit count
- Cache Wallet - Store wallet data in sessionStorage
Generating Entropy
The wallet entropy is generated by signing an EIP-712 document:
// This happens automatically in generateWallet()
// The hook:
// 1. Ensures we're on Ethereum mainnet
// 2. Creates EIP-712 document for wallet generation
// 3. Signs the document with walletClient
// 4. Uses signature bytes as entropyAccount Generation
Accounts are generated based on deposit count:
// If allDeposits is false (default):
// - Only generates accounts for current deposit count
// - More efficient for most use cases
// If allDeposits is true:
// - Generates accounts for all deposits (0 to depositCount)
// - Useful for historical deposit accessUsing Facilitator Groups
Once the wallet is generated, you can access facilitator groups:
const { wallet } = useWallet({
address: address!,
auth,
walletClient,
});
// Get facilitator group for first account
const facilitatorGroup = await wallet?.accounts[0]?.group();
// Export public keys for quote
const viewer = await facilitatorGroup.viewer();
const { publicKeyBytes: viewerPk } = viewer.exportPublicKey(
'*',
FacilitatorKeyType.SECP256K1
);
const groupPks = await facilitatorGroup.exportPublicKeys(
outputs.length,
PublicKeyArgGroups.GENERIC
);Caching
The wallet is cached in sessionStorage:
- Key: Based on user address
- TTL: Session-based (cleared on browser close)
- Format: Base93-encoded entropy + account nonces
Manual Wallet Management
const {
generateWallet,
getCachedWallet,
clearWallet,
refreshWallet,
} = useWallet({
address: address!,
auth,
walletClient,
});
// Get cached wallet without generating
const cached = getCachedWallet();
// Clear wallet cache
clearWallet();
// Refresh wallet (clear + regenerate)
await refreshWallet();Error Handling
const { wallet, generateWallet, error } = useWallet({
address: address!,
auth,
walletClient,
});
const handleGenerate = async () => {
try {
await generateWallet();
} catch (err) {
console.error('Wallet generation failed:', err);
// Handle error (show user message, retry, etc.)
}
};
// Display errors
{error && (
<div className="error">
Wallet generation failed: {error.message}
</div>
)}Chain Requirements
Wallet generation requires being on Ethereum mainnet:
// The hook automatically switches to Ethereum mainnet
// if needed before generating entropy
// This is required by the protocolBest Practices
- Auto-Generate - Generate wallet automatically after authentication
- Cache Management - Let the hook handle caching automatically
- Error Recovery - Provide retry mechanisms for failed generation
- Loading States - Show loading indicators during generation
- Account Selection - Use the appropriate account nonce for your use case
Next Steps
- Learn about quote and execution
- Understand order management
- See complete example