DEV Community

Amit chakraborty
Amit chakraborty

Posted on Originally published at amitchakraborty.dev

What Bridgeless Mode Actually Changed in React Native

For nearly a decade, the architecture of React Native was defined by a single, asynchronous bottleneck: The Bridge. During my eight years in professional software engineering, I have shipped 18 production applications across mobile, web, and desktop. I have seen the Bridge evolve from a revolutionary idea into the primary architectural constraint for high-performance apps.

When I joined Synapsis Medical Technologies as the founding engineer, I was tasked with owning the architecture from 0 to 1 across React Native, Next.js, and NestJS. We were building a HealthTech AI platform that required real-time data processing, HIPAA-aligned RAG pipelines, and deep integration with wearables. In that environment, every millisecond of latency in the UI thread mattered. We eventually scaled the engineering team from zero to 21 engineers in 13 months, and during that growth, the limitations of the "Old Architecture" became our daily reality.

The release of React Native’s New Architecture—specifically Bridgeless Mode—is not just a performance patch. It is a fundamental shift in how JavaScript interacts with native code.

The Problem: The Asynchronous Wall

In the legacy architecture, the JavaScript thread and the Native thread lived in total isolation. They communicated by serializing JSON messages and passing them over a bridge. This created three specific failure modes that I encountered repeatedly while shipping five production systems at Synapsis:

  1. Serialization Overhead: Every touch event, every frame of an animation, and every byte of data from a wearable device had to be stringified, sent across the bridge, and parsed. For our clinical AI platform, where we needed to display complex data visualizations from FHIR/HL7 streams, this overhead was non-trivial.
  2. Asynchronous Bottlenecks: Because the bridge was asynchronous, you could never guarantee that a UI update would happen in the same frame as a user interaction. This led to the "white screen" effect during rapid scrolling or jumpy headers in navigation.
  3. Initialization Latency: The Bridge had to be initialized before any native module could be used. In our iOS and Android apps, this added a fixed cost to the startup time that we could never fully optimize away.

The Technical Shift: JSI and Fabric

Bridgeless Mode is the final stage of a multi-year transition to the JavaScript Interface (JSI). JSI allows the JavaScript engine (Hermes) to hold a direct reference to C++ host objects.

In the old world, if I wanted to call a native method to trigger a HIPAA-compliant encryption routine, I had to emit an event and hope the native side picked it up. In Bridgeless Mode, the JavaScript thread calls the C++ method directly. There is no JSON serialization. There is no message queue.

This enables Fabric (the new rendering system) and TurboModules (the new native module system). Fabric treats UI operations as synchronous functions. When a user interacts with a component, the layout calculation and the view update can happen on the same thread without waiting for a bridge round-trip. This is what finally allows React Native to achieve the same "feel" as a purely native application.

Architecture and Trade-offs

Moving to Bridgeless Mode requires moving away from the RCTBridge entirely. This is a destructive change for many legacy libraries.

In the architecture I owned at Synapsis, we integrated various wearables and medical devices. Many of the third-party SDKs we relied on were built for the legacy bridge. The trade-off we face today is one of stability versus performance.

  • The Benefit: TurboModules are lazy-loaded. In the old architecture, all native modules were initialized at startup, regardless of whether they were used. Shifting to Bridgeless Mode means that if a user never opens the "Settings" page of our app, the native modules for the camera or file picker are never loaded into memory.
  • The Cost: Bridgeless Mode removes the global __fbBatchedBridge object. If your app or any of its dependencies rely on require('NativeModules') without a TurboModule backing, the app will crash.

We also have to consider the Interop Layer. Meta provided a shim that allows legacy modules to run in a Bridgeless environment, but this is a stopgap. To get the true performance gains, the modules must be rewritten as TurboModules using C++ Codegen.

A Worked Example: Synchronous State Access

Consider a scenario we faced: verifying a clinician’s credentials against a local encrypted cache before allowing an AI-driven RAG pipeline to execute.

In the Bridge architecture:

// JavaScript
NativeModules.AuthModule.isAuthorized((authorized) => {
  if (authorized) {
    runSensitivePipeline();
  }
});
Enter fullscreen mode Exit fullscreen mode

This is always asynchronous. Even if the value is already in memory on the native side, the JS thread must yield and wait for the bridge.

In Bridgeless Mode with a TurboModule:

// JavaScript
const authorized = AuthModule.isAuthorized(); // Returns boolean immediately
if (authorized) {
  runSensitivePipeline();
}
Enter fullscreen mode Exit fullscreen mode

Because the JS object is a proxy for a C++ object, the value is returned synchronously. For our clinical AI, which maintained 99.9% uptime, this reduced the complexity of our state machines significantly. We no longer had to manage "pending" states for simple boolean checks from the native side.

What it Cost to Learn

The transition to this architecture isn't free. When I led the CI/CD overhaul that cut our release cycles from 2 days to 4 hours, I learned that the complexity of the build pipeline increases with the New Architecture.

Because the New Architecture relies heavily on C++ and Codegen, your build times will initially spike. You are no longer just bundling JavaScript; you are compiling C++ bindings that bridge the gap between Hermes and the Android NDK/iOS SDK. We had to optimize our GitHub Actions runners specifically to handle the increased CPU load of these native compilations.

Furthermore, debugging becomes harder. When a bridge-based app fails, you can usually see the message in the queue. When a Bridgeless app fails, it often results in a memory access violation in C++, which provides a much less friendly stack trace for a traditional web developer.

Practical Recommendations

If you are managing a production React Native stack, do not flip the Bridgeless switch without a migration plan. Based on shipping 18+ apps, here is how I suggest approaching it:

  1. Audit Dependencies: Use the React Native New Architecture helper to see which of your libraries lack TurboModule support. If your core business logic depends on an unmaintained library that uses RCTDeviceEventEmitter heavily, Bridgeless Mode will cause friction.
  2. Codegen First: Before enabling Bridgeless Mode, ensure your custom native modules are migrated to TurboModules. Define your specs in TypeScript or Flow and let the Codegen do the heavy lifting of creating the C++ boilerplate.
  3. Memory Management: With JSI, you are sharing memory between JS and C++. Be cautious with large data blobs (like the HL7 clinical data we handled). In the bridge days, the copy-by-value nature of JSON provided a safety net. In Bridgeless Mode, you need to be more mindful of object lifetimes.
  4. Incremental Adoption: Use the Interop Layer. You don’t have to rewrite the entire app on day one. Enable the New Architecture, but keep the Interop Layer active so your legacy modules still function while you migrate the high-performance paths.

Conclusion

Bridgeless Mode is the realization of what React Native was always meant to be: a thin UI orchestration layer over high-performance native code. By removing the asynchronous serialization layer, we gain synchronous execution, lower memory overhead, and faster startup times.

For the systems I built—from AI pipelines to medical platforms—the Bridge was a constant source of "jank." Moving past it is not just an optimization; it is a requirement for the next generation of complex, data-heavy mobile applications. The transition is difficult, requiring a deeper understanding of the native layer, but the result is a platform that finally removes the "cross-platform" performance penalty.


Amit Chakraborty is a founding engineer and senior architect — React Native, AI/RAG systems and production architecture. Portfolio: www.amitchakraborty.dev · LinkedIn · GitHub. Open to senior and founding engineering roles, remote worldwide.

Top comments (0)