$bindable — 바인딩 가능한 props

$bindable — 바인딩 가능한 props

보통 props는 부모에서 자식으로 한 방향으로 흐르기 때문에 앱 안의 데이터 흐름을 이해하기 쉬워요. Svelte에서는 컴포넌트 props를 바인딩(bound) 할 수 있는데, 그러면 데이터가 자식에서 부모로 위쪽으로도 흐를 수 있어요. 자주 쓰는 건 권장하지 않지만, 드물게 신중하게 쓰면 코드가 단순해질 수 있어요.

출처: https://svelte.dev/docs/svelte/$bindable

props를 바인딩 가능하게 표시하려면 $bindable 런을 사용해요.

<script>
  let { value = $bindable(), ...props } = $props();
</script>

<input bind:value={value} {...props} />

그러면 이 컴포넌트를 쓰는 쪽에서 bind: 디렉티브를 붙일 수 있어요.

<script>
  import FancyInput from './FancyInput.svelte';
  let message = $state('hello');
</script>

<FancyInput bind:value={message} />
<p>{message}</p>

부모는 반드시 bind:를 써야 하는 건 아니에요. 일반 props로 그냥 전달할 수도 있어요. 어떤 부모는 자식의 말을 듣고 싶지 않을 테니까요.

이 경우 props가 전혀 전달되지 않을 때 쓸 fallback 값을 지정할 수 있어요.

<script>
  let { bindableProperty = $bindable('fallback value'), ...props } = $props();
</script>

이 fallback 값은 속성이 바인딩되지 않을 때만 적용돼요. 속성이 바인딩되면서 fallback 값이 있으면, 부모가 undefined가 아닌 값을 제공해야 하고 그렇지 않으면 런타임 오류가 발생해요. 어느 값이 적용돼야 하는지 애매한 상황을 막아주는 장치예요.

속성을 bindable로 선언한다는 건 bind:쓸 수 있다는 뜻이지, 반드시 써야 한다는 뜻이 아니에요. props를 바인딩하면 자식이 상태 프록시를 변형(mutate) 할 수도 있어요. 일반 props로도 변형은 가능하지만 Svelte가 소유하지 않은 상태를 변형하는 걸 감지하면 경고를 띄우므로, 강하게 권장하지 않아요.

더 알아보기