Skip to Content
Tech stack

Tech stack

NativeExpress uses Expo and React Native for the app, Supabase for the backend, and Uniwind for styling.

Expo

Expo is a framework and platform for universal React applications. We use it to build and deploy the app on iOS and Android from one codebase.

NativeExpress runs on Expo SDK 57, React Native 0.86 and React 19.2.

Uniwind & Tailwind CSS v4

Uniwind brings Tailwind CSS v4 to React Native. Core components such as View, Text and Pressable accept a className prop. Metro compiles the stylesheet used by the app.

The styling configuration is split across these files:

  • Fonts and breakpoints. src/global.css defines the font tokens and the tablet: breakpoint in its @theme block.
  • Colors and themes. src/theme/themes/<name>.css defines light and dark color tokens in @variant blocks. It is generated from a seed in src/theme/seeds/ by yarn theme:generate, never edited by hand. src/global.css imports the active theme and APP_THEME in src/theme/index.ts names it; setAppTheme() in the same file changes the active mode. See Design.
  • Metro configuration. metro.config.js uses withUniwindConfig with ./src/global.css, on top of Sentry’s Metro wrapper when @sentry/react-native is installed and Expo’s default config otherwise. Generated TypeScript declarations are written to uniwind-types.d.ts.

Non-style colour props (a component’s color, tintColor, placeholderTextColor) are not part of style and cannot take a text-* class. Use the matching {prop}ClassName prop with an accent- class instead: <ActivityIndicator colorClassName="accent-foreground" />.

HeroUI Native

HeroUI Native provides Button, BottomSheet, Spinner and form controls. Import them from heroui-native.

Its components use the theme’s CSS variables, so they pick up your colors automatically. Use a component’s variant prop for its built-in appearance options.

Routing and app state

Expo Router maps files under src/app/ to screens. Protected route groups handle signed-in and signed-out navigation. React Query manages server data, while React Hook Form and Zod handle forms and validation.

See Project structure for the directories and Authentication for the session flow.

Supabase

Supabase provides four backend services:

  • Authentication: Supabase Auth handles sign-in, sessions and the Google and Apple OAuth flows.
  • Database: Supabase Postgres is our primary database.
  • Storage: Supabase Storage holds avatars and the private chat-media bucket used by chat attachments, generated images and scans.
  • Edge Functions: The AI features (chat, generate, identify) and delete-account run as Supabase Edge Functions. See Edge Functions.

AI

  • Vercel AI SDK (ai + @ai-sdk/react): powers streaming chat on the client and streamText / generateText / generateObject inside the edge functions.
  • OpenRouter: the provider used by the AI functions. Set one server-side API key and configure model IDs in supabase/functions/_utils/ai.config.json. See Models for model capabilities and deployment.

See AI & Chat.

Additional tools

Monitoring

Sentry reports errors and crashes. See Monitoring.

Analytics

PostHog captures product events. See Analytics.

Payments

  • RevenueCat: For managing in-app purchases and subscriptions.
  • Superwall: Optional paywall layer that sits on top of RevenueCat. See Superwall.

Push notifications

OneSignal is our push notification service. It covers iOS and Android from one dashboard, where you can compose, schedule and segment campaigns without shipping an app update. See Push Notifications.

Last updated on