Modern Expo starter for multi-platform apps. It ships with Expo Router, TypeScript, Biome, NativeWind, Tailwind CSS, shadcn-inspired React Native primitives, Supabase utilities, Zustand, React Query, and English/Chinese i18n.
- Expo SDK 56 with Expo Router
- React Native 0.85 and React 19
- TypeScript in strict mode
- Biome for linting and formatting
- NativeWind v5 preview with Tailwind CSS 4
- React Native Reusables /
@rn-primitivesUI primitives - i18n with
i18next,react-i18next, andexpo-localization - Supabase client wrapper with AsyncStorage session persistence
- Zustand, React Query, React Hook Form, Zod, and Lucide icons
- Node.js 22+ recommended
- npm 11+ recommended
- Android Studio / Xcode for local development builds
npm installCreate .env from .env.example and fill in your Supabase credentials:
cp .env.example .envEXPO_PUBLIC_SUPABASE_URL=your-project-url
EXPO_PUBLIC_SUPABASE_ANON_KEY=your-anon-keyutils/supabase.ts throws during import when either value is missing. If your app
does not use Supabase, remove utils/supabase.ts and the Supabase-related
dependencies.
npm start # Expo CLI for a development build
npm run android # expo run:android
npm run ios # expo run:ios
npm run web # expo start --webRun npm run android or npm run ios once to install a development build, then
use npm start for the Metro server. Use npm run start:go only when you want
to open the project in Expo Go.
Use npm run startc after changing Metro, NativeWind, or Tailwind configuration
so Expo starts with a clean cache.
npm run start- start Expo for a development buildnpm run startc- start Expo for a development build with cache resetnpm run start:go- start Expo for Expo Gonpm run android- build and run Android locallynpm run ios- build and run iOS locallynpm run web- start Expo webnpm run static- export and serve the static web buildnpm run lint- run Biome checksnpm run format/npm run fix- apply Biome fixesnpm run typecheck- run TypeScript checksnpm run doctor- run Expo Doctornpm run align- runexpo install --fixnpm run prebuild- generate native projectsnpm run apk- local EAS Android production buildnpm run ipa- local EAS iOS production buildnpm run shadcn- add React Native Reusables componentsnpm run taze- update dependencies
app/- Expo Router routes and root layoutcomponents/- shared components and UI primitivescomponents/theme.tsx- status bar, system background, and web dark class synccomponents/ui/- shadcn-inspired React Native componentslib/utils.ts-cnhelper usingclsxandtailwind-mergelocales/- English and Chinese translation catalogsstore/- Zustand store setuputils/supabase.ts- Supabase clientglobal.css- Tailwind CSS 4 imports, NativeWind theme import, sources, and theme tokenspostcss.config.mjs- Tailwind CSS 4 PostCSS pluginmetro.config.js- Expo Metro wrapped by NativeWind
NativeWind is configured for Tailwind CSS 4. Theme tokens live in global.css
inside @theme, with light and dark CSS variables below it.
Important files:
global.csspostcss.config.mjsmetro.config.jsbabel.config.jsnativewind-env.d.ts
The app imports global.css once in app/_layout.tsx.
Language detection reads the device locale via expo-localization and normalizes
to en or zh.
To add a language:
- Add
locales/<lang>.json. - Register it in
locales/index.ts. - Keep translation keys mirrored across locale files.
Supabase is included as a starter utility, not a required architecture choice. The client expects:
EXPO_PUBLIC_SUPABASE_URLEXPO_PUBLIC_SUPABASE_ANON_KEY
Auth sessions persist in AsyncStorage and auto-refresh by default.
eas.json includes development, preview, and production profiles. Before
publishing a real app, update:
expo.nameexpo.slugexpo.schemeandroid.package- iOS
bundleIdentifierif you add iOS native config
This template currently includes an Android native project. If you want a pure
Expo CNG template, remove generated native folders and let each app run
npm run prebuild when needed.
Run these before shipping template changes:
npm run lint
npm run typecheck
npm run doctor- If NativeWind styles do not update, restart with
npm run startc. - If Expo reports dependency mismatches, run
npm run align. - If Supabase env values are missing, create
.envfrom.env.example. - If a new project uses different app identifiers, update
app.jsonbefore native builds.