Platform-agnostic embedded provider core logic for Phantom Wallet SDK
npm install @phantom/embedded-provider-corePlatform-agnostic embedded provider core logic for Phantom Wallet SDK.
This package contains the core business logic for Phantom's embedded wallet provider, designed to be shared across different platforms (browser, React Native, etc.). It provides a unified interface for wallet operations while allowing platform-specific implementations through adapters.
The embedded provider core follows a platform adapter pattern:
```
┌─────────────────────────────────────┐
│ Platform SDK │
│ (browser-sdk, react-native) │
└─────────────┬───────────────────────┘
│
┌─────────────▼───────────────────────┐
│ EmbeddedProvider (Core) │
│ - Authentication flows │
│ - Session management │
│ - Wallet operations │
│ - Business logic │
└─────────────┬───────────────────────┘
│
┌─────────────▼───────────────────────┐
│ Platform Adapters │
│ - Storage (IndexedDB/AsyncStorage) │
│ - Auth (redirects/deep links) │
│ - URL params (window/linking) │
│ - Logger (debug/console) │
└─────────────────────────────────────┘
- Cross-platform compatibility: Share 90%+ of wallet logic across platforms
- Clean separation of concerns: Platform-specific code isolated in adapters
- Multiple auth flows: JWT, Google OAuth, Apple OAuth, app-wallet creation
- Session management: Persistent sessions with validation and recovery
- Retry logic: Built-in retry with exponential backoff for network operations
- Type safety: Full TypeScript support with comprehensive interfaces
`typescript
import {
EmbeddedProvider,
EmbeddedProviderConfig,
PlatformAdapter,
DebugLogger,
} from "@phantom/embedded-provider-core";
// 1. Define your configuration
const config: EmbeddedProviderConfig = {
apiBaseUrl: "https://api.phantom.app",
appId: "your-app-id",
embeddedWalletType: "user-wallet", // or 'app-wallet'
addressTypes: ["solana", "ethereum"],
authOptions: {
authUrl: "https://auth.phantom.app",
redirectUrl: "https://your-app.com/callback",
},
};
// 2. Implement platform adapters (see examples below)
const platform: PlatformAdapter = {
storage: new YourStorageAdapter(),
authProvider: new YourAuthProvider(),
urlParamsAccessor: new YourURLParamsAccessor(),
};
// 3. Implement logger
const logger: DebugLogger = new YourLogger();
// 4. Create provider instance
const provider = new EmbeddedProvider(config, platform, logger);
// 5. Use the provider
const result = await provider.connect();
console.log("Connected addresses:", result.addresses);
`
Handles persistent session storage:
`typescript
import { EmbeddedStorage, Session } from "@phantom/embedded-provider-core";
export class YourStorageAdapter implements EmbeddedStorage {
async getSession(): Promise
// Platform-specific session retrieval
// Browser: IndexedDB, React Native: AsyncStorage
}
async saveSession(session: Session): Promise
// Platform-specific session storage
}
async clearSession(): Promise
// Platform-specific session cleanup
}
}
`
Handles authentication flows:
`typescript
import { AuthProvider, AuthResult, PhantomConnectOptions } from "@phantom/embedded-provider-core";
export class YourAuthProvider implements AuthProvider {
async authenticate(options: PhantomConnectOptions): Promise
// Platform-specific authentication
// Browser: window redirects, React Native: deep links
}
resumeAuthFromRedirect?(provider: EmbeddedProviderAuthType): AuthResult | null {
// Resume authentication after redirect/deep link
}
}
`
Handles URL parameter access:
`typescript
import { URLParamsAccessor } from "@phantom/embedded-provider-core";
export class YourURLParamsAccessor implements URLParamsAccessor {
getParam(key: string): string | null {
// Platform-specific URL parameter access
// Browser: window.location.search, React Native: Linking.getInitialURL()
}
}
`
Handles logging:
`typescript
import { DebugLogger } from "@phantom/embedded-provider-core";
export class YourLogger implements DebugLogger {
info(category: string, message: string, data?: any): void {
// Platform-specific logging
}
warn(category: string, message: string, data?: any): void {
// Platform-specific warning
}
error(category: string, message: string, data?: any): void {
// Platform-specific error logging
}
log(category: string, message: string, data?: any): void {
// Platform-specific debug logging
}
}
`
For server-side authenticated users:
`typescript
const authOptions = {
provider: "jwt",
jwtToken: "your-jwt-token",
};
const result = await provider.connect(authOptions);
`
For social login flows:
`typescript
// Google OAuth
const authOptions = {
provider: "google",
};
await provider.connect(authOptions); // Will redirect/deep link
// Apple OAuth
const authOptions = {
provider: "apple",
};
await provider.connect(authOptions); // Will redirect/deep link
`
For application-controlled wallets:
`typescript
const config = {
// ... other config
embeddedWalletType: "app-wallet",
};
const result = await provider.connect(); // No auth needed
`
Sessions are automatically managed by the core provider:
`typescript
// Check connection status
if (provider.isConnected()) {
const addresses = provider.getAddresses();
console.log("Available addresses:", addresses);
}
// Sign a message
const signature = await provider.signMessage({
message: "Hello, world!",
networkId: "solana:mainnet",
});
// Sign and send transaction
const result = await provider.signAndSendTransaction({
transaction: transactionBytes,
networkId: "solana:mainnet",
});
// Disconnect
await provider.disconnect();
`
The core provider provides detailed error messages:
`typescript`
try {
await provider.connect();
} catch (error) {
if (error.message.includes("JWT")) {
// Handle JWT authentication errors
} else if (error.message.includes("Storage")) {
// Handle storage errors
} else if (error.message.includes("Network")) {
// Handle network errors
}
}
`typescript
interface EmbeddedProviderConfig {
// Required
apiBaseUrl: string; // Phantom API base URL
appId: string;
embeddedWalletType: "app-wallet" | "user-wallet";
addressTypes: [AddressType, ...AddressType[]]; // Supported blockchain addresses
// Optional
authOptions?: {
authUrl?: string; // Custom auth URL
redirectUrl?: string; // OAuth redirect URL
};
}
`
`typescript`
interface Session {
sessionId: string; // Unique session identifier
walletId: string; // Phantom wallet ID
keypair: {
// Cryptographic keypair
publicKey: string;
secretKey: string;
};
authProvider: string; // Auth method used
userInfo: Record
status: "pending" | "completed"; // Session status
createdAt: number; // Creation timestamp
lastUsed: number; // Last access timestamp
}
1. Platform Adapters: Keep platform-specific code in adapters only
2. Error Handling: Always handle authentication and network errors
3. Session Validation: The core automatically validates sessions
4. Logging: Use structured logging with categories for debugging
5. Security: Never log sensitive data like private keys
See the @phantom/browser-sdk package for a complete implementation example using this core package with browser-specific adapters.
`bashInstall dependencies
yarn install
This package is designed to be extended for new platforms. When adding support for a new platform:
1. Implement all required platform adapter interfaces
2. Add comprehensive tests for your adapters
3. Update documentation with platform-specific examples
4. Ensure error handling covers platform-specific edge cases
MIT