You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: src/content/blog/2022/03/08/react-18-upgrade-guide.md
+1-1
Original file line number
Diff line number
Diff line change
@@ -239,7 +239,7 @@ React 18 워킹 그룹은 스타일이나 외부 저장 장치와 같은 특정
239
239
240
240
이 기능은 React의 성능을 대폭 향상할 것이지만, 컴포넌트들이 effect들이 여러 번 마운트되었다가 사라지는 것에 아무런 영향을 받지 않아야 합니다. 대부분의 effect들은 변함없이 계속 작동하겠지만, 어떤 것들은 단 한 번만 마운트되고 사라질 수 있도록 설계되어 있습니다.
241
241
242
-
React 18은 이러한 문제를 시각적으로 보여주기 위해 Strict 모드에 개발 전용 검사를 새롭게 도입합니다. 이 검사는 컴포넌트가 처음 마운트될 때 자동으로 언마운트한 다음, 이전 상태를 복원하면서 다시 마운트할 것입니다.
242
+
React 18은 이러한 문제를 시각적으로 보여주기 위해 Strict 모드에 개발 전용 검사를 새롭게 도입합니다. 이 검사는 컴포넌트가 처음 마운트될 때 자동으로 마운트 해제한 다음, 이전 상태를 복원하면서 다시 마운트할 것입니다.
243
243
244
244
이 업데이트 이전에는 React가 다음과 같이 컴포넌트를 마운트하고 effect를 생성했습니다.
Effect는 컴포넌트와 다른 생명주기를 가집니다. 컴포넌트는 마운트, 업데이트 또는 언마운트할 수 있습니다. 반면 Effect는 동기화를 시작하거나 후에 동기화를 중지하는 두 가지 작업만 할 수 있습니다. Effect가 시간에 따라 변하는 props와 state에 의존하는 경우 이 주기는 여러 번 발생할 수 있습니다.
240
+
Effect는 컴포넌트와 다른 생명주기를 가집니다. 컴포넌트는 마운트, 업데이트 또는 마운트 해제할 수 있습니다. 반면 Effect는 동기화를 시작하거나 후에 동기화를 중지하는 두 가지 작업만 할 수 있습니다. Effect가 시간에 따라 변하는 props와 state에 의존하는 경우 이 주기는 여러 번 발생할 수 있습니다.
241
241
242
242
다음 Effect는 `roomId` prop의 값에 의존합니다. Props는 다시 렌더링할 때 변할 수 있는 *반응형 값* 입니다. `roomId`가 변경되면 Effect가 *다시 동기화* (및 서버에 다시 연결)합니다.
이 Effect는 마운트될 때만 실행되므로 콘솔에 "✅ 연결 중..."이 한 번 출력될 것으로 예상할 수 있습니다. 그러나 콘솔을 확인해 보면 "✅ 연결 중..."이 두 번 출력됩니다. 왜 그럴까요?
526
526
527
-
ChatRoom 컴포넌트가 여러 화면으로 구성된 큰 앱의 일부라고 가정해 보겠습니다. 사용자가 ChatRoom 페이지에서 여정을 시작합니다. 컴포넌트가 마운트되고 connection.connect()를 호출합니다. 그런 다음 사용자가 다른 화면으로 이동한다고 상상해보세요. 예를 들어, 설정 페이지로 이동할 수 있습니다. ChatRoom 컴포넌트가 언마운트됩니다. 마지막으로 사용자가 뒤로 가기 버튼을 클릭하고 ChatRoom이 다시 마운트됩니다. 이렇게 되면 두 번째 연결이 설정되지만 첫 번째 연결은 종료되지 않았습니다! 사용자가 앱을 탐색하는 동안 연결은 종료되지 않고 계속 쌓일 것입니다.
527
+
ChatRoom 컴포넌트가 여러 화면으로 구성된 큰 앱의 일부라고 가정해 보겠습니다. 사용자가 ChatRoom 페이지에서 여정을 시작합니다. 컴포넌트가 마운트되고 `connection.connect()`를 호출합니다. 그런 다음 사용자가 다른 화면으로 이동한다고 상상해보세요. 예를 들어, 설정 페이지로 이동할 수 있습니다. ChatRoom 컴포넌트가 마운트 해제됩니다. 마지막으로 사용자가 뒤로 가기 버튼을 클릭하고 ChatRoom이 다시 마운트됩니다. 이렇게 되면 두 번째 연결이 설정되지만 첫 번째 연결은 종료되지 않았습니다! 사용자가 앱을 탐색하는 동안 연결은 종료되지 않고 계속 쌓일 것입니다.
528
528
529
529
이와 같은 버그는 앱의 이곳저곳을 수동으로 테스트해보지 않으면 놓치기 쉽습니다. 이러한 문제를 빠르게 파악할 수 있도록 React는 개발 모드에서 초기 마운트 후 모든 컴포넌트를 한 번 다시 마운트합니다.
530
530
531
-
"✅ 연결 중..." 로그가 두 번 출력되는 것을 보면 결국 무엇이 문제인지 알 수 있습니다. 컴포넌트가 언마운트될 때 연결을 닫지 않는 문제가 바로 그것이죠.
531
+
"✅ 연결 중..." 로그가 두 번 출력되는 것을 보면 결국 무엇이 문제인지 알 수 있습니다. 컴포넌트가 마운트 해제될 때 연결을 닫지 않는 문제가 바로 그것이죠.
532
532
533
533
이 문제를 해결하려면 Effect에서 클린업 함수를 반환하면 됩니다.
534
534
@@ -542,7 +542,7 @@ ChatRoom 컴포넌트가 여러 화면으로 구성된 큰 앱의 일부라고
542
542
}, []);
543
543
```
544
544
545
-
React는 Effect가 다시 실행되기 전마다 클린업 함수를 호출하고, 컴포넌트가 언마운트(제거)될 때에도 마지막으로 호출합니다. 클린업 함수가 구현된 경우 어떤 일이 일어나는지 살펴보겠습니다.
545
+
React는 Effect가 다시 실행되기 전마다 클린업 함수를 호출하고, 컴포넌트가 마운트 해제(제거)될 때에도 마지막으로 호출합니다. 클린업 함수가 구현된 경우 어떤 일이 일어나는지 살펴보겠습니다.
546
546
547
547
<Sandpack>
548
548
@@ -727,7 +727,7 @@ Effect 안에서 `fetch` 호출을 작성하는 것은 [데이터를 가져오
727
727
728
728
- **Effect는 서버에서 실행되지 않습니다.** 따라서 초기 서버 렌더링된 HTML은 데이터가 없는 로딩 상태만 포함하게 됩니다. 클라이언트 컴퓨터는 모든 JavaScript를 다운로드하고 앱을 렌더링해야만 데이터를 로드해야 한다는 것을 알게 될 것입니다. 이는 효율적이지 않습니다.
729
729
- **Effect 안에서 직접 가져오면 "네트워크 폭포"를 쉽게 만들 수 있습니다.** 부모 컴포넌트를 렌더링하면 일부 데이터를 가져오고 자식 컴포넌트를 렌더링한 다음 그들이 데이터를 가져오기 시작합니다. 네트워크가 빠르지 않으면 이는 모든 데이터를 병렬로 가져오는 것보다 훨씬 느립니다.
730
-
- **Effect 안에서 직접 가져오는 것은 일반적으로 데이터를 미리 로드하거나 캐시하지 않음을 의미합니다.** 예를 들어 컴포넌트가 언마운트되고 다시 마운트되면 데이터를 다시 가져와야 합니다.
730
+
- **Effect 안에서 직접 가져오는 것은 일반적으로 데이터를 미리 로드하거나 캐시하지 않음을 의미합니다.** 예를 들어 컴포넌트가 마운트 해제되고 다시 마운트되면 데이터를 다시 가져와야 합니다.
731
731
- **그리 편리하지 않습니다.** `fetch` 호출을 작성할 때 [경쟁 상태](https://maxrozen.com/race-conditions-fetching-data-react-with-useeffect)와 같은 버그에 영향을 받지 않는 방식으로 작성하는 데 꽤 많은 보일러플레이트 코드가 필요합니다.
732
732
733
733
이 단점 목록은 React에만 해당되는 것은 아닙니다. 어떤 라이브러리에서든 마운트 시에 데이터를 가져온다면 비슷한 단점이 존재합니다. 마운트 시에 데이터를 페칭하는 것도 라우팅과 마찬가지로 잘 수행하기 어려운 작업이므로 다음 접근 방식을 권장합니다.
@@ -843,7 +843,7 @@ export default function App() {
843
843
return (
844
844
<>
845
845
<button onClick={() =>setShow(!show)}>
846
-
컴포넌트 {show ?'언마운트':'마운트'}
846
+
컴포넌트 {show ?'마운트 해제':'마운트'}
847
847
</button>
848
848
{show &&<hr />}
849
849
{show &&<Playground />}
@@ -858,7 +858,7 @@ export default function App() {
858
858
859
859
이제 입력란을 `abc`로 수정해 보세요. 충분히 빠르게 입력하면 `Schedule "ab" log` 바로 뒤에 `Cancel "ab" log`와 `Schedule "abc" log`가 나타날 것입니다. **React는 항상 이전 렌더의 Effect를 다음 렌더의 Effect보다 먼저 정리합니다.** 따라서 빠르게 입력하더라도 한 번에 최대 하나의 타임아웃만 예약되는 것을 볼 수 있습니다. 입력을 몇 번 해보면서 Effect가 어떻게 정리되는지 느껴보세요.
860
860
861
-
입력란에 무언가를 입력한 다음 "컴포넌트 언마운트"를 눌러보세요. 언마운트가 마지막 렌더의 Effect를 정리함을 주목하세요. 여기서는 타임아웃이 실행되기 전에 마지막 타임아웃이 취소됩니다.
861
+
입력란에 무언가를 입력한 다음 "컴포넌트 마운트 해제"를 눌러보세요. 마운트 해제가 마지막 렌더의 Effect를 정리함을 주목하세요. 여기서는 타임아웃이 실행되기 전에 마지막 타임아웃이 취소됩니다.
862
862
863
863
마지막으로 위 컴포넌트를 수정하고 정리 함수의 주석 처리를 해제하여 타임아웃이 취소되지 않도록 해보세요. `abcde`를 빠르게 입력해 보세요. 몇 초 후에 무엇이 기대되는지 생각해 보세요. 타임아웃 내부의 `console.log(text)`가 가장 최근의 `text`를 출력하고 다섯 번의 `abcde` 로그가 생성될까요? 직접 시도하여 확인해 보세요!
864
864
@@ -964,9 +964,9 @@ React는 세 번째 렌더링에서의 `['travel']`와 두 번째 렌더링에
964
964
965
965
그 후에 React는 세 번째 렌더링의 Effect를 실행합니다. `'travel'` 채팅방에 연결합니다.
966
966
967
-
#### 언마운트 {/*unmount*/}
967
+
#### 마운트 해제 {/*unmount*/}
968
968
969
-
마지막으로, 사용자가 다른 페이지로 이동하게 되어 `ChatRoom` 컴포넌트가 언마운트됩니다. React는 마지막 Effect의 클린업 함수를 실행합니다. 마지막 Effect는 세 번째 렌더링에서 온 것입니다. 세 번째 렌더링의 클린업은 `createConnection('travel')` 연결을 종료합니다. 그래서 앱은 `'travel'` 채팅방과의 연결을 해제하게 됩니다.
969
+
마지막으로, 사용자가 다른 페이지로 이동하게 되어 `ChatRoom` 컴포넌트가 마운트 해제됩니다. React는 마지막 Effect의 클린업 함수를 실행합니다. 마지막 Effect는 세 번째 렌더링에서 온 것입니다. 세 번째 렌더링의 클린업은 `createConnection('travel')` 연결을 종료합니다. 그래서 앱은 `'travel'` 채팅방과의 연결을 해제하게 됩니다.
970
970
971
971
#### 개발 환경에서만의 동작 {/*development-only-behaviors*/}
972
972
@@ -984,7 +984,7 @@ React는 세 번째 렌더링에서의 `['travel']`와 두 번째 렌더링에
984
984
- 빈 의존성 배열(`[]`)은 컴포넌트 "마운팅"(화면에 추가됨)을 의미합니다.
985
985
- Strict Mode에서 React는 컴포넌트를 두 번 마운트합니다(개발 환경에서만!) 이는 Effect의 스트레스 테스트를 위한 것입니다.
986
986
- Effect가 다시 마운트로 인해 중단된 경우 클린업 함수를 구현해야 합니다.
987
-
- React는 Effect가 다음에 실행되기 전에 정리 함수를 호출하며, 언마운트 중에도 호출합니다.
987
+
- React는 Effect가 다음에 실행되기 전에 정리 함수를 호출하며, 마운트 해제 중에도 호출합니다.
Copy file name to clipboardExpand all lines: src/content/reference/react-dom/client/createRoot.md
+3-3
Original file line number
Diff line number
Diff line change
@@ -103,7 +103,7 @@ root.unmount();
103
103
104
104
이 함수는 주로 React 루트의 DOM 노드(또는 그 조상 노드)가 다른 코드에 의해 DOM에서 제거될 수 있는 경우에 유용합니다. 예를 들어 DOM에서 비활성 탭을 제거하는 jQuery 탭 패널을 상상해 보세요. 탭이 제거되면 그 안에 있는 모든 것(내부의 React 루트를 포함)이 DOM에서 제거됩니다. 이 경우 `root.unmount`를 호출하여 제거된 루트의 콘텐츠 관리를 "중지"하도록 React에 지시해야 합니다. 그렇지 않으면 제거된 루트 내부의 컴포넌트는 구독과 같은 전역 리소스를 정리하고 확보하는 법을 모르는 채로 있게 됩니다.
105
105
106
-
`root.unmount`를 호출하면 루트에 있는 모든 컴포넌트가 unmount 되고, 트리상의 이벤트 핸들러나 state가 제거되며, 루트 DOM 노드에서 React가 "분리"됩니다.
106
+
`root.unmount`를 호출하면 루트에 있는 모든 컴포넌트가 마운트 해제되고, 트리상의 이벤트 핸들러나 state가 제거되며, 루트 DOM 노드에서 React가 "분리"됩니다.
107
107
108
108
109
109
#### 매개변수 {/*root-unmount-parameters*/}
@@ -117,9 +117,9 @@ root.unmount();
117
117
118
118
#### 주의사항 {/*root-unmount-caveats*/}
119
119
120
-
* `root.unmount`를 호출하면 트리의 모든 컴포넌트가 unmount 되고 루트 DOM 노드에서 React가 "분리"됩니다.
120
+
* `root.unmount`를 호출하면 트리의 모든 컴포넌트가 마운트 해제되고 루트 DOM 노드에서 React가 "분리"됩니다.
121
121
122
-
* `root.unmount`를 한 번 호출한 후에는 같은 루트에서 `root.render`를 다시 호출할 수 없습니다. unmount 된 루트에서 `root.render`를 호출하려고 하면 "unmount 된 root를 업데이트할 수 없습니다." 오류가 발생합니다. 그러나 해당 노드의 이전 루트가 unmount 된 후 동일한 DOM 노드에 새로운 루트를 만들 수는 있습니다.
122
+
* `root.unmount`를 한 번 호출한 후에는 같은 루트에서 `root.render`를 다시 호출할 수 없습니다. 마운트 해제된 루트에서 `root.render`를 호출하려고 하면 "마운트 해제된 root를 업데이트할 수 없습니다." 오류가 발생합니다. 그러나 해당 노드의 이전 루트가 마운트 해제된 후 동일한 DOM 노드에 새로운 루트를 만들 수는 있습니다.
Copy file name to clipboardExpand all lines: src/content/reference/react-dom/client/hydrateRoot.md
+3-3
Original file line number
Diff line number
Diff line change
@@ -100,7 +100,7 @@ root.unmount();
100
100
101
101
주로 React root부터 혹은 그 상위에서부터 시작된 DOM node들을 다른 코드에 의해 DOM에서 삭제되어야 하는 경우 유용합니다. 예를 들어, jQuery 탭 패널이 활성화 되어 있지 않은 탭을 DOM에서 지운다고 가정해봅시다. 탭이 지워지면, React root와 그 내부를 포함해 그 안의 모든 것이 지워지게 되고 DOM에서 또한 지워지게 됩니다. `root.unmount`를 호출해 React에게 삭제된 컨텐츠들을 "그만" 다루라고 알려주어야 합니다. 그렇지 않으면 삭제되어버린 React root 내부의 컴포넌트들은 삭제되지 않을 것이며, "구독"처럼 컴퓨팅 자원을 자유롭게 놓아주지 못하게 됩니다.
102
102
103
-
`root.unmount`를 호출하면 root 내부의 모든 컴포넌트를 unmount하고 root DOM node에서 React를 "떼어"냅니다. root 내부의 event handler와 state까지 모두 포함해 unmount 및 삭제됩니다.
103
+
`root.unmount`를 호출하면 root 내부의 모든 컴포넌트를 마운트 해제하고 root DOM node에서 React를 "떼어"냅니다. root 내부의 event handler와 state까지 모두 포함해 마운트 해제 및 삭제됩니다.
104
104
105
105
#### Parameters {/*root-unmount-parameters*/}
106
106
@@ -113,9 +113,9 @@ root.unmount();
113
113
114
114
#### Caveats {/*root-unmount-caveats*/}
115
115
116
-
* `root.unmount`를 호출하면 root부터 그 안의 모든 컴포넌트가 unmount되고 root DOM node에서 React를 떼어냅니다.
116
+
* `root.unmount`를 호출하면 root부터 그 안의 모든 컴포넌트가 마운트 해제되고 root DOM node에서 React를 떼어냅니다.
117
117
118
-
* `root.unmount`를 한번 호출한 이후엔 `root.render`를 root에 다시 사용할 수 없습니다. unmount된 root에 다시 `root.render`를 호출하려고 한다면 "Cannot update an unmounted root" 에러를 throw하게 됩니다.
118
+
* `root.unmount`를 한번 호출한 이후엔 `root.render`를 root에 다시 사용할 수 없습니다. 마운트 해제된 root에 다시 `root.render`를 호출하려고 한다면 "Cannot update an unmounted root" 에러를 throw하게 됩니다.
0 commit comments