Skip to content
Vibecoding
Vibecoding·9 min read·May 4, 2026

Cursor Rules for React Native (Expo) in 2026

Production-ready Cursor rules and AGENTS.md patterns for React Native and Expo projects. Stops the AI from inventing imports, choosing the wrong styling system, and undoing your conventions.

Written by
Kaspar Noor
Cursor Rules for React Native (Expo) in 2026
Why this matters

The default Cursor and Claude Code experience on a React Native project in 2026 is decent, but it makes predictable mistakes: wrong styling library, the wrong navigation library, useEffect for data fetching, fake imports. A small set of rules removes most of that.

This is the exact rule structure we use on Shipnative and that we recommend customers paste into their own Expo / React Native projects. It works in Cursor (.cursorrules), Claude Code (AGENTS.md or CLAUDE.md), and any agent that respects an AGENTS.md file.

If you want a fully working project that ships with these rules already in place, the React Native boilerplate chooser helps you find the right starting point.

The four mistakes AI agents make on React Native projects

Before writing rules, name the failures you are preventing. Otherwise the rules drift into vibes.

  1. The agent picks a styling system that disagrees with your codebase (NativeWind in a Unistyles project, or vice versa).
  2. The agent picks a navigation library that disagrees with your codebase (Expo Router in a React Navigation project, or vice versa).
  3. The agent uses useEffect to fetch data instead of the project's React Query / Convex pattern.
  4. The agent invents imports that do not exist, especially for hook helpers and theme tokens.

If you remove those four, the AI experience on RN projects becomes dramatically better.

The rule file structure that works in 2026

You want a single source of truth your tools agree on. The pattern that works:

  • AGENTS.md at the repo root, with the project's high-level rules and tech stack.
  • .cursorrules at the repo root that points at AGENTS.md and adds Cursor-specific shortcuts.
  • A vibe/ folder for deeper docs the agent can pull into context when needed (architecture, screen templates, error handling, monetization).

The reason for splitting is context window economics. AGENTS.md should fit comfortably in any agent's default context. The deeper docs in vibe/ get pulled in only when relevant.

We wrote about this layered pattern in layered context docs for vibecoding monorepos.

A copy-paste AGENTS.md for a Supabase + Expo project

This is the shape that reliably works for an Expo + Supabase + RevenueCat + Unistyles + React Navigation project. Adjust the libraries to match yours.

# AGENTS.md

## Setup
- `yarn install` to install dependencies
- `yarn app:start` to run the Expo dev server
- `yarn app:ios` for iOS simulator, `yarn app:android` for Android

## Tech Stack
- Expo SDK 54, React Native 0.76+
- TypeScript strict mode
- React Navigation v7 (NEVER suggest Expo Router)
- Unistyles 3.0 for styling (NEVER suggest NativeWind, Tailwind, or inline styles)
- Zustand for global state, React Query for server state
- React Hook Form + Zod for forms
- Supabase for auth and database
- RevenueCat for subscriptions
- PostHog for analytics, Sentry for errors

## Rules
- ALWAYS check apps/app/app/components/ before creating a new component
- ALWAYS use translation keys (tx props) instead of hardcoded user-facing strings
- ALWAYS use theme values (theme.colors.*, theme.spacing.*) — never hardcode colors or spacing
- NEVER use useEffect for data fetching — use React Query
- NEVER mix layout patterns — use the project's <Screen> or <Container> components
- NEVER store sensitive data (tokens, PII, billing) in MMKV — use Supabase Auth secure storage

## Directory Map
- Screens: apps/app/app/screens/
- Components: apps/app/app/components/
- Hooks (import from here): apps/app/app/hooks/index.ts
- Stores (Zustand): apps/app/app/stores/
- Theme config: apps/app/app/theme/unistyles.ts
- Translation keys: apps/app/app/i18n/en.ts (colon notation: "screenName:keyName")

## Patterns to Follow
- Auth: use `useAuth()` from `@/hooks` — works with both Supabase and Convex
- Subscriptions: use `useSubscriptionStore` for client cache, server-side verification for paid features
- Lists: use FlatList with `keyExtractor` and `getItemLayout` when item heights are known
- Navigation: type-safe via navigationTypes.ts

## Out of Scope
- Do not introduce new state management libraries (Redux, Jotai, etc.)
- Do not introduce new styling libraries
- Do not refactor unrelated files when fixing a bug

The key word in those rules is "NEVER." Soft language ("prefer", "consider") is ignored by AI agents under pressure. Hard language is followed.

A copy-paste .cursorrules

.cursorrules is loaded by Cursor automatically and complements AGENTS.md. Keep it short and pointed.

# Cursor Rules

Read AGENTS.md at the repo root for the full rules. Key reminders for editing:

- This project uses Unistyles 3.0, not NativeWind. Do not import nativewind.
- This project uses React Navigation, not Expo Router. Do not import expo-router.
- Use React Query for data fetching. Do not use useEffect for fetches.
- All user-facing text uses translation keys. Never hardcode strings in JSX.
- Theme values come from theme.colors and theme.spacing. Never hardcode hex codes or px values.
- Before creating a component, search apps/app/app/components/ for an existing one.

## Style
- Functional components with hooks. No class components.
- Named exports preferred over default exports for components.
- Co-locate styles using StyleSheet.create((theme) => ({...})) inside the component file.

## Testing
- Integration tests live in apps/app/app/__tests__/integration/
- Run tests with `yarn test`

Rules for Claude Code specifically

Claude Code (the CLI) reads CLAUDE.md files at any level of the directory tree. The pattern that works:

  • Root CLAUDE.md for project-level conventions.
  • A CLAUDE.md inside apps/app/ if your monorepo has multiple apps with different conventions.
  • A short CLAUDE.md inside vibe/ pointing at the deeper docs.

Claude Code merges these as it traverses, so you can be specific without bloating the root context.

A pattern that works for Claude Code specifically:

# CLAUDE.md

This project follows the conventions in AGENTS.md at the repo root.

## When you create a new screen
1. Use `<Screen preset="scroll" safeAreaEdges={["top", "bottom"]}>` as the wrapper.
2. Pull translation keys from `i18n/en.ts` (colon notation, e.g. `"todoScreen:emptyHeading"`).
3. Add the screen to the navigator with type-safe params.
4. If the screen does data fetching, use the React Query pattern shown in `screens/DataDemoScreen.supabase.tsx`.

## When you create a new component
1. Check `apps/app/app/components/` for an existing one first.
2. Use Unistyles `StyleSheet.create((theme) => ({ ... }))`.
3. Support dark mode via semantic theme colors (do not hardcode).
4. Add translation keys for any user-facing strings.

## When you debug a crash
- Check Sentry for the actual stack trace before guessing.
- Check `vibe/ERROR_HANDLING.md` for the boundary scope (ErrorBoundary does not catch async or pre-mount errors).

The numbered steps matter. Agents follow ordered instructions more reliably than they follow paragraphs.

Rules for the LLM agnostic case (AGENTS.md)

If you want one file that any agent respects (Cursor, Claude Code, Codex, Copilot Workspace, Aider), follow the AGENTS.md standard. Most modern agents read it.

Keep AGENTS.md to:

  1. Setup commands.
  2. Tech stack with NEVER clauses for the wrong libraries.
  3. Directory map.
  4. Three to five high-leverage rules.
  5. Out of scope clauses.

If AGENTS.md grows past ~200 lines, split deeper docs into vibe/ and link to them from AGENTS.md.

How to test that your rules actually work

After writing the rules, run this trial:

1
Open a fresh Cursor or Claude Code session
Make sure no chat history is leaking context. Close and reopen if needed.
2
Ask the agent to create a new screen with a list and a form
Use a generic prompt: 'Create a todo screen with a list and an add form.'
3
Check if it picked the right styling system
If it imports nativewind, your rules failed. If it uses StyleSheet.create((theme) => ...), they worked.
4
Check if it picked the right navigation library
If it imports expo-router or pushes a route as a string, your rules failed.
5
Check if it used your translation keys
Hardcoded strings in JSX means your rules failed.
6
Iterate the rules where it failed, not where it succeeded
Most teams over-edit successful rules and under-edit failing ones. Fix what is broken.

A good rule set should make a fresh session ship a passable screen on the first attempt. If you are correcting the same thing twice, the rule needs sharper language.

What changes in 2026 vs 2024

A few patterns are new this year and worth calling out:

  • The AGENTS.md standard is now broadly respected. You no longer need separate files for every agent.
  • Long-context models (Claude Sonnet 4.6 with 1M, Gemini 3 Pro) make it cheaper to include deeper docs in vibe/. The cost has dropped enough that I now recommend including the architecture doc by default.
  • AI tools are noticeably better at recognizing the New Architecture. You no longer need rules about Fabric specifically.
  • Subagents and parallel work mean your rules need clearer "out of scope" clauses, because agents now propose multi-file refactors more aggressively.

FAQ

Do I need both .cursorrules and AGENTS.md?

If your team only uses Cursor, no. If your team uses any other agent (Claude Code, Codex, Copilot Workspace, Aider), keep AGENTS.md as the source of truth and .cursorrules as a thin pointer.

How long should AGENTS.md be?

Under 200 lines if possible. Deeper docs go in vibe/ and get pulled in when relevant. If AGENTS.md is too long, the agent ignores the back half.

Should rules forbid specific libraries?

Yes. Soft preferences ("prefer X") get ignored. Hard "NEVER use Y" rules get followed. List the wrong libraries by name.

Will rules slow down the agent?

No. The agent reads them once per session. They are short text. They save you correction loops, which are far more expensive.

What about MCP servers and tool use?

Configure those separately. Rules govern the code style and architecture; MCP configures what the agent can do (read files, run commands, query a database). They complement each other.

A boilerplate that ships with these rules built in

Shipnative includes AGENTS.md, vibe/ docs, and a layered context structure your AI agent already understands.

Get Started Now

Further reading

Ready to ship faster?

Get lifetime access to Shipnative for a one-time payment of $99.