최신 Svelte v5 반응성 시스템 완벽 분석과 마이그레이션 가이드
2024-10-25 08:13:04Svelte v5 반응성 시스템 소개
Svelte v5는 현재 존재하는 가장 뛰어난 프론트엔드 프레임워크의 최신 버전으로, 이전 버전과 매우 다릅니다. 변경의 핵심은 변수의 반응성 구현 방식에 있습니다. 이러한 변화 덕분에 Svelte는 더 쉬워졌지만 동시에 약간 더 어려워졌습니다. 필자는 Svelte v5@next.155부터 실제 마이크로 프론트엔드 프로젝트에서 작업해왔기 때문에, 이러한 지식을 전달하기 위한 글 시리즈를 작성하게 되었습니다.
Svelte v4의 반응성 시스템
Svelte v4는 아름다운 반응성 시스템을 자랑합니다. 이 시스템은 컴포넌트의 코드를 정적으로 분석하고, 일반 자바스크립트 변수가 변경될 때마다 DOM을 명령형으로 변경하는 코드를 생성합니다. 간단하고 우아하며, 매우 효율적인 구조입니다.
아래는 예시 코드입니다.
<script lang="ts">
let clickCount = 0;
function countClicks() {
++clickCount;
}
</script>
<svelte:document on:click={() => countClicks()} />
<pre>문서 내 클릭 횟수: {clickCount}</pre>
이 코드는 문서 객체에 클릭 이벤트 리스너를 추가하고, 클릭 수를 실시간으로 표시합니다. 그러나 이러한 반응성 접근 방식에도 단점이 존재합니다.
코드 리팩토링의 어려움
Svelte v4의 반응성 시스템의 가장 큰 단점 중 하나는 이 시스템을 컴포넌트 외부에서 사용할 수 없다는 점입니다. 예를 들어, countClicks 함수를 모듈로 분리하면, 정적 코드 분석기에서 변수 변경을 감지할 수 없어 반응성이 사라집니다.
Svelte v5의 반응성: 룬(Runes)
Svelte v5에서 반응성은 다음과 같은 "마법의 기호"인 룬의 사용을 통해 관리됩니다:
$state$props$bindable$derived$effect
룬은 함수처럼 보이지만, 실제로는 L-value를 생성합니다. 즉, 상태를 다른 변수에 전달할 수는 없으며, 이를 통해 코드의 리팩토링이 가능해졌습니다.
새로운 반응성 시스템의 장점
Svelte v5의 반응성 시스템은 다음과 같은 주요 장점을 제공합니다:
- 컴포넌트 외부에서도 반응형 변수 사용 가능
- 세밀한 반응성 제공
예를 들어, 데이터 테이블에서 새로운 행이 추가되면 Svelte는 새로운 행만 렌더링합니다. 특정 셀의 값이 변경되면 해당 셀만 다시 렌더링되어 성능을 개선합니다. 이제 이러한 개선 사항이 명확해졌다면 좋겠습니다.
$state 룬
$state 룬은 반응형 상태를 생성하는 데 사용됩니다. 이전의 Svelte v4 코드 샘플을 간단히 리팩토링해 보겠습니다.
<script lang="ts">
let clickCount = $state(0);
function countClicks() {
++clickCount;
}
</script>
<svelte:document onclick={() => countClicks()} />
<pre>문서 내 클릭 횟수: {clickCount}</pre>
이제 0 대신 $state(0)을 사용하여 같은 결과를 얻을 수 있습니다. $state는 변수를 초기화하는 데만 사용될 수 있으며, Runes는 경쟁하는 변수가 아닙니다. 즉, 변수가 아닌 상태를 만드는데 중점을 둡니다.
$props 룬 사용하기
Svelte v5는 $props 룬을 통해 컴포넌트 속성을 반응형으로 만듭니다.
<script lang="ts">
type Props = {
data: number[];
operation?: 'sum' | 'avg';
};
let {
data,
operation = 'sum',
...restProps,
}: Props = $props();
function sum() {
return data.reduce((p, c) => p + c);
}
function avg() {
return sum() / data.length;
}
</script>
<span class="amount" {...restProps}>{operation === 'sum' ? sum() : avg()}</span>
<style>
.amount {
font-family: monospace;
}
</style>
타입스크립트를 사용하는 프로젝트에서는 속성을 먼저 정의한 후, $props()를 사용하여 반응형 속성을 가져옵니다. 기본값을 설정하고 나머지 속성(restProps)을 다루는 방법을 제시하여 타입 안정성도 유지합니다.
마무리
Svelte v5의 새로운 반응성 시스템은 개발자에게 더 많은 자유와 효율성을 제공합니다. 컴포넌트 외부에서 반응형 코드를 정상적으로 사용할 수 있게 되면서, 코드 재사용성과 유지보수성이 크게 향상되었습니다. 이 글이 Svelte v5를 이해하고, 마이그레이션을 고려하는 데 도움이 되었기를 바랍니다.
추가적으로 Svelte에 대한 더 많은 정보와 문서를 원하신다면 아래의 링크를 참조하시기 바랍니다.