React Native’s Inner Life

#js #native #react

This article aims to look closer at the processes of JS code running on Android and iOS devices, the way it is translated into native code, and much more.

What is React Native?

React Native is a JavaScript library that helps develop mobile applications supported by both Android and iOS. Let’s take a look at how exactly does this library manage to run JavaScript on those systems.

Rendering the React Native Application’s UI

React Native app is rendered using native views. However, JavaScript code is not compiled to the platform’s native language; the reason for that is the fact that a phone is not able to translate a loosely typed language, which JavaScript is, into strongly typed languages (e.g., Java, Objective C).

The communication between UI written in React Native and a component tree happens by means of properties and callbacks.

However, the library helps with the native-RN communication and vice versa, in case writing some native code is required.

So what comes next? No matter which one you use, Android or iOS, they both should comprehend JavaScript code somehow.

The Bundling Processes

The native app will be developed in the programming language that a specific OS uses. Developing using React Native, one is not required to code in Objective C or Java unless everything is covered by the library.

Despite that, any React Native project must contain iOS and Android directories. These directories basically bootstrap React Native, providing “starting points” for both platforms. They contain platform-specific code, and that is where JS code is divided by platforms.

yarn android or yarn ios starts an application and typing react-native run-android or react-native run-ios respectively will start up the packager. One of the packagers is Metro. It takes all your JavaScript code and makes a single file of it: main.bundle.js. When the application is opened on a phone, the phone starts seeking the proper starting point, either the previously mentioned android or ios directory. The chosen directory launches JS Virtual Machine in a thread, where the bundled code, contained in main.bundle.js, runs. The JS code that runs within the thread communicates with the native thread using React Native.


JavaScriptCore is a framework that allows JS code to run on various devices. As for iOS and Android, development processes differ. iOS provides JavaScriptCore, while Android doesn’t. That means Android requires React Native to bundle it with the applications.

There is a thing worth mentioning to save some debugging time. JavaScriptCore runs JS code when an application runs on a device. However, for an app debug, the JS code will run using Chrome. Chrome uses the V8 engine and WebSockets in order to communicate with the native code. Thus, it is important to remember that the V8 engine and JavaScriptCore are different environments, and the bugs may only happen on the V8 engine environment, but not in the actual environment where the end-users run the application. When your app misbehaves when you are debugging it, check if the behavior remains wrong when the debugger is not attached.

React Native Bridge

The RN Bridge is written in Java/C++, and it is used to ensure communication between the native thread of the app and the JS thread. For that, it uses a custom message-passing protocol.

The JS thread determines what is to be rendered on the screen, and it will use the bridge to communicate with the main thread via serialized JSON.

But when it comes to where exactly the message is to be rendered, the shadow thread is applied. It is launched along the JS thread, and it allows computing the positions of the views. The results are passed to the main thread via the bridge.

Any action user performs on the application’s interface happens on the main thread. But tapping buttons, toggling switches, etc., is serialized and sent to the JS thread by means of the RN bridge.

How does this all affect the app’s performance?

React Native’s advantage is that it uses native views instead of running its code inside of a WebView. This provides with an ability to develop smooth and fast applications that are able to run at 60 FPS. Furthermore, in case you change the state of a component that is located somewhere high in the tree, you won’t be obliged to re-render everything dependent on the component, since the whole component tree will be re-rendered itself, and it mostly won’t be visible for the end-users.


It is not possible to say which mobile development approach is the best. However, we are capable of choosing the most fitting one. React Native covers most of the development needs, and that is the reason it is worth considering.

Previous Topic
Basic CSS Selectors
Next Topic
Basic concepts of Node.js
We Love to Hear From You
For any support, sales, careers, or security inquiry please contact us!

    * - marked fields are required.