Basic store example is not reactive

I'm struggling to understand why this code isn't reactive
import { createEffect, createMemo, createRoot } from "solid-js/dist/solid.js";
import {
createStore,
type Store,
type SetStoreFunction,
} from "solid-js/store/dist/store.js";

interface FooWorld {
readonly store: {
foo: Store<FooWorldState>;
setFoo: SetStoreFunction<FooWorldState>;
};
}

/**
* Bar state for a foo world.
*/
interface FooWorldState {
bar: number;
}

namespace World {
export function create(): FooWorld {
return createRoot(() => {
const [fooStore, setFooStore] = createStore<FooWorldState>({
bar: 0,
});

const getBar = createMemo(() => fooStore.bar);

createEffect(() => {
console.log(`why don't I see this twice?`, getBar());
});

return {
store: {
foo: fooStore,
setFoo: setFooStore,
},
};
});
}
}

const world = World.create();

setTimeout(() => {
world.store.setFoo("bar", 1);
console.log(`I see this!`, world.store.foo.bar);
}, 1000);
import { createEffect, createMemo, createRoot } from "solid-js/dist/solid.js";
import {
createStore,
type Store,
type SetStoreFunction,
} from "solid-js/store/dist/store.js";

interface FooWorld {
readonly store: {
foo: Store<FooWorldState>;
setFoo: SetStoreFunction<FooWorldState>;
};
}

/**
* Bar state for a foo world.
*/
interface FooWorldState {
bar: number;
}

namespace World {
export function create(): FooWorld {
return createRoot(() => {
const [fooStore, setFooStore] = createStore<FooWorldState>({
bar: 0,
});

const getBar = createMemo(() => fooStore.bar);

createEffect(() => {
console.log(`why don't I see this twice?`, getBar());
});

return {
store: {
foo: fooStore,
setFoo: setFooStore,
},
};
});
}
}

const world = World.create();

setTimeout(() => {
world.store.setFoo("bar", 1);
console.log(`I see this!`, world.store.foo.bar);
}, 1000);
I expect the createEffect to run twice, but it only runs once. What am I missing here?
4 Replies
peerreynders
peerreynders6d ago
I suspect that you are still pulling in the server version of Solid which isn't reactive. Compare to: https://stackblitz.com/edit/vitejs-vite-ut3nkg?file=src%2Fmain.ts&terminal=dev
peerreynders
StackBlitz
Vitejs - Vite (forked) - StackBlitz
Next generation frontend tooling. It's fast!
vveisard
vveisard5d ago
That seems to be the case, but it's unclear to me why those imports are "still" resolving to the server versions of solid, despite being explicit Okay, I see the problem: solid-js/store/dist/store.js imports solid-js which then resolves to the server version because of conditional exports.
peerreynders
peerreynders5d ago
// file: index.ts
import { createEffect, createMemo, createRoot } from 'solid-js';
import {
createStore,
type Store,
type SetStoreFunction,
} from 'solid-js/store';
// …
// file: index.ts
import { createEffect, createMemo, createRoot } from 'solid-js';
import {
createStore,
type Store,
type SetStoreFunction,
} from 'solid-js/store';
// …
package.json:
{
"name": "rt-cli",
"version": "0.0.0",
"description": "",
"scripts": {
"bundle": "esbuild index.ts --bundle --packages=external --platform=node --format=cjs --outfile=./index.cjs",
"exec": "node --require solid-register ./index.cjs"
},
"keywords": [],
"author": "",
"license": "ISC",
"dependencies": {
"esbuild": "^0.21.5",
"solid-js": "^1.8.17",
"solid-register": "^0.2.5"
}
}
{
"name": "rt-cli",
"version": "0.0.0",
"description": "",
"scripts": {
"bundle": "esbuild index.ts --bundle --packages=external --platform=node --format=cjs --outfile=./index.cjs",
"exec": "node --require solid-register ./index.cjs"
},
"keywords": [],
"author": "",
"license": "ISC",
"dependencies": {
"esbuild": "^0.21.5",
"solid-js": "^1.8.17",
"solid-register": "^0.2.5"
}
}
$ pnpm run bundle

> rt-cli@0.0.0 bundle /rt-cli
> esbuild index.ts --bundle --packages=external --platform=node --format=cjs --outfile=./index.cjs

index.cjs 814b

:zap: Done in 2ms

rt-cli$ pnpm run exec

> rt-cli@0.0.0 exec /rt-cli
> node --require solid-register ./index.cjs

why don't I see this twice? 0
why don't I see this twice? 1
I see this! 1
$ pnpm run bundle

> rt-cli@0.0.0 bundle /rt-cli
> esbuild index.ts --bundle --packages=external --platform=node --format=cjs --outfile=./index.cjs

index.cjs 814b

:zap: Done in 2ms

rt-cli$ pnpm run exec

> rt-cli@0.0.0 exec /rt-cli
> node --require solid-register ./index.cjs

why don't I see this twice? 0
why don't I see this twice? 1
I see this! 1
vveisard
vveisard5d ago
I also came up with the workaround to bundle beforehand, but I'm trying to use the bun runtime without bundling. I think this problem can only be truly fixed by a standalone reactivity package, which I know is in the works, so I'll close this post for now.