Skip to content

antepodeum/rune-sync

Repository files navigation

rune-sync

npm version License: MIT Svelte Types

Svelte 5 reactive state that automatically persists to any storage backend.

Quick Start

npm install rune-sync
import { lsSync } from 'rune-sync/localstorage'; let settings = lsSync('settings', { theme: 'dark', lang: 'en' }); settings.theme = 'light'; // Persisted automatically

Note: State must always be an object — primitives are not supported as root values.

Drivers

localStorage

import { lsSync } from 'rune-sync/localstorage'; let state = lsSync('key', { count: 0 });

Cross-tab sync via the native storage event. No extra dependencies.

localForage (IndexedDB)

npm install localforage
import { lfSync } from 'rune-sync/localforage'; let state = lfSync('key', { count: 0 });

Cross-tab sync via BroadcastChannel. Requires localforage as a peer dependency.

Cookie

import { ckSync } from 'rune-sync/cookie'; // Default options (path: '/', sameSite: 'lax') let state = ckSync('key', { count: 0 });

With custom cookie settings:

import { createCookieSync } from 'rune-sync/cookie'; const cookieSync = createCookieSync({ path: '/', maxAge: 86400, sameSite: 'strict', secure: true }); let state = cookieSync('key', { count: 0 });

Cross-tab sync via BroadcastChannel. Keep in mind the ~4KB cookie size limit.

CookieOptions:

Option Type Default
path string '/'
domain string
maxAge number (seconds)
expires Date
sameSite 'strict' | 'lax' | 'none' 'lax'
secure boolean

Settings

All drivers accept an optional third argument:

let state = lsSync('key', { value: 0 }, { debounce: 500, // Wait 500ms after last change before writing throttle: 1000, // Write at most once per 1000ms doNotSubscribe: true // Disable cross-tab sync });
Option Type Description
debounce number Delay writes by N ms after the last change
throttle number Write at most once per N ms (with trailing)
doNotSubscribe boolean Disable cross-tab synchronization

Custom Synchronizers

Implement the StateSynchronizer interface to use any storage backend:

import { createSyncState } from 'rune-sync'; import type { StateSynchronizer } from 'rune-sync'; const mySynchronizer: StateSynchronizer = { read: async (key) => { const data = await myStorage.get(key); return data ?? null; }, write: async (key, value) => { await myStorage.set(key, value); }, // Optional: enable real-time updates subscribe: (key, write) => { const unsubscribe = myRealtimeService.on(key, (data) => { write(data); }); return unsubscribe; } }; const mySync = createSyncState(mySynchronizer); let state = mySync('app-state', { counter: 0 });

StateSynchronizer Interface

interface StateSynchronizer { read<T>(key: string): Promise<T | null> | T | null; write<T>(key: string, value: T): Promise<void> | void; subscribe?<T>(key: string, write: (newValue: T) => void): () => void; }

License

MIT License - see LICENSE for details.

About

Svelte 5 library for synchronizing reactive state across various storage backends

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors