React는 지속적으로 발전하면서 성능 최적화와 개발자 경험을 개선하는 다양한 기능을 도입하고 있습니다. React 18에서는 Concurrent Rendering(동시 렌더링), 자동 배치(Automatic Batching), 스트리밍 서버 렌더링(Streaming SSR) 등의 기능이 추가되었으며, React 19에서는 Actions API, 서버 컴포넌트(Server Components), useOptimistic 훅 등의 기능이 도입되었습니다. 이번 글에서는 React 18과 19의 주요 변경 사항과 최신 트렌드를 정리합니다.
1. React 18의 주요 기능
1.1 Concurrent Rendering (동시 렌더링)
React 18에서는 Concurrent Rendering이 기본적으로 활성화되었습니다. 기존 React는 한 번 렌더링이 시작되면 모든 작업을 완료할 때까지 UI가 멈췄으나, Concurrent Rendering을 통해 UI 응답성을 유지하면서 중요한 작업을 먼저 처리할 수 있게 되었습니다.
예제: useTransition을 활용한 동시 렌더링
import { useState, useTransition } from 'react';
function SearchComponent({ items }) {
const [searchTerm, setSearchTerm] = useState('');
const [filteredItems, setFilteredItems] = useState([]);
const [isPending, startTransition] = useTransition();
function handleChange(event) {
setSearchTerm(event.target.value);
startTransition(() => {
const filtered = items.filter((item) => item.includes(event.target.value));
setFilteredItems(filtered);
});
}
return (
<div>
<input type="text" value={searchTerm} onChange={handleChange} />
{isPending ? <p>필터링 중...</p> : <ul>{filteredItems.map((item) => <li key={item}>{item}</li>)}</ul>}
</div>
);
}
useTransition을 활용하면 UI 입력(예: 검색어 입력)과 무거운 연산(예: 리스트 필터링)을 분리하여 부드러운 사용자 경험을 제공합니다.
1.2 Automatic Batching (자동 배치)
React 18에서는 비동기 함수 내에서도 상태 업데이트가 자동으로 배치 처리됩니다.
기존에는 상태를 여러 번 업데이트하면 매번 다시 렌더링되었으나, React 18부터는 하나의 렌더링으로 처리됩니다.
예제: 자동 배치 적용 전 (React 17)
import { useState } from 'react';
function MyComponent() {
const [count, setCount] = useState(0);
const [flag, setFlag] = useState(false);
function handleClick() {
setCount(count + 1);
setFlag(!flag);
// React 17에서는 두 번의 렌더링이 발생함
}
return <button onClick={handleClick}>Click me</button>;
}
예제: 자동 배치 적용 후 (React 18)
function handleClick() {
setCount(count + 1);
setFlag(!flag);
// React 18에서는 한 번의 렌더링으로 처리됨
}
자동 배치 기능이 적용되면서 불필요한 렌더링이 감소하고 성능이 향상되었습니다.
1.3 Suspense 개선
React 18에서는 Suspense를 활용하여 데이터 로딩을 더욱 효율적으로 처리할 수 있도록 개선되었습니다.
이전에는 코드 스플리팅에만 사용할 수 있었으나, 이제는 서버 컴포넌트와도 연동됩니다.
예제: Suspense를 이용한 데이터 로딩
import { Suspense } from 'react';
const DataComponent = React.lazy(() => import('./DataComponent'));
function App() {
return (
<Suspense fallback={<p>데이터 로딩 중...</p>}>
<DataComponent />
</Suspense>
);
}
Suspense를 활용하면 데이터가 로딩될 때까지 대체 UI를 표시할 수 있으며, 서버 컴포넌트와 함께 사용하여 성능을 최적화할 수 있습니다.
2. React 19의 새로운 기능
2.1 Actions API
React 19에서는 useAction을 도입하여 비동기 작업을 보다 간결하게 처리할 수 있도록 개선되었습니다.
Actions API를 활용하면 서버 요청과 상태 업데이트를 한 번에 처리할 수 있습니다.
예제: Actions API를 활용한 서버 업데이트
import { useAction } from 'react';
function UpdateName() {
const updateName = useAction(async (name) => {
await api.updateName(name);
});
return (
<form action={updateName}>
<input name="name" />
<button type="submit">Update</button>
</form>
);
}
Actions API를 사용하면 서버 요청과 폼 전송을 간소화할 수 있습니다.
2.2 useOptimistic 훅
React 19에서는 useOptimistic 훅이 추가되어 낙관적 UI 업데이트를 쉽게 구현할 수 있습니다.
서버 요청 후 응답을 기다리지 않고 즉시 UI를 변경하여 사용자 경험을 개선할 수 있습니다.
예제: useOptimistic을 활용한 UI 업데이트
import { useOptimistic } from 'react';
function OptimisticComponent() {
const [optimisticState, updateOptimisticState] = useOptimistic({ text: 'Initial Text' });
function handleSubmit(newText) {
updateOptimisticState({ text: newText });
sendToServer(newText); // 서버에 데이터 전송
}
return (
<div>
<p>{optimisticState.text}</p>
<button onClick={() => handleSubmit('Updated Text')}>Update</button>
</div>
);
}
useOptimistic을 사용하면 서버 응답을 기다리는 동안 사용자 경험이 자연스럽게 유지됩니다.
2.3 서버 컴포넌트(Server Components)
React 19에서는 서버 컴포넌트가 더욱 발전하여 서버에서 데이터를 렌더링한 후 클라이언트로 전달하는 기능이 강화되었습니다.
예제: 서버 컴포넌트를 활용한 데이터 로딩
export default async function ServerComponent() {
const data = await fetchDataFromAPI();
return <ClientComponent data={data} />;
}
서버 컴포넌트를 사용하면 SEO 성능이 향상되고, 클라이언트에서 불필요한 렌더링을 줄일 수 있습니다.
3. 최신 트렌드와 권장 사항
서버 컴포넌트와 스트리밍 서버 렌더링(Streaming SSR)
React 19에서는 서버 컴포넌트와 **스트리밍 서버 렌더링(Streaming SSR)**이 발전하면서 서버에서 HTML을 부분적으로 렌더링하여 클라이언트로 전송하는 기능이 더욱 최적화되었습니다.
낙관적 UI 업데이트 활용
useOptimistic과 Actions API를 적극적으로 활용하여 사용자가 즉각적인 피드백을 받을 수 있도록 구현하는 것이 최신 트렌드입니다.
결론
React 18과 19에서는 Concurrent Rendering, 자동 배치, Suspense 개선, Actions API, 서버 컴포넌트 등 다양한 기능이 추가되었습니다.
이러한 기능을 적극 활용하면 성능이 최적화된 애플리케이션을 개발할 수 있습니다.
'개발이야기' 카테고리의 다른 글
React 고급 기술 익히기 - 9편: React와 WebAssembly(WASM) 연동하기 (0) | 2025.02.08 |
---|---|
React 고급 기술 익히기 - 8편: React Compiler의 원리와 최적화 기술 (0) | 2025.02.06 |
React 고급 기술 익히기 - 6편: Concurrent Mode와 Fiber 아키텍처 (0) | 2025.02.04 |
React 고급 기술 익히기 - 5편: Reconciliation과 렌더링 최적화 (0) | 2025.02.03 |
React 고급 기술 익히기 - 4편: 코드 스플리팅과 서버 사이드 렌더링(SSR) 최적화 (0) | 2025.02.03 |