Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Slot props and typescript, how to handle types?

I'm using slot props in a project. I'm having a generic component that takes an Array as input.

MyComponent:

<script lang="ts">
    export let data: Array<any>;
</script>

<div>
    <!-- some stuff ... -->
    {#each data as item}
        <slot {item} />
    {/each}
    <!-- ... and other stuff ... -->
</div>

Caller:

<script lang="ts">
    let myData : Array<MyType> = ...
</script>

<MyComponent data={myData} let:item>
    <li>{item.myVerySpecificField}
</MyComponent>

I can't get my head around how to force the item to be typed as MyType. Any ideas?

It works as is, but I don't get any checks at compile time.

like image 863
Krillegeddon Avatar asked Nov 16 '22 00:11

Krillegeddon


1 Answers

Generic components are, as far as I know, experimentally implemented as described here: https://github.com/dummdidumm/rfcs/blob/ts-typedefs-within-svelte-components/text/ts-typing-props-slots-events.md

In your case, that would translate to:

MyComponent:

<script lang="ts">
  // define a generic
  type T = $$Generic;

  // use that generic
  export let data: Array<T>;
</script>

<div>
  <!-- some stuff ... -->
  {#each data as item}
    <slot {item} />
  {/each}
  <!-- ... and other stuff ... -->
</div>

Caller:

<script lang="ts">
  import MyComponent from "./MyComponent.svelte";

  type MyType = { field: "one" | "two" | "three" };

  let myData: Array<MyType> = [
    { field: "one" },
    { field: "two" },
    { field: "three" },
  ];
</script>

<MyComponent data={myData} let:item>
  <li>{item.field}</li>
</MyComponent>

item should then be properly typed.

like image 144
Sophia Mersmann Avatar answered Dec 21 '22 16:12

Sophia Mersmann