Initialize the React client
Create a shared Carpo client and mount its provider.
Create the client once for the project and environment it represents. Pass a storageBucketId only when the app needs the combined Storage client.
'use client'
import { useState } from 'react'
import { QueryClient, QueryClientProvider } from '@tanstack/react-query'
import { CarpoProvider, createCarpoClient } from '@carpodev/carpo-sdk'
export function AppProviders({ children }: { children: React.ReactNode }) {
const [queryClient] = useState(() => new QueryClient())
const [carpo] = useState(() => createCarpoClient({
apiUrl: 'https://api.carpo.dev',
projectId: 'your-project-id',
databaseId: 'your-database-id',
storageBucketId: 'your-bucket-id',
environment: 'production',
}))
return (
<QueryClientProvider client={queryClient}>
<CarpoProvider client={carpo}>{children}</CarpoProvider>
</QueryClientProvider>
)
}CarpoProvider must be inside the TanStack QueryClientProvider. createCarpoClient returns auth, database, and functions; it adds storage when storageBucketId is configured.
Configuration
| Option | Required | Description |
|---|---|---|
apiUrl | Yes | Absolute Carpo API origin without an /api suffix or path |
projectId | Yes | Carpo project ID |
databaseId | Yes | Managed database ID used by the Database Data API and Realtime |
environment | No | production or development, default production |
storageBucketId | No | Enables client.storage and Storage hooks |
getAccessToken | No | Getter for a Project Auth JWT or user scoped API key |
getAccessTokenCacheKey | No | Stable, non secret user identity for bearer query cache isolation |
fetch | No | Custom fetch implementation for Carpo API requests |
uploadFetch | No | Custom fetch implementation for signed Storage transfers |
The client uses cookie credentials by default. Use bearer authentication only when your app intentionally uses Project Auth tokens instead of the session cookie.
What the provider manages
The provider subscribes to Better Auth's session hook and gates Database queries while the initial session loads. It scopes Database and Storage query keys by the current user. On a user change, it cancels and removes that user's cached service data. Storage queries wait for the initial session lookup, then the API evaluates the bucket policy, including any public policy.
The provider also updates the Realtime identity when session credentials change, which closes the old connection and requests a new short lived ticket.