Search code examples
sveltestoresveltekitsvelte-store

SvelteKit store undefined when accessed from a different component


I'm attempting to set a store within one Svelte component and access it another. I immediately log the store after setting it (in Component.svelte), and it's what I expect however my reactive statement in a different file (the root +page.svelte) sees it as undefined. The store is being set as it contains an initial value "initial" (logged at the start) which is then removed after a node is clicked and the set function is called.

stores.ts

export type SelectedNode = {
    name: string;
    group: string;
    id: string;
}

const selectedNodeInit: SelectedNode[] = [<SelectedNode>({
    group: "",
    name: "initial",
    id: ""
})];
export const selectedNodeStore = writable(selectedNodeInit);

Component.svelte

import { selectedNodeStore } from '../stores';

...

.onNodeClick(node => {
    let selectedNode = {
        name: node.id,
        group: node.group == 1 ? "one" : "two",
        id: node.id != null ? node.id : ""
    };

    selectedNodeStore.set(selectedNode);
    console.log($selectedNodeStore); // contains the correct value

    ...

+page.svelte

<script>
    import { selectedNodeStore, someOtherStore } from '../stores';

    ...

    $: console.log("retrieved node from store: " + get($selectedNodeStore)[0]?.name) // is undefined
</script>

Component.svelte is written in JavaScript as I'm using a library to create a graph of nodes, and setting the store from within that.

What I find more confusing is that I have another store that's set up in the same way, and I set it in async functions and use it in a similar way and have no issues.


Solution

  • I worked it out, it was a type mismatch from when I was setting the store in Component.svelte that was using JavaScript instead of TypeScript. I needed to set an array, not an object. Fixed code:

    Component.svelte

    import { selectedNodeStore } from '../stores';
    
    ...
    
    .onNodeClick(node => {
        let selectedNode = [{
            name: node.id,
            group: node.group == 1 ? "one" : "two",
            id: node.id != null ? node.id : ""
        }];
    
        selectedNodeStore.set(selectedNode);
        console.log($selectedNodeStore);
    
        ...
    

    Remember, kids, strict typing saves lives.