From 267637edd5d415c5065ee0d828031791f19e3d80 Mon Sep 17 00:00:00 2001 From: Valerii Strilets Date: Sun, 6 Sep 2026 09:54:22 +0300 Subject: [PATCH] fix: rehydrate Svelte PermixHydrate when state changes PermixHydrate only hydrated once at init, so a new `state` prop (for example after navigation) was ignored. React and Vue already re-hydrate on prop change; Svelte now does the same via $effect.pre. Co-Authored-By: Claude Fable 5.1 --- permix/src/svelte/PermixHydrate.svelte | 6 +++++- permix/src/svelte/components.test.ts | 16 ++++++++++++++++ 2 files changed, 21 insertions(+), 1 deletion(-) diff --git a/permix/src/svelte/PermixHydrate.svelte b/permix/src/svelte/PermixHydrate.svelte index d98ac4bc..413c8579 100644 --- a/permix/src/svelte/PermixHydrate.svelte +++ b/permix/src/svelte/PermixHydrate.svelte @@ -8,7 +8,11 @@ const { state, children }: { state: DehydratedState, children: Snippet } = const context = usePermixContext() -untrack(() => context.permix.hydrate(state)) +// Hydrate before children render, and again whenever `state` changes. +$effect.pre(() => { + const next = state + untrack(() => context.permix.hydrate(next)) +}) {@render children()} diff --git a/permix/src/svelte/components.test.ts b/permix/src/svelte/components.test.ts index a999f398..a7fe777d 100644 --- a/permix/src/svelte/components.test.ts +++ b/permix/src/svelte/components.test.ts @@ -35,6 +35,22 @@ describe('components', () => { expect(getByTestId('create')).toHaveTextContent('true') }) + it('should rehydrate when state changes', async () => { + const permix = createPermix<{ + post: ['create', 'read'] + }>() + + const { getByTestId, rerender } = render(HydrateApp, { + props: { permix, state: { post: { create: true, read: false } } }, + }) + + expect(getByTestId('create')).toHaveTextContent('true') + + await rerender({ permix, state: { post: { create: false, read: false } } }) + + expect(getByTestId('create')).toHaveTextContent('false') + }) + it('should work with Check component', () => { const permix = createPermix<{ post: ['create']