Prefer video over text? Watch the full breakdown above — everything covered in this post is explained visually in the video. If you'd rather read, keep going.
Every React Native app you've ever built runs on a JavaScript engine. You write JS, something executes it, and your app comes to life. For years, that "something" was V8 — the same engine powering Chrome and Node.js. Then Meta built Hermes. And with React Native 0.84 shipping Hermes V1 as the default engine in February 2026, it's time to understand what's actually happening under the hood — and why it matters for your app's performance.
This isn't an academic comparison. This is the architecture deep dive that explains why your cold start times dropped, why your FlatList scrolls smoother, and why the engine choice is one of the most consequential decisions in your React Native stack.
What Is a JavaScript Engine, Really?
A JavaScript engine is the runtime that takes your JavaScript source code and executes it on a device. It handles parsing, compilation, memory allocation, and garbage collection. In a browser or Node.js environment, V8 does all of this. In React Native, you have a choice — and since RN 0.76, that choice has defaulted to Hermes.
The reason engine choice matters so much in mobile development is the constraint environment. Mobile devices — especially mid-range Android phones which represent the majority of your real user base — have limited RAM, slower CPUs, and no JIT warmup time to spare. The engine that wins on mobile isn't the fastest in absolute terms. It's the one that starts fastest, uses the least memory, and keeps garbage collection pauses short enough that users never feel a jank.
How V8 Works: Ignition, TurboFan, and JIT Compilation
V8 is a masterpiece of JIT (Just-In-Time) compilation engineering. When V8 receives your JavaScript, it goes through a multi-stage pipeline designed to balance startup speed with long-term execution performance.
First, V8's parser reads your source code and produces an Abstract Syntax Tree (AST). Then Ignition — V8's bytecode interpreter — compiles that AST into bytecode and starts executing it immediately. This is fast to start, but bytecode execution isn't as fast as native machine code.
Here's where V8 gets clever. While Ignition executes your code, it profiles it — tracking which functions are called frequently, what types of values they receive, and which branches are taken. This profiling data feeds into TurboFan, V8's optimising compiler. TurboFan takes "hot" functions — the ones called most often — and recompiles them into highly optimised native machine code.
This is brilliant for long-running server processes and browser applications where the JIT compiler has time to warm up. A Node.js server running for hours will continuously optimise hot paths. But a mobile app has a different problem. Users tap your app icon and expect it to be interactive in under a second. There is no warmup time. The JIT compiler is a liability at startup, not an asset.
How Hermes Works: AOT Bytecode and the Mobile-First Philosophy
Meta built Hermes with a single design principle: optimise for mobile app startup, not long-running execution. The architectural decision that flows from this is radical — don't compile JavaScript at runtime at all. Compile it at build time.
This is Ahead-Of-Time (AOT) compilation. When you build your React Native app with Hermes enabled, the Metro bundler compiles your entire JavaScript bundle into Hermes bytecode before the app is packaged. By the time a user downloads your app, there is no JavaScript source code in it. There is only pre-compiled bytecode.
When your app launches, Hermes doesn't need to parse JavaScript. It doesn't need to build an AST. It doesn't need to run an interpreter while a JIT compiler warms up in the background. It loads bytecode and executes it directly. That's why cold start times drop so dramatically with Hermes.
What Changed in Hermes V1 (React Native 0.84)
Hermes has been available since React Native 0.60, but Hermes V1 — shipped as the default engine in RN 0.84 — is a fundamentally different piece of software from what came before. The original Hermes was a solid AOT bytecode engine with intentionally limited scope. Hermes V1 is a complete rewrite with genuine ambitions to close the gap with V8 on sustained execution performance, while keeping every startup advantage of the original.
- Rewritten compiler pipeline — Better optimisation passes, smarter dead code elimination, and improved handling of modern JS patterns including optional chaining, nullish coalescing, and async/await.
- Improved JIT tier — A lightweight JIT compiler for hot functions at runtime, giving it some of V8's long-running execution advantages without sacrificing startup performance.
- Hades Garbage Collector — A concurrent, generational GC that runs most of its work on a background thread, dramatically reducing pause times during list scrolling and animations.
- New bytecode format — Better cache locality and faster decoding, contributing to further cold start improvements.
- Full ES2022+ support — Earlier Hermes versions had gaps in modern JavaScript support. Hermes V1 is fully compliant and handles the patterns modern React code relies on.
AOT vs JIT: The Fundamental Trade-off
JIT compilation (V8's approach) defers optimisation to runtime, when real profiling data is available. A JIT compiler knows which functions are hot and makes aggressive type-specialised optimisations. The downside: parsing, compilation, and profiling all consume CPU and memory during the period your user is staring at a loading screen.
AOT compilation (Hermes's approach) moves all compilation work to build time. The runtime simply executes pre-compiled bytecode — fast, predictable, no surprises. The trade-off is lower peak throughput for sustained long-running workloads compared to a fully warmed-up JIT.
Garbage Collection: Hades vs Orinoco
Garbage collection is where the performance difference between Hermes and V8 is most visible to end users. GC pauses are the invisible cause of jank — that momentary freeze when a FlatList stutters, or an animation drops frames for a split second.
V8 uses Orinoco, a generational garbage collector with incremental and concurrent marking. Sophisticated and well-tuned for general-purpose workloads — but in a React Native app that's constantly allocating objects for component renders, Orinoco's stop-the-world pauses are noticeable on constrained devices.
Hermes V1's Hades GC was designed specifically for this problem. Hades runs almost entirely on a background thread, using a concurrent marking algorithm that doesn't pause the main JS thread during collection. Stop-the-world phases in Hades are measured in microseconds rather than milliseconds.
Real Performance Numbers
The numbers below come from production migrations at Meta and Shopify — real apps, real users, real conditions. Your results will vary based on your app's architecture, native module usage, and target device profile. But these figures represent the realistic range of what Hermes V1 delivers.
The cold start improvement is largely from eliminating JS parsing and TurboModules lazy loading. The rendering improvement comes from Hades GC reducing pauses during list scrolling. The memory improvement comes from both the compact bytecode format and Hades's more efficient heap management. Your mileage will vary — always benchmark your specific app before and after.
Enabling Hermes in Your Project
If you're on React Native 0.76 or higher, Hermes is already your default engine. You don't need to do anything. If you're on an older version or need to verify:
For bare React Native (Android):
# android/gradle.properties
hermesEnabled=true
For bare React Native (iOS) in your Podfile:
use_react_native!(
:path => config[:reactNativePath],
:hermes_enabled => true
)
For Expo projects:
// app.json
{
"expo": {
"jsEngine": "hermes"
}
}
To verify Hermes is running at runtime:
const isHermes = () => !!global.HermesInternal;
console.log('Running on Hermes:', isHermes()); // true
When Would You Still Use V8?
Hermes is the right choice for the overwhelming majority of React Native apps. But there are edge cases where V8 — available via react-native-v8 — makes sense:
- Apps with heavy sustained JavaScript computation — Complex algorithms, physics simulations, or heavy data processing that runs for extended periods. V8's TurboFan JIT will outperform Hermes on peak throughput once warmed up.
- React Native for macOS or Windows — Desktop platforms where startup time advantage is less critical and sustained execution performance matters more.
- Specific library compatibility issues — Rare, and increasingly uncommon as the ecosystem has fully embraced Hermes V1.
For everything else — consumer mobile apps on iOS and Android — Hermes V1 is the answer.
Debugging With Hermes
One area where the Hermes developer experience used to lag behind V8 was debugging. Hermes V1 closes this gap significantly. The React Native DevTools (shipping with RN 0.76+) has full Hermes support including breakpoints, call stack inspection, heap snapshots, and CPU profiling. The Chrome DevTools debugger now works reliably with Hermes via the inspector protocol.
# Enable Hermes inspector for debugging
# In your app's dev menu → Debug → Open Debugger
# Or via CLI:
npx react-native start --experimental-debugger
The Bottom Line
The JavaScript engine question used to be more complicated than it needed to be. V8 was battle-tested and familiar. Hermes was fast at startup but felt limited. Hermes V1 changes that calculus permanently.
With a rewritten compiler, a lightweight JIT tier, Hades concurrent garbage collection, and full modern JavaScript support, Hermes V1 isn't just the mobile-optimised option — it's the better option for React Native, full stop. React Native 0.84 made it the default for a reason.
If you're still on a legacy React Native version without Hermes, or if you disabled it somewhere along the way, the upgrade path is straightforward and the performance gains are immediate. Your users — especially the ones on mid-range Android devices — will notice the difference.
Understand your engine. Ship faster apps.