| name | rn-scaffold-expo |
| description | Scaffold and wire up a new Expo (managed) React Native project using curated menus per concern. The agent presents 2-5 vetted alternatives for each of navigation, state, server data, styling, storage, forms, lists, animations, auth, and observability — and implements whichever the user picks. Apply when creating a new project, adding a core library, restructuring folders, or wiring up an unmet concern in an existing project. |
| metadata | {"owner":"rn-builder","status":"stable"} |
rn-scaffold-expo
Purpose
Source of truth for standing up a new Expo project (or extending an existing one) using curated menus. Each per-concern reference file lists the vetted alternatives with full coverage — the agent reads the file, presents the menu via AskUserQuestion, then implements the picked option.
When to Apply
Use this skill when the task is:
- Creating a new Expo project from scratch
- Adding a vetted-stack library to a project that doesn't have one yet
- Auditing or restructuring folder architecture
- Wiring up a previously-unimplemented concern
Do not use this skill when the task is:
- A performance issue → read
~/.claude/skills/react-native-best-practices/SKILL.md
- A test → read
../rn-testing/SKILL.md
- A build, sign, or store submit → read
../rn-release-eas/SKILL.md
- A native module → read
../rn-native-modules/SKILL.md
- Brownfield embedding into an existing native app → read the brownfield migration skill
Skill Format
Each per-concern reference file is structured as a menu document:
- Overview — what this concern covers and why the choice matters
- Menu — table of vetted options with one-line trade-offs
- Decision Flow — how to pick (criteria, not opinions)
- Per-option deep dives — for each option in the menu:
- Quick Pattern (install + minimum-viable wiring)
- When to pick / When not to pick
- Deep Dive
- Common Pitfalls
- Recommended marker — one option is marked Recommended as the default when the user has no preference, but the agent always asks unless the project already has a pick installed.
Problem → Reference
Menu Summary
The full menus live in each reference file. This table is a navigation aid only.
| Concern | Options (recommended in bold) |
|---|
| Navigation | Expo Router, React Navigation |
| State (client) | Zustand, Jotai, Redux Toolkit, Legend State |
| Server data | TanStack Query v5, SWR, Apollo Client, RTK Query |
| Styling | NativeWind v4, Unistyles 3, Tamagui, StyleSheet, Restyle |
| Storage (general) | MMKV, expo-sqlite + Drizzle, WatermelonDB, Op-SQLite |
| Storage (secrets) | expo-secure-store (fixed, no menu) |
| Forms | React Hook Form + Zod, Formik + Yup, TanStack Form |
| Lists | FlashList v2, FlatList, LegendList |
| Animations | Reanimated 4 + Gesture Handler, LayoutAnimation, Lottie |
| Auth | Clerk Expo, Supabase Auth, Auth0, Better Auth, Firebase Auth |
| Observability | Sentry + PostHog, Crashlytics + Firebase Analytics, Bugsnag + Mixpanel, LogRocket |
"Recommended" means: when the user has no preference and asks the agent to choose, this is the pick. The agent still surfaces the menu — it does not silently default.
Verification After Scaffold
After any scaffold or stack change, the agent must:
npx tsc --noEmit passes
npx expo start --clear boots
- iOS simulator or Android emulator renders the home route
- Lint passes (
npx expo lint or project equivalent)
- A
STACK.md or PR description records what was picked from each menu
If any of the five fails, the scaffold is not done.
Detecting Existing Picks
Before asking the user, the agent reads package.json to detect what's already installed. Matching dependencies short-circuit the menu — the agent uses what's there.
cat package.json | grep -E '"(zustand|jotai|@reduxjs/toolkit|@tanstack/react-query|swr|@apollo/client|nativewind|react-native-unistyles|tamagui|react-native-mmkv|react-native-nitro-modules|@nozbe/watermelondb|expo-sqlite|drizzle-orm|react-hook-form|formik|@tanstack/react-form|@shopify/flash-list|react-native-reanimated|react-native-worklets|@clerk/expo|@supabase/supabase-js|@sentry/react-native|posthog-react-native)":'
This prevents re-prompting on every feature task in an existing project.