Field Stack

The Non-Technical Founder's App Stack

Every config file, every Cursor rule, every build shortcut. The exact stack DreamLaunch uses to ship production mobile apps in under 5 weeks.

Harshil Tomar

Harshil Tomar

Founder, DreamLaunch

·

June 25, 2026

Field Stack / 2026 Edition — DreamLaunch Studio

The Non-Technical Founder's App Stack.

Every config file. Every Cursor rule. Every build shortcut. The exact system we use to get a production mobile app shipped in under 5 weeks.

10+

Apps shipped

5 wks

Zero to live

5+

Generating revenue

This isn't a framework doc. These are the exact files we open on day one of every build. Copy them. The opportunity right now — particularly on the App Store and Play Store — is real, and it's sitting unclaimed while most founders are still arguing about which tech stack to use.

Use this. Ship before someone else does.

Why right now is the window.

Both stores changed the rules in 2026. If you shipped before this, you played a different game. The non-technical founder's path just got meaningfully shorter.

App Store — what changed

Change What it means for you
Editorial featuring expanded to solo developers Apple's Today tab now runs dedicated "Indie Spotlight" slots. A well-designed app from a solo founder can get the same feature placement as a funded startup. Design quality is the only criteria — not installs.
Custom product pages (CPPs) now searchable You can create up to 35 alternate app store pages, each targeting a different search intent. Before 2026 these were ad-only. Now they rank organically.
Review response time now a ranking signal Apps that respond to reviews within 24 hrs get a visibility boost in browse and search. Automated response tooling now counts.

Play Store — what changed

Change What it means for you
LiveOps events surface in search In-app events and feature drops now appear directly in Play Store search results. Running a weekly event (even a simple "new content drop") boosts discovery without paid spend.
Engagement-weighted ranking update Google shifted ranking weight toward session frequency and retention. A small app with high daily engagement beats a large app with low return rate.
Pre-registration conversion now tracks to rank Pre-registration conversion rate is now a day-one ranking input. Building a waitlist before launch directly improves your initial rank velocity.

The window is 12–18 months.

Every meaningful platform change like this has a window before the larger studios and well-funded teams adapt and flood in. You're inside that window right now. The founders who ship in the next 90 days will have an organic head start that money can't easily replicate later.

The full stack.

These are the exact tools across every build. No variation. Consistency here is the shortcut — the stack is already configured, already documented, already debugged. You pick it up and build.

Core layer

React Native + Expo

One codebase, both platforms. Expo SDK 52 removes most of the friction that made RN frustrating two years ago. EAS Build handles store submissions.

Framework
TypeScript (strict)

Non-negotiable. Strict mode catches the class of bug that kills a launch timeline. Every file. No exceptions.

Language
NativeWind v4

Tailwind CSS for React Native. Eliminates the styling context switch between web and mobile. Same class names, same mental model.

Styling
Expo Router v3

File-based routing. Same pattern as Next.js. Deep links, shared routes, and universal links all configured from the file structure.

Navigation

Backend layer

Supabase

Postgres + auth + storage + realtime in one. The row-level security model maps directly to how mobile apps need to scope data per user.

Database + Auth
Edge Functions (Deno)

Supabase edge functions for any server-side logic. No separate backend deployment. Runs globally, cold-starts under 100ms.

Serverless

Product + revenue layer

RevenueCat

Handles all subscription logic across iOS and Android. Paywalls, trial periods, restore purchases, and webhook events for both stores — single SDK.

Monetization
PostHog

Self-hosted analytics, feature flags, and session replay. GDPR-compliant. Connects directly to the funnel events that matter: onboarding completion, paywall view, conversion.

Analytics
Expo Notifications

Push notification infrastructure built into Expo. Handles APNs and FCM registration, scheduling, and deep-link routing from notification tap.

Engagement
Sentry

Error monitoring + crash reporting. Catches the issues in production that never surfaced in testing. Source maps configured via EAS.

Monitoring

Dev tooling

Cursor (with project rules)

AI-first editor. The rules in Section 03 are what make it understand your stack without constant correction. Setup once, works across every file.

Editor
EAS Build + Submit

Cloud builds for iOS and Android. Manages certificates, provisioning profiles, and store submission. Eliminates the Xcode dependency for iOS builds.

CI/CD

Cursor rules.

Cursor is only as useful as the rules you give it. Without a project rules file, it guesses at your stack, your conventions, and your preferences — and guesses wrong often enough to slow you down. With these rules, it generates components that drop into the project without correction.

Create .cursorrules in the root of your project and paste the following. Do not trim it — every line is there because we removed something that caused a problem.

.cursorrules — copy to project root
# DreamLaunch Mobile Stack — Cursor Project Rules
# Stack: React Native + Expo SDK 52 + TypeScript (strict) + NativeWind v4 + Supabase + Expo Router v3

You are an expert React Native developer.
Always use TypeScript with strict mode. Never use 'any'.
Never use class components. Always use functional components with hooks.

## Framework rules
- Use Expo SDK 52. Never use bare React Native unless I ask.
- Use Expo Router v3 for all navigation. No React Navigation.
- File-based routing lives in /app directory.
- Shared components live in /components. Screens live in /app.
- Use NativeWind v4 for all styling. No StyleSheet.create() unless unavoidable.
- Tailwind classes only — no inline style objects for layout.

## Data + auth
- Use Supabase for all database operations.
- Import the Supabase client from @/lib/supabase.
- Always use row-level security. Never expose the service role key client-side.
- Auth state lives in a context at @/context/AuthContext.
- Use Supabase realtime subscriptions for live data — not polling.

## Component conventions
- Component files use PascalCase. Utility files use camelCase.
- Export components as named exports, not default.
- Props interfaces defined above the component, named [ComponentName]Props.
- Use React.memo() for list item components only.
- No prop drilling beyond 2 levels — use context or Zustand.

## State management
- Local UI state: useState.
- Cross-component state: Zustand stores in /store directory.
- Server state: TanStack Query (React Query) with Supabase fetcher.
- Never store auth tokens manually — use Supabase session.

## Payments
- RevenueCat SDK is the only payment handler. Import from react-native-purchases.
- Paywall component lives at @/components/Paywall.tsx.
- Always check entitlement status before showing premium features.
- Never implement custom receipt validation.

## Error handling
- Use Sentry.captureException() for all caught errors in production paths.
- User-facing errors show a toast (via Burnt library), not an alert().
- Never swallow errors silently.

## Performance
- FlashList instead of FlatList for all scrollable lists.
- Images use expo-image, not the built-in Image component.
- Use useMemo and useCallback only when profiling shows it helps.
- Avoid anonymous functions in JSX render paths for list items.

## File generation
When creating a new screen, always include:
1. Types file alongside the screen
2. A loading state
3. An error state
4. A proper KeyboardAvoidingView if the screen has inputs

Update the rules as the project grows.

Add a new rule every time Cursor gives you a wrong answer twice in a row. The rules file is a living document — treat it like internal documentation. By week 5, it will encode everything specific about your app that Cursor needs to generate production-ready code.

Core config files.

These files go into every project on day one. They take 20 minutes to set up manually. We've extracted the templates here so you copy, adjust the two or three values specific to your app, and move on.

app.config.ts — Expo config

app.config.ts
import { ExpoConfig, ConfigContext } from 'expo/config';

export default ({ config }: ConfigContext): ExpoConfig => ({
  ...config,
  name: 'Your App Name',
  slug: 'your-app-slug',
  version: '1.0.0',
  orientation: 'portrait',
  icon: './assets/icon.png',
  scheme: 'yourapp',          // deep link scheme
  userInterfaceStyle: 'automatic',  // supports dark mode
  splash: {
    image: './assets/splash.png',
    resizeMode: 'contain',
    backgroundColor: '#ffffff',
  },
  ios: {
    supportsTablet: false,
    bundleIdentifier: 'com.yourcompany.yourapp',
    buildNumber: '1',
    infoPlist: {
      NSCameraUsageDescription: 'Used for profile photos',
    },
  },
  android: {
    package: 'com.yourcompany.yourapp',
    versionCode: 1,
    adaptiveIcon: {
      foregroundImage: './assets/adaptive-icon.png',
      backgroundColor: '#ffffff',
    },
    permissions: ['CAMERA', 'READ_EXTERNAL_STORAGE'],
  },
  plugins: [
    'expo-router',
    'expo-notifications',
    ['expo-image-picker', { photosPermission: '...' }],
    ['@sentry/react-native/expo', { organization: '...', project: '...' }],
  ],
  extra: {
    supabaseUrl: process.env.EXPO_PUBLIC_SUPABASE_URL,
    supabaseAnonKey: process.env.EXPO_PUBLIC_SUPABASE_ANON_KEY,
    revenueCatApiKey: process.env.EXPO_PUBLIC_REVENUECAT_KEY,
    eas: { projectId: 'your-eas-project-id' },
  },
});

lib/supabase.ts — client setup

lib/supabase.ts
import { createClient } from '@supabase/supabase-js';
import AsyncStorage from '@react-native-async-storage/async-storage';
import { AppState } from 'react-native';

const supabaseUrl = process.env.EXPO_PUBLIC_SUPABASE_URL!;
const supabaseAnonKey = process.env.EXPO_PUBLIC_SUPABASE_ANON_KEY!;

export const supabase = createClient(supabaseUrl, supabaseAnonKey, {
  auth: {
    storage: AsyncStorage,
    autoRefreshToken: true,
    persistSession: true,
    detectSessionInUrl: false,
  },
});

// Keep session alive when app returns from background
AppState.addEventListener('change', (state) => {
  if (state === 'active') supabase.auth.startAutoRefresh();
  else supabase.auth.stopAutoRefresh();
});

eas.json — build profiles

eas.json
{
  "cli": { "version": ">= 7.0.0" },
  "build": {
    "development": {
      "developmentClient": true,
      "distribution": "internal",
      "env": { "APP_ENV": "development" }
    },
    "preview": {
      "distribution": "internal",
      "env": { "APP_ENV": "preview" },
      "ios": { "simulator": false }
    },
    "production": {
      "autoIncrement": true,
      "env": { "APP_ENV": "production" }
    }
  },
  "submit": {
    "production": {
      "ios": { "appleId": "your@email.com", "ascAppId": "YOUR_APP_ID" },
      "android": { "serviceAccountKeyPath": "./google-play-key.json", "track": "internal" }
    }
  }
}

Build shortcuts.

Every command that runs more than twice a week gets a shortcut. These are the package.json scripts we add to every project, plus the shell aliases that make the day-to-day flow fast without memorising flags.

package.json scripts

package.json → "scripts"
{
  "scripts": {
    // Dev
    "start":         "expo start",
    "ios":           "expo start --ios",
    "android":       "expo start --android",
    "dev-client":    "expo start --dev-client",

    // Type checks
    "type-check":    "tsc --noEmit",
    "lint":          "eslint . --ext .ts,.tsx --fix",

    // EAS builds
    "build:dev":     "eas build --profile development --platform all",
    "build:preview": "eas build --profile preview --platform all",
    "build:prod":    "eas build --profile production --platform all",
    "build:ios":     "eas build --profile production --platform ios",
    "build:android": "eas build --profile production --platform android",

    // Submissions
    "submit:ios":    "eas submit --platform ios",
    "submit:android":"eas submit --platform android",
    "submit:all":    "eas submit --platform all",

    // Updates (OTA)
    "update":        "eas update --branch production --message",
    "update:staging":"eas update --branch preview",

    // Database
    "db:types":      "supabase gen types typescript --linked > types/supabase.ts",
    "db:push":       "supabase db push",
    "db:reset":      "supabase db reset"
  }
}

Shell aliases (add to .zshrc / .bashrc)

~/.zshrc — paste at bottom
# Expo shortcuts
alias es="expo start"
alias ec="expo start --dev-client"
alias ecl="expo start --clear"

# EAS one-liners
alias bp="eas build --profile production --platform all"
alias bios="eas build --profile production --platform ios"
alias band="eas build --profile production --platform android"
alias sub="eas submit --platform all"

# Supabase
alias dbt="supabase gen types typescript --linked > types/supabase.ts"
alias sbstart="supabase start"
alias sbstop="supabase stop"

# OTA push (usage: ota "fix login bug")
ota() { eas update --branch production --message "$1"; }

The OTA deployment rule

EAS Update (over-the-air updates) lets you push JS changes to users without a new store submission. Use it aggressively for bug fixes, copy changes, and feature flags. The one rule: never use OTA to update native modules or permissions — those require a full build.

Change type OTA? Requires build?
Bug fix in JS logic ✓ Yes — ship in minutes No
UI / copy changes ✓ Yes No
New screen (JS only) ✓ Yes No
New native module / SDK ✗ No Yes — EAS Build
Permission changes ✗ No Yes — new store submission
Splash screen / icon change ✗ No Yes — new store submission

The 5-week map.

This is how 10+ apps went from idea to live in under 5 weeks. The sequence matters as much as the tasks. Week 4 is usually where founders want to start. Starting in Week 4 is why most founders are still building 6 months later.

Week 1
Validate the assumption, not the app

One landing page. One clear promise. Real email signups from real people in the target market. The metric is 50+ signups before writing a line of code. If you can't get 50 signups from a landing page, the app won't get downloads either. Set up Supabase project, configure EAS, scaffold the repo.

Week 2
Auth + core loop only

Supabase auth live. The one core action the app exists to do — and only that. No settings screen, no profile page, no social features. The core loop is: user arrives → user does the thing → user gets the value. Ship nothing else until the core loop is done and feels right.

Week 3
Paywall + retention hooks

RevenueCat live. Paywall built and tested on both platforms. Push notifications configured with at least one re-engagement trigger (e.g., streak break, new content). PostHog events firing on: onboarding complete, paywall view, trial start, conversion. These events are non-negotiable — you can't improve what you can't see.

Week 4
Polish + store assets

This is the only week where the output is screenshots, not code. App Store and Play Store screenshots drive 60–70% of conversion from impression to install. Custom product pages configured for the top 3 search intents. App preview video recorded. Review prompt configured to fire after the first successful core-loop completion.

Week 5
Launch + first 100 users

Submit to both stores. Target the first 100 users from the waitlist you built in Week 1 — not from paid ads. Waitlist users convert at 40–60%. Paid cold traffic converts at 2–5%. Reply to every review in the first 30 days. Run the first LiveOps event on Play Store within 7 days of launch. Watch the PostHog funnel daily.

The rule we give every founder we work with:

If a feature doesn't appear in the 5-week map, it doesn't exist yet. Defer it. Write it in a doc. Ship the 5-week version first. You can always add. You can't unship late.

Revenue setup.

The difference between an app that generates revenue and one that doesn't is usually not the product. It's whether the revenue infrastructure was built in Week 3 or Week 7. By Week 7, the founder is tired, the motivation is lower, and "we'll add payments later" has become a six-month delay.

RevenueCat setup checklist

Step Where Notes
Create products in App Store Connect App Store Connect → In-App Purchases Create at minimum: monthly sub, annual sub. Name them clearly — reviewers read these.
Create products in Play Console Play Console → Monetize → Subscriptions Mirror the same product IDs as iOS. RevenueCat maps them as one entitlement.
Add products to RevenueCat dashboard app.revenuecat.com Create one Entitlement (e.g. "premium"). Add both iOS + Android products to it.
Configure offerings RevenueCat → Offerings The "default" offering is what the SDK serves to the paywall automatically.
Test on sandbox iOS Simulator + sandbox Apple ID Sandbox purchases don't charge. Test full purchase → restore → entitlement check flow.

The paywall timing rule

Most apps show the paywall too early (on first open) or too late (never, until the user finds the locked feature). The pattern that works across our builds:

  • Show the paywall after the first successful core-loop completion — the user has just got the value, motivation to pay is highest
  • Offer a 3-day free trial — trial users convert at 2–3× the rate of direct purchases, and the churn difference is minimal
  • Price anchoring: show the annual plan first, prominently, with per-month equivalent. Monthly plan below it
  • Never gate onboarding — users who don't finish onboarding don't pay either

Revenue benchmarks to aim for by week 8

2–5%

Trial → paid conversion

40–60%

Waitlist → install rate

Day 7

First paying user target

If you're below these numbers in week 8, the issue is almost always one of three things: the paywall timing, the pricing anchor, or the trial length. Change one variable at a time. PostHog's funnel view shows exactly where users drop.

The $100K/mo path from here.

$100K/month from a subscription app is ~3,300 monthly subscribers at $30/month, or ~830 annual subscribers at $120/year. With the 2026 store changes giving organic reach to well-designed small apps, this number is reachable in 12–18 months from a cold start. It requires: strong retention (D30 > 25%), a paywall that converts, and consistent LiveOps events to maintain store visibility. None of those things require a large team. They require building the right infrastructure in the first 5 weeks.

DreamLaunch Studio — dreamlaunch.studio — All metrics from internal builds, 2024–2026.

Book a Call