Every React Native project starts with the same question: Expo or bare workflow? The answer used to be simpler. Expo was the easy path with significant limitations, and bare React Native was the flexible path with significant setup overhead. In 2025, the landscape has changed dramatically. Expo has evolved from a limited sandbox into a comprehensive development platform that covers the vast majority of use cases, and the "bare workflow" distinction has blurred as Expo modules work in any React Native project.
We have shipped production apps with both approaches. Our perspective, informed by dozens of mobile projects, is that Expo is now the right starting point for nearly every React Native application. But "nearly every" is not "every," and understanding where Expo falls short is just as important as understanding where it excels.
What Expo Actually Is in 2025
Expo is no longer just a "managed" wrapper around React Native. It is a collection of tools that work independently or together:
Expo CLI replaces the React Native CLI for project creation, development, and building. It is faster, more reliable, and handles the sharp edges (Xcode configuration, Gradle versions, CocoaPods) that make bare React Native setup frustrating.
Expo Modules are native modules (camera, file system, notifications, secure storage, haptics, sensors, and 50+ more) that work in both Expo and bare React Native projects. They are actively maintained, well documented, and follow consistent API patterns.
EAS (Expo Application Services) handles builds, submissions, and over the air updates. EAS Build compiles your app in the cloud, so you do not need a Mac to build iOS apps. EAS Submit pushes builds directly to the App Store and Google Play. EAS Update deploys JavaScript updates to production apps without going through app store review.
Expo Router brings file based routing (similar to Next.js) to React Native, with deep linking, type safe navigation, and universal support for web, iOS, and Android from the same codebase.
Config Plugins are the key innovation that eliminated most reasons to eject from Expo. A config plugin modifies the native iOS and Android projects at build time, letting you configure native settings, add entitlements, modify the Info.plist or AndroidManifest.xml, and integrate native SDKs without manually editing native code. Most third party libraries that previously required bare React Native now ship config plugins that work with Expo.
We discuss the broader React Native ecosystem in our React Native vs Flutter and React Native vs native comparisons.
Where Expo Excels
Development speed. Starting a new project with Expo takes minutes. `npx create-expo-app` gives you a working project with TypeScript, file based routing, and a development build system. With bare React Native, setting up a comparable development environment takes hours of configuring Metro, linking native dependencies, and troubleshooting Xcode and Android Studio.
Over the air updates. EAS Update lets you push JavaScript and asset changes to production apps instantly, bypassing app store review cycles. A critical bug fix that would take 1 to 7 days through App Store review goes live in minutes. This is one of the most impactful features for production apps. We have used it to ship emergency fixes on Friday afternoons instead of waiting for Monday's review queue.
Cloud builds. EAS Build compiles your app on Expo's servers. This means your development team does not need local Xcode or Android Studio installations for routine builds. It also means reproducible builds, since the build environment is consistent regardless of what is on each developer's laptop. For distributed teams, this eliminates an entire category of "it builds on my machine" problems.
Consistent module API. Expo modules follow the same patterns for permissions, error handling, and platform differences. `expo-camera`, `expo-location`, `expo-notifications`, and others work the same way across iOS and Android. With bare React Native, you often use community modules from different authors with different API conventions, different permission handling, and different levels of maintenance.
Where Bare React Native Still Wins
The cases for bare React Native have narrowed significantly, but they still exist:
Heavy native module development. If your app's core value proposition requires custom native code, such as a custom camera pipeline, hardware integration, or a proprietary audio/video processing engine, bare React Native gives you direct access to the native projects. Config plugins can handle many native configurations, but when you need to write Swift/Kotlin code that integrates deeply with the React Native bridge, having the native projects in your repository is more straightforward.
Brownfield integration. If you are adding React Native to an existing native iOS or Android app rather than building a new app from scratch, bare React Native is the established path. Expo is designed for greenfield projects where it controls the native project structure. Integrating Expo into an existing native app is possible but not the primary use case.
Specific native SDK requirements. Some enterprise SDKs (certain banking, healthcare, or DRM libraries) require manual native project modifications that config plugins cannot express. This is increasingly rare as config plugins become more capable, but it still occurs with niche SDKs.
Build system control. Teams with existing CI/CD pipelines built around Fastlane, custom Gradle configurations, or specific Xcode build settings may find bare React Native easier to integrate. EAS Build is excellent but it is a different system, and migrating existing build infrastructure takes effort.
The EAS Build Cost Consideration
EAS Build pricing matters for team budgets. The free tier gives you 30 builds per month on slower machines. The Production plan at $99 per month provides faster builds, priority queuing, and more concurrent builds. The Enterprise plan adds custom build environments and dedicated support.
With bare React Native, builds run on your own infrastructure (or your CI/CD service like GitHub Actions or CircleCI). If you already have CI/CD set up, the incremental cost of adding mobile builds is lower than an EAS subscription. However, maintaining the build environment (keeping Xcode updated, managing Android SDK versions, handling signing certificates) has its own cost in engineering time.
For teams without existing CI/CD or without Mac hardware for iOS builds, EAS Build is worth every dollar. It eliminates days of DevOps work setting up and maintaining mobile build pipelines.
Production Readiness
Both approaches produce the same output: a native iOS and Android app compiled from the same JavaScript codebase. There is no performance difference between an Expo app and a bare React Native app. Expo does not add a runtime layer or wrapper that affects performance. The JavaScript bundle runs on the same Hermes engine in both cases.
Apps built with Expo are in production at significant scale. The Expo modules are tested against React Native's release cycle and updated promptly when new React Native versions ship. For most teams, Expo's update cadence is actually faster than what you would achieve maintaining bare React Native dependencies yourself.
We have deployed Expo apps to both app stores for clients across multiple industries, and the submission process is identical to bare React Native. Apple and Google cannot tell the difference, and there is no technical disadvantage to using Expo in production.
Our Recommendation
Start with Expo unless you have a specific, documented reason not to. The development speed advantage is real and compounds over the lifetime of a project. Over the air updates alone justify the choice for any production application. The config plugin system has eliminated the vast majority of "eject" scenarios that plagued earlier Expo versions.
Choose bare React Native when you are integrating React Native into an existing native app (brownfield), when your core product requires deep custom native code that goes beyond what config plugins can express, or when you have existing build infrastructure that you do not want to migrate.
Even in the bare React Native case, use Expo modules wherever possible. They work in bare projects and provide better maintained, more consistent native module implementations than most community alternatives.
If you are planning a mobile application and want help choosing the right approach, get in touch. We cover the full spectrum of mobile development decisions in our mobile app cost guide and through our web and mobile apps service.