Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Grammar fixes, added notes for differences in new versions #23

Merged
merged 1 commit into from Mar 3, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
23 changes: 11 additions & 12 deletions 3-react-native-internals/3.1-react-native-internals.md
Expand Up @@ -17,32 +17,31 @@ Both iOS and Android have a similar architecture with subtle differences.

If we consider the big picture, there are three parts to the RN platform:

1. **Native Code/Modules** :
1. **Native Code/Modules**:
Most of the native code in case of iOS is written in Objective C or Swift, while in the case of Android it is written in Java.
But for writing our React Native app, we would hardly ever need to write native code for iOS or Android.

2. **Javascript VM** :
2. **Javascript VM**:
The JS Virtual Machine that runs all our JavaScript code.
On iOS/Android simulators and devices React Native uses JavaScriptCore, which is the JavaScript engine that powers Safari.
JavaScriptCore is an open source JavaScript engine originally built for WebKit.
Incase of iOS, React Native uses the JavaScriptCore provided by the iOS platform.
In case of iOS, React Native uses the JavaScriptCore provided by the iOS platform.
It was first introduced in iOS 7 along with OS X Mavericks.<br/>
https://developer.apple.com/reference/javascriptcore.

In case of Android, React Native bundles the JavaScriptCore along with the application. This increases the app size. Hence the Hello World application of RN would take around 3 to 4 megabytes for Android.

In case of Chrome debugging mode, the JavaScript code runs within Chrome itself (instead of the JavaScriptCore on the device) and communicates with native code via WebSocket. Here, it will use the V8 engine. This allows us to see a lot of information on the Chrome debugging tools like network requests, console logs, etc. 😎

In case of Android, React Native bundles the JavaScriptCore along with the application. This increases the app size. Hence the Hello World application of RN would take around 3 to 4 megabytes for Android.

In case of Chrome debugging mode, the JavaScript code runs within Chrome itself (instead of the JavaScriptCore on the device) and communicates with native code via WebSocket. Here, it will use the V8 engine. This allows us to see a lot of information on the Chrome debugging tools like network requests, console logs, etc. 😎

3. **React Native Bridge** :
3. **React Native Bridge**:
React Native bridge is a C++/Java bridge which is responsible for communication between the native and Javascript thread.
A custom protocol is used for message passing.


![react native architecture diagram](/assets/images/rn-architecture.png)


In most cases, a developer would write the entire React Native application in Javascript. To run the application one of the following commands are issued via the cli - `react-native run-ios` or `react-native run-android`. At this point, React Native cli would spawn a node packager/bundler that would bundle the JS code into a single `main.bundle.js` file. The packager can be considered as being similar to webpack. Now, whenever the React Native app is launched, the first item to be loaded is the native entry point. The Native thread spawns the JS VM thread which runs the bundled JS code. The JS code has all the business logic of the application. The Native thread now sends messages via the RN Bridge to start the JS application. Now, the spawned Javascript thread starts issuing instructions to the native thread via the RN Bridge. The instructions include what views to load, what information is to be retrieved from the hardware, etc. For example, if the JS thread wants a view and text to be created it will batch the request into a single message and send it across to the Native thread to render them.
In most cases, a developer would write the entire React Native application in Javascript. To run the application one of the following commands are issued via the CLI - `react-native run-ios` or `react-native run-android`. At this point, React Native CLI would spawn a node packager/bundler that would bundle the JS code into a single `main.bundle.js` file. The packager can be considered as being similar to Webpack. Now, whenever the React Native app is launched, the first item to be loaded is the native entry point. The Native thread spawns the JS VM thread which runs the bundled JS code. The JS code has all the business logic of the application. The Native thread now sends messages via the RN Bridge to start the JS application. Now, the spawned Javascript thread starts issuing instructions to the native thread via the RN Bridge. The instructions include what views to load, what information is to be retrieved from the hardware, etc. For example, if the JS thread wants a view and text to be created it will batch the request into a single message and send it across to the Native thread to render them.

`[ [2,3,[2,'Text',{...}]] [2,3,[3,'View',{...}]] ]`

Expand All @@ -59,7 +58,7 @@ MessageQueue.spy(true);
When a React Native application is launched, it spawns up the following threading queues.

1. **Main thread** _(Native Queue)_ - This is the main thread which gets spawned as soon as the application launches.
It loads the app and starts the JS thread to execute the Javascript code. The native thread also listens to the UI events like 'press' , 'touch', etc. These events are then passed onto the JS thread via the RN Bridge. Once the Javascript loads, the JS thread sends the information on what needs to be rendered onto the screen. This information is used by a **shadow node thread** to compute the layouts. The shadow thread is basically like a mathematical engine which finally decides on how to compute the view positions. These instructions are then passed back to the main thread to render the view.
It loads the app and starts the JS thread to execute the Javascript code. The native thread also listens to the UI events like 'press', 'touch', etc. These events are then passed to the JS thread via the RN Bridge. Once the Javascript loads, the JS thread sends the information on what needs to be rendered onto the screen. This information is used by a **shadow node thread** to compute the layouts. The shadow thread is basically like a mathematical engine which finally decides on how to compute the view positions. These instructions are then passed back to the main thread to render the view.

2. **Javascript thread** _(JS Queue)_ - The Javascript Queue is the thread queue where main bundled JS thread runs.
The JS thread runs all the business logic, i.e., the code we write in React Native.
Expand Down Expand Up @@ -108,10 +107,10 @@ View Managers are basically classes extended from `ViewManager` class in Android

### Development mode 🔨

When the app is run on `DEV` mode ,the Javascript thread is spawned on the development machine. Even though the JS code is running on a more powerful machine as compared to a phone, you will soon notice that the performance is considerably lower as compared to when run in bundled mode or production mode. This is unavoidable because a lot more work is done in DEV mode at runtime to provide good warnings and error messages, such as validating propTypes and various other assertions. Furthermore, latency of communication between the device and the JS thread also comes into play.
When the app is run in `DEV` mode, the Javascript thread is spawned on the development machine. Even though the JS code is running on a more powerful machine as compared to a phone, you will soon notice that the performance is considerably lower as compared to when running in bundled mode or production mode. This is unavoidable because a lot more work is done in DEV mode at runtime to provide good warnings and error messages, such as validating propTypes and various other assertions. Furthermore, the latency of communication between the device and the JS thread also comes into play.


Link : <https://www.youtube.com/watch?v=8N4f4h6SThc> - RN android architecture
Link: <https://www.youtube.com/watch?v=8N4f4h6SThc> - RN android architecture
<span style="display: flex;align-items: center;justify-content: center; padding: 20px 0;">
<iframe width="560" height="315" src="https://www.youtube.com/embed/8N4f4h6SThc" frameborder="0" allowfullscreen></iframe>
</span>
17 changes: 8 additions & 9 deletions 4-setting-up-the-project/4.1-installing-react-native.md
@@ -1,22 +1,21 @@
# Setting up the Project

This section covers the basic boilerplate setup of a sample project that we will be using to learn. We believe that one should setup his/her project from scratch or use a minimal boilerplate instead of using a ready made feature rich boilerplate. The reason being , when a developer/team sets up its own boiler plate , they know what exactly is going into the app. A lot of boiler plates have features/libraries which the team will be unaware of and would contribute to the clutter.
This section covers the basic boilerplate setup of a sample project that we will be using to learn React Native. We believe that one should set up his/her project from scratch or use a minimal boilerplate instead of using a ready-made, feature rich boilerplate. The reason behind this is that when a developer/team sets up its own boilerplate, they know exactly what is going into the app. A lot of boilerplates have features/libraries which the team will be unaware of and it would only contribute to code clutter.

### Popular boilerplates review
### Popular boilerplates' review

- create-react-native-app `OR`
- Expo `OR`
- react-native init

React-native has a bunch of options to setup the project. `create-react-native-app`, `react-native init` and `EXPO` are among most popular ones and interestingly all three of them are mentioned in the official website of react-native. It might create a lot of confusion for someone who is starting to know which one to use.
React-native has a bunch of options to set up a project. `create-react-native-app`, `react-native init` and `Expo` are among the most popular ones and interestingly, all three of them are mentioned on the official website of react-native. It might create a lot of confusion for someone who is starting with RN to decide which one to use.

Here is short desciption for each of them:
Here is a short description of each of them:

* __create-react-native-app:__ It is similar to the `creat-react-app`. It has all the necessary tasks to run your application. All the necessary setup has been taken care and you can start hacking around react-native. This is very useful if you are starting to learn react-native and you don't want to worry about anything else. It uses Exponent's open source tools to debug the application. To run the app, all you need to do is install expo client app and scan a QR code. Although its very quick to setup, everything seems like a black-box. Due to this, it can get pretty messy when you want to change a lot of configurations. Hence we do not recommend it for a long term production application.
* __create-react-native-app:__ It is similar to `create-react-app`. It has all the necessary tasks to run your application. All the necessary setup has been taken care of and you can start hacking around react-native. This is very useful if you are starting with react-native and don't want to worry about anything else. It uses Exponent's open source tools to debug the application. To run the app, all you need to do is install the Expo Client app and scan a QR code. Although it is very quick to setup, everything seems like a black-box. Due to this, it can get pretty messy when you want to change a lot of configurations. Hence we do not recommend it for a long-term production application.

* __Expo__: It is a third party framework which provides you with a lot of cool features like: sharing your app with anyone while your are developing it, live code changes on your real device by just scanning a QR, generating IPA/APK files for you. We do not recommend using this if your app uses a lot of third party native modules or you wish to hack around the native code since you don't get access to native code out of the box. Refer to this page to know more: [Why not Expo?](https://docs.expo.io/versions/latest/introduction/why-not-expo.html) Also, It supports only **android 4.4 and up.** which can be a big turn off if you user base has a large number of ** android 4.1 - 4.3 ** users.
* __Expo__: It is a third-party framework which provides you with a lot of cool features like sharing your app with anyone while you are developing it and showing live code changes on a real device by just scanning a QR code. We do not recommend using this if your app uses a lot of third party native modules or you wish to hack around the native code since you don't get access to native code out of the box. Refer to this page to know more: [Why not Expo?](https://docs.expo.io/versions/latest/introduction/why-not-expo.html) Also, it supports only **Android 4.4 and above**, which can be a big turn off if your user base has a large number of **Android 4.1 - 4.3** users.

* __react-native init:__ This provides you with the very basic setup of the application including native `ios` and `android` folders. This allows you to change native code if required. You would use native android/ios simulators or devices to run your application.You have 2 separate files which defines entry points for android and ios. You can run the dev version of the application by `react-native run-ios` \(It will open the ios emulator and run your app on it\). Here we will need to setup everything from scratch. But on the contrary we get full access to native code and have control over almost everything that is going on with our application. Another factor is, it is easier to upgrade `react-native` and other core libraries using this boilerplate as compared to others. Hence any critical updates can be integrated much easily. **Thus, we recommend this boilerplate for any long term production application**.
* __react-native init:__ This provides you with a very basic setup of the application including native `ios` and `android` folders. This allows you to change the native code if required. You would use native Android/iOS simulators or devices to run your application. You can run the dev version of the application with `react-native run-ios` \(it will open the iOS simulator and run your app on it\). Here we will need to setup everything from scratch. But on the contrary, we get full access to native code and have control over almost everything that is going on in our application. Also, it is easier to upgrade `react-native` and other core libraries using this boilerplate as compared to others. Hence any critical updates can be integrated much more easily. **Thus, we recommend this boilerplate for any long term production application**.


Setup instructions for **react-native init** can be found at https://facebook.github.io/react-native/docs/getting-started.html. Open up the page in a browser and select the second tab, **Building Projects with Native Code** and follow the instructions.
Setup instructions for **react-native init** can be found at https://facebook.github.io/react-native/docs/getting-started.html. You can find them at the **Building Projects with Native Code** section.
20 changes: 11 additions & 9 deletions 5-project-structure-and-start-building-some-app/5.0-intro.md
@@ -1,11 +1,11 @@
# Project structure

We will be creating a Note Taking App in React Native.Lets call it `NoteTaker`. By the end of this book we will be able to build and deploy the NoteTaker to the Android play store and the Apple app store for users to download.
We will begin with the standard react native boiler plate and as we progress through the concepts we will keep updating the app. Also, at the end of the book we will also show how to extend our app originally written in Android and IOS to any other platforms, for example: Web (because we just love web). So, Lets begin.
We will be creating a note-taking App in React Native. Let's call it `NoteTaker`. By the end of this book, we will be able to build and deploy the NoteTaker to the Android Play Store and the Apple App Store for users to download.
We will begin with the standard React Native boilerplate and as we progress through the concepts we will keep updating it. Also, at the end of the book, we will show how to extend our app originally written in Android and iOS to any other platforms, for example, web (because we just love web). So, let us begin.

### Boilerplate
To create a new project run `react-native init <project-name>`. Example: `react-native init notetaker`.
We will use this project as our base in this book.
We will use this as our base project in this book.
Once the project setup is complete you should have a project structure similar to this.
```
.
Expand All @@ -29,19 +29,19 @@ Once the project setup is complete you should have a project structure similar t
```

### Run the app
Firsty, lets run the project to see how it looks.
First, let's run the project to see how it looks.

Type the command

`react-native run-ios` - for running the app on iOS simulator

or

`react-native run-android` - for running the app on a connected android phone /emulator.
`react-native run-android` - for running the app on a connected Android phone/emulator.

Note that for `react-native run-android` to work, you should have an open android emulator or an android device with USB Debugging enabled connected to your laptop via a USB cable.
Note that for `react-native run-android` to work, you should have an open Android emulator or an Android device with USB Debugging enabled connected to your system via a USB cable.

If all goes well you should see the following screen on iOS or android emulator.
If all goes well you should see the following screen on your iOS or Android emulator.

<br>
<div style="text-align:center">
Expand All @@ -51,9 +51,11 @@ If all goes well you should see the following screen on iOS or android emulator.
<br>

If you noticed there are two entry point files `index.ios.js` and `index.android.js`.
Hence, when we run the command `react-native run-ios` the file `index.ios.js` serves as our entry point.
Hence, when we run the command `react-native run-ios`, the file `index.ios.js` serves as our entry point.

Under the hood, when we run the command `react-native run-ios`, first the iOS native project inside `ios` directory is compiled. Along with the native project react-native packager kicks in on another terminal window and runs on port `8081` by default. The packager is responsible for compilation of javascript code to a js bundle file. When the native project is successfully launched on the simulator, it asks the packager for the bundle file to load. Then all the instructions inside the js code is run to successfully launch the app.
_**Note: The above is applicable only to React Native 0.49 and below. Later versions have only one entry point `index.js`**_

Under the hood, when we run the command `react-native run-ios`, the iOS native project inside `ios` directory starts compiling. Along with the native project, react-native packager kicks in on another terminal window and runs on port `8081` by default. The packager is responsible for the compilation of JavaScript code to a js bundle file. When the native project is successfully launched on the simulator, it asks the packager for the bundle file to load. Then all the instructions inside the js code are run to successfully launch the app.

{% exposnack %}
@master-atul/snack_5_0_intro_example
Expand Down