ReactDOM.createRoot ๐ ReactDOM.render
11252 ๋จ์ด reactwebdevjavascriptprogramming
React 18์ ์๋ก์ด ๋ฃจํธ API๋ฅผ ๋์ ํ์ต๋๋ค.
๐ ํ์ฌ API
๋ช ์์ ์ผ๋ก ๋ ๋๋งํ ๋๋ง๋ค ํจ์๋ฅผ ๋ ๋๋งํ๊ธฐ ์ํด
container
๋ฅผ ์ ๋ฌํด์ผ ํฉ๋๋ค.const container = document.querySelector('#root');
// Initial render. Container is explicitly accessed.
ReactDOM.render(<App text="Hello" />, container);
// Subsequent renders. Container is explicitly accessed.
ReactDOM.render(<App text="Hello world!" />, container);
๐
ReactDOM.render
๋ ๋ฌด์์ ๊ฐ์ ธ๊ฐ๋์?render
ํจ์๋ ์ธ ๊ฐ์ ์ธ์๋ฅผ ์ทจํฉ๋๋ค.๊ทธ๋ฆฌ๊ณ ๋์ผํ
container
์ ๋ฐํํ์ง๋ง ๋ ๋๋ง๋ ๊ตฌ์ฑ ์์๊ฐ ์์ต๋๋ค./**
* @param element - React element to be rendered
* @param container - DOM element to render in
* @param callback - function to be executed after render happens
* @return container - container with renderned component
*/
function render(element, container, callback) {
// ...
}
๐
ReactDOM.render
๋ ํ๋ ์๋์์ ์ด๋ป๊ฒ ์๋ํฉ๋๊น?ReactDOM.render
๋ ๋ช ๊ฐ์ง ์ ํจ์ฑ ๊ฒ์ฌ๋ฅผ ์ํํฉ๋๋ค.createRoot
๋ก ์ ๋ฌ๋์ง ์์๋์ง ์ฌ๋ถ๊ทธ๋ฐ ๋ค์ ์์ ๋ ๋ชจ๋ ์ธ์๋ฅผ
legacyRenderSubtreeIntoContainer
์ ์ ๋ฌํฉ๋๋ค.// simplified structure
function render(element, container, callback) {
if (isValidContainer(element)) {
throw Error('Target container is not a DOM element.');
}
if (isContainerMarkedAsRoot(container) && container._reactRootContainer === undefined) {
// don't throw an error, but logs it into console
error('container was previously passed to ReactDOM.createRoot().');
}
return legacyRenderSubtreeIntoContainer(null, element, container, false, callback);
}
๐ ์๋ก์ด API
๋ช ์์ ์ผ๋ก ๋ ๋๋งํ ๋๋ง๋ค ์ปจํ ์ด๋๋ฅผ ์ ๋ฌํ๋ ๋ฌธ์ ๋ฅผ ํด๊ฒฐํฉ๋๋ค.
// First, we create a root
const root = ReactDOM.createRoot(document.querySelector('#root'));
// Initial render. Container is implicitly accessed.
root.render(<App name="Hello" />);
// Subsequent renders. Container is implicitly accessed.
root.render(<App name="Hello world!" />);
๐
ReactDOM.createRoot
๋ ๋ฌด์์ ๊ฐ์ ธ๊ฐ๋์?createRoot
ํจ์๋ ํ๋์ ํ์ ์ธ์(๋ ๋๋งํ DOM ์์)๋ง ์ฌ์ฉํฉ๋๋ค.๊ทธ๋ฆฌ๊ณ render ๋ฐ unmount ๋ฉ์๋๊ฐ ์๋
RootType
๋ฅผ ๋ฐํํฉ๋๋ค.์ถ์ ๋ํ
createRoot
๋ ๋ ๋ฒ์งธ RootOptions
์ธ์๋ฅผ ์ทจํ์ง๋ง ํฅํ ์ด๋ฅผ ๊ฒํ ํ ๊ฒ์
๋๋ค./**
* @param container - DOM element to render in
* @param options - options, related to hydration
* @return RootType - instance of root
*/
function createRoot(container, options) {
// ...
}
๐
ReactDOM.createRoot
๋ ํ๋ ์๋์์ ์ด๋ป๊ฒ ์๋ํฉ๋๊น?๋ ๋๋ง ๊ธฐ๋ฅ ์์
createRoot
:๊ทธ๋ฐ ๋ค์
createRoot
์ ReactDOMRoot
๊ฐ์ฒด๋ฅผ ์ธ์คํด์คํํ๊ณ ๋ฐํํฉ๋๋ค. ์๋legacyRenderSubtreeIntoContainer
์ ํ!// simplified structure
function createRoot(container, options) {
if (isValidContainer(element)) {
throw Error('Target container is not a DOM element.');
}
if (container.nodeType === 1 && container.tagName.toUpperCase() === 'BODY') {
console.error('Creating roots directly with document.body is discouraged');
}
if (isContainerMarkedAsRoot(container) {
if (container._reactRootContainer) {
console.error('container was previously passed to ReactDOM.render().')
} else {
console.error('container has already been passed to createRoot() before.');
}
}
return new ReactDOMRoot(container, options);
}
์ด์ ์ด์ ๋ ๋๋ง๊ณผ ์
createRoot
ํจ์ ๊ฐ์ ๋ฐ์ค ์ฐจ์ด๋ฅผ ์์์ต๋๋ค!legacyRenderSubtreeIntoContainer
์ new ReactDOMRoot
๋ฅผ ๋ ๋น๊ตํ๊ณ ์ถ๋ค๋ฉด ์๋ ค์ฃผ์ธ์.์ถ์ ์ด์ ๊ฐ์ ๋ ๋ง์ ์ฝํ ์ธ ๋ฅผ ์ํด!
๋ | ๋ฆฌ์กํธ ํ ์ปค๋ฌ โ๏ธ
React Fragments๋ ์ด๋ป๊ฒ ๊ตฌํ๋ฉ๋๊น? React๋ ๊น๋ํ๊ณ ๊นจ๋ํ ์ํ๋ฅผ ์ ์งํ๋ ๊ฒ์ ๋ชฉํ๋ก ํ๊ณ ์์ต๋๋ค. ์ด๊ฒ์ด ๋ฐ๋ก ํ๋๊ทธ๋จผํธ๊ฐ ์กด์ฌํ๋ ์ด์ ์ ๋๋ค. ์ฌ๋ฌ ์์๋ฅผ ๋ ๋๋งํ๋ ๋์ ๊ณผ๋ํ ๋ํผ๋ฅผ ์ ๊ฑฐํ ์ ์์ต๋๋ค! ๊ฝค ๋ฉ์ง์ง๋ง ๋ด๋ถ์์ ์ด๋ป๊ฒ ์๋ํฉ๋๊น? ๐งต๐
์คํ 17:34 - 2022๋ 1์ 25์ผ
Reference
์ด ๋ฌธ์ ์ ๊ดํ์ฌ(ReactDOM.createRoot ๐ ReactDOM.render), ์ฐ๋ฆฌ๋ ์ด๊ณณ์์ ๋ ๋ง์ ์๋ฃ๋ฅผ ๋ฐ๊ฒฌํ๊ณ ๋งํฌ๋ฅผ ํด๋ฆญํ์ฌ ๋ณด์๋ค https://dev.to/fromaline/reactdomcreateroot-reactdomrender-1jg6ํ ์คํธ๋ฅผ ์์ ๋กญ๊ฒ ๊ณต์ ํ๊ฑฐ๋ ๋ณต์ฌํ ์ ์์ต๋๋ค.ํ์ง๋ง ์ด ๋ฌธ์์ URL์ ์ฐธ์กฐ URL๋ก ๋จ๊ฒจ ๋์ญ์์ค.
์ฐ์ํ ๊ฐ๋ฐ์ ์ฝํ ์ธ ๋ฐ๊ฒฌ์ ์ ๋ (Collection and Share based on the CC Protocol.)
์ข์ ์นํ์ด์ง ์ฆ๊ฒจ์ฐพ๊ธฐ
๊ฐ๋ฐ์ ์ฐ์ ์ฌ์ดํธ ์์ง
๊ฐ๋ฐ์๊ฐ ์์์ผ ํ ํ์ ์ฌ์ดํธ 100์ ์ถ์ฒ ์ฐ๋ฆฌ๋ ๋น์ ์ ์ํด 100๊ฐ์ ์์ฃผ ์ฌ์ฉํ๋ ๊ฐ๋ฐ์ ํ์ต ์ฌ์ดํธ๋ฅผ ์ ๋ฆฌํ์ต๋๋ค