integrating-convex-expo
npx skills add https://github.com/tristanmanchester/agent-skills --skill integrating-convex-expo
Agent 安装分布
Skill 文档
Integrating Convex with Expo (React Native)
Why this skill exists
Convex setup in React Native is straightforward, but small details (Expo environment variables, file locations, keeping convex dev running)
regularly cause broken builds or âit returns undefinedâ confusion. This skill standardises a reliable, end-to-end workflow.
Non-negotiables (do these every time)
- Keep
npx convex devrunning while developing. It syncs functions + generates theconvex/_generatedAPI/types. - Use Expo public env vars: the client should read
process.env.EXPO_PUBLIC_CONVEX_URL. - Create exactly one Convex client per app, and wrap the whole tree in
ConvexProvider. - React Native: set
unsavedChangesWarning: falseonConvexReactClient(the default warning is web-centric). - Donât hand-type API names: always import from
convex/_generated/apiand callapi.someFile.someExport.
First decision: what kind of Expo project is this?
- expo-router project (common with
create-expo-app):- root layout is usually
app/_layout.tsxorsrc/app/_layout.tsx
- root layout is usually
- classic App.tsx entrypoint:
- wrap
App.tsxwithConvexProvider
- wrap
When unsure, search for expo-router in package.json and look for an app/ folder.
Workflow A â Add Convex to an existing Expo app (recommended default)
A1) Install Convex
From the Expo app root:
npx expo install convex
(If you arenât using Expoâs installer, npm i convex also works.)
A2) Create a Convex dev deployment + backend folder
npx convex dev
What you should see / get:
- prompts to log in and create a project
- a new
convex/folder for backend functions .env.localcontainingEXPO_PUBLIC_CONVEX_URL=...- the command keeps running to sync changes
A3) Ensure EXPO_PUBLIC_CONVEX_URL is available in development and builds
- Dev (Expo CLI / Metro):
npx convex devwrites.env.localwithEXPO_PUBLIC_CONVEX_URL. - EAS builds: copy that value into EAS env vars.
A4) Wire up the Convex client + provider (expo-router)
Edit app/_layout.tsx or src/app/_layout.tsx:
import { ConvexProvider, ConvexReactClient } from "convex/react";
import { Stack } from "expo-router";
const convex = new ConvexReactClient(process.env.EXPO_PUBLIC_CONVEX_URL!, {
unsavedChangesWarning: false,
});
export default function RootLayout() {
return (
<ConvexProvider client={convex}>
<Stack />
</ConvexProvider>
);
}
If the project does not use expo-router
Wrap your top-level component (usually App.tsx) similarly:
import { ConvexProvider, ConvexReactClient } from "convex/react";
const convex = new ConvexReactClient(process.env.EXPO_PUBLIC_CONVEX_URL!, {
unsavedChangesWarning: false,
});
export default function App() {
return (
<ConvexProvider client={convex}>
{/* your existing navigation / UI */}
</ConvexProvider>
);
}
A5) Create a first query + show it in the app
Use the canonical âtasksâ example:
- backend:
convex/tasks.ts - seed:
sampleData.jsonl - import:
npx convex import --table tasks sampleData.jsonl - UI:
useQuery(api.tasks.get)
See: references/tasks-example.md
â
Quality gate: when the app loads, useQuery should initially be undefined (loading) and then become an array of tasks.
Workflow B â Add a new feature end-to-end (schema â function â UI)
Use this loop for each feature (it keeps you âin syncâ across app/backend/db):
-
Data model first (schema + indexes)
- define/extend tables in
convex/schema.ts - add indexes youâll query by (before you have 1000+ docs)
- see: references/schema-and-indexes.md
- define/extend tables in
-
Backend API (query/mutation/action)
- prefer query for reads, mutation for writes, action when you need Node APIs or third-party fetches that donât fit the normal runtime
- always validate args with
v.* - see: references/functions.md
-
Frontend integration
useQuery(api.file.export)useMutation(api.file.export)- consider loading/empty/error states explicitly
- see: references/frontend-patterns.md
-
Run/verify
- keep
npx convex devrunning - restart Metro if env vars changed
- run the validation script:
python scripts/validate_project.py
- keep
Workflow C â Authentication (pick one and stick to it)
Convex supports multiple approaches; the right choice depends on your appâs needs:
- Convex Auth: simplest end-to-end if youâre all-in on Convex.
- Clerk: common in Expo; Convex provides
<ConvexProviderWithClerk>for integration. - Other OIDC/JWT providers: generally work by passing JWTs and enforcing access control in functions.
See: references/auth.md
Workflow D â File uploads from Expo / React Native
Use Convex File Storage upload URLs:
- mutation generates a short-lived upload URL
- client
fetch(putUrl, { method: "POST", ... }) - store the returned
storageIdin your table
See: references/file-uploads.md
Troubleshooting (fast path)
If something breaks, do this in order:
- Is
npx convex devrunning? If not, start it. - Is
process.env.EXPO_PUBLIC_CONVEX_URLdefined at runtime?- if you added/changed
.env*, restart Metro with cache cleared.
- if you added/changed
- Does the app wrap the entire tree with
ConvexProvider? - Are you importing
apifromconvex/_generated/apiand callinguseQuery(api.x.y)? - Run:
python scripts/validate_project.py
More cases + fixes: references/troubleshooting.md
Scripts included
scripts/validate_project.pyâ checks package.json, env vars, Convex folder, and provider wiring.scripts/scaffold_tasks_example.pyâ generates the âtasksâ example files (dry-run by default).
References (load only when needed)
- references/eas-env.md â
.env.localvs EAS env vars, Expo gotchas - references/tasks-example.md â seed + query + UI in Expo
- references/schema-and-indexes.md â schemas, validators, indexes, query perf
- references/functions.md â queries, mutations, actions patterns
- references/frontend-patterns.md â hooks patterns, loading/error handling, navigation
- references/auth.md â Convex Auth vs Clerk vs others, access control patterns
- references/file-uploads.md â RN/Expo file URIs â Blob â Convex storage
- references/troubleshooting.md â common issues and exact fixes
- references/sources.md â upstream docs used to build this skill