일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | 4 | 5 | 6 | 7 |
8 | 9 | 10 | 11 | 12 | 13 | 14 |
15 | 16 | 17 | 18 | 19 | 20 | 21 |
22 | 23 | 24 | 25 | 26 | 27 | 28 |
29 | 30 | 31 |
- Basic
- 비동기
- 기본
- mock service worker
- Babel
- amplify
- Cache
- Critical Rendering Path
- MSW
- CSS-in-JS
- next.js
- react-query
- 개발자
- link
- styled-component
- 쓰레드
- vanilla-extract
- 리액트
- 기초
- React
- thread
- 아키텍처
- react server component
- next hydration
- 리액트쿼리
- 컴포넌트
- mockoon
- 목킹
- 최적화
- async
- 동기
- JavaScript
- 캐쉬
- react-native
- 리액트네이티브
- Concurrent Mode
- SWC
- front-end mocking
- sprinkles
- 자바스크립트
- Today
- Total
Don’t worry about failures
React native 구동 방식 ( 구 ) 본문
어떠한 라이브러리 혹은 프레임워크를 제대로 사용하기 위해 해당 라이브러리가 어떻게 작동하는지에 대해 알아보는 것이 중요하다고 생각한다. 이에 react native가 어떻게 구동하고 있는지 파악하기 위해 이 글을 써내려가겠다.
리액트 네이티브의 구 아키텍처와 새로운 아키텍처에 대해 살펴볼것이다.
구 아키텍처
우선, 위의 사진으로 간단한 흐름을 파악해보자
1. 유저가 버튼을 클릭
2. 클릭에 의한 이벤트는 native threads에서 브릿지를 통해 js thread를 실행.
3. 해당 결과 값을 브릿지를 통해 다시 native threads에 전달하여 유저에게 해당 이벤트에 맞게 화면을 보여준다.
엄청 간단하게 흐름을 보면 이렇다.
이제 자세하게 파악해보자 ( 설명 후 위의 간단한 단계를 디테일하게 풀어서 다시 단계를 적어볼 예정이다. )
React native 번들
개발자가 작성한 코드를 빌드를 하면서 metro (웹펙과 같은 번들러)로 스크립트를 묶어준다. 이 코드가 각각의 플랫폼에 넘겨지게 되고, 이를 실행할 수 있도록 bridge가 script와 native 상호 소통하도록 도와준다.
React native App Thread
react native app에는 3개의 병렬 스레드가 존재한다.
1. Main Thread (UI Thread, Base Thread) : 핸들 사용자 인터페이스에 대한 책임. UI를 업데이트하거나 기본 기능에 액세스해야 할 때마다 JS 스레드와 통신한다.
1-1) 네이티브 UI -기본 안드로이드 또는 ios의 UI 렌더링에 사용된다.
1-2) 네이티브 모듈
2. Shadow Thread : 레이아웃이 계산되는 쓰레드. facebook의 자체 레이아웃 엔진인 Yoga를 사용하여 flexbox 레이아웃을 계산하고 UI 쓰레드로 다시 보낸다.
3. JS Thread : 모든 자바 스크립트 코드를 읽고, 컴파일 및 응용프로그램의 비즈니스 로직의 대부분이 일어나는 곳이다.
좋은 성능을 유지하기 위해 JS 스레드는 다음 프레임 렌더링 데드라인 전에 배치 업데이트를 UI 스레드에 전달할 수 있어야한다.
ex ) ios - 초당 60프레임. 1프레임에 16.67ms 마다 새로운 프레임을 이어지게 해야한다. javascript 이벤트 루프에서 UI변경으로 이어지는 복잡한 처리를 수행할 때 1프레임에 16.67ms가 넘어가게 되면 UI가 느리게 나타난다.
UI 스레드에서 완전히 일어나는 네이티브 뷰는 예외.
ex ) navigatorIOS 또는 scrollView는 UI 스레드에서 완전히 실행 되므로 js 스레드로 인해 차단되지는 않는다.
- metro : 앱이 프로덕션을 위해 번들될 때, js 번들을 생성
- JavascriptCore : 앱이 실행될 때 번들을 실행 ( 자바스크립트 엔진 )
위와 같이 리액트 네이트브의 구조는 이루어져있다. 각각의 구조 및 역할을 봤으니 디테일하게 단계적으로 흐름을 파악해보자.
1. 개발자가 코드를 작성한 코드는 metro와 함께 번들된다.
2. 앱이 실행되고 메인 쓰레드가 돌고, 여기서 번든된 js가 로드를하기 시작한다.
3. 로드가 완료된 후 js는 앱에 관련된 화면 및 정보에 대해 json형태로 브릿지에 넘겨준다.
4. 브릿지는 shadow thread에 넘겨준다. shadow thread는 layout을 계산을 한다.
5. 계산한 값을 main thread에 넘겨주고 main thread는 실제 View를 그려준다.
6. 사용자가 어떠한 이벤트를 실행할 하면 main thread는 브릿지에게 전달한다.
7. script는 해당 이벤트를 처리한다.
8. 이에 따라 변경된 layout을 react는 가상돔과 비교 ( diffing)하여 변경된 부분만 bridge에 넘겨준다.
9. 넘겨준 값을 shadow thread에서 계산 하고 이를 main thread에 넘겨주고 main thread는 그려준다.
이러한 과정이 계속해서 반복되며 리액트 네이티브 앱을 이루게 된다.
문제점
위의 아키텍처에 대한 문제는 무엇일까
문제는 native와 js 간의 소통에 있어 bridge를 통해 이루어지고, 이를 비동기로 소통을 한다는 것이 문제이다.
이것이 왜 문제인가 ? 모든 스레드는 브릿지를 통해 전송되는데 이에 대한 응답을 언제 올지 모르는 체로, 응답에 상관없이 계속해서 요청을 보낸다는 것이다. 이는 혼잡함을 제공하고, 성능을 떨어트리게 된다.
ex ) 네이트브 영역에서 onScroll event가 발생할 때마다 정보는 javascript 영역으로 비동기적으로 전송이 된다. 이렇게 전송을 하고 네이티브 영역에서는 이를 기다리지 않고 다른 작업을 계속하게 된다. 이로 인해 전보가 화면에 표시 되기 전에 이벤트는 계속 이러나고 결국 ui상 공백을 이끌게 된다.
이러한 문제점을 가지고 있기 때문에 facebook팀은 새로운 아키텍처를 도입하게 된 것이다.
새 아키텍처에 대해서는 다음 글에서 이어지도록하겠다.
다음 : https://sangwonny.tistory.com/45
참고자료 :
https://chifuyu.tistory.com/23
https://velog.io/@koreanhole/React-Native%EC%9D%98-%EC%9E%91%EB%8F%99%EC%9B%90%EB%A6%AC
https://ichi.pro/ko/2020-nyeon-react-native-ui-jae-akitegcheo-171215219685676
'react native' 카테고리의 다른 글
React-native-video 문제 그리고 첫 opensource Pr (0) | 2022.01.13 |
---|---|
React native 구동 방식 ( 신 ) (0) | 2021.12.26 |
dependency 버전 문제 (0) | 2021.12.18 |
react-native 프로젝트 구조 (0) | 2021.12.18 |
react native 들어가기 전에 ( Expo vs React native CLI ) (0) | 2021.11.10 |