UNPKG

@zeix/cause-effect

Version:

Cause & Effect - reactive state management primitives library for TypeScript.

148 lines (122 loc) 4.9 kB
--- title: "Store, List, and Collection" description: "API reference for composite object and keyed collection primitives." --- Import path for every item on this page: `@zeix/cause-effect`. Source files: `src/nodes/store.ts`, `src/nodes/list.ts`, and `src/nodes/collection.ts`. ## `createStore` ```ts function createStore<T extends UnknownRecord>( value: T, options?: StoreOptions, ): Store<T> ``` | Parameter | Type | Default | Description | |-----------|------|---------|-------------| | `value` | `T` | | Initial plain object. Arrays become `List`, nested records become `Store`. | | `options.watched` | `() => Cleanup` | `undefined` | Optional lifecycle callback for first subscriber / last unsubscribe. | Key methods: ```ts type Store<T extends UnknownRecord> = { get(): T set(next: T): void update(fn: (prev: T) => T): void keys(): IterableIterator<string> byKey<K extends keyof T & string>(key: K): ... add<K extends keyof T & string>(key: K, value: T[K]): K remove(key: string): void } ``` ## `createList` ```ts function createList<T extends {}, S extends MutableSignal<T> = MutableSignal<T>>( value: T[], options?: ListOptions<T, S>, ): List<T, S> ``` | Parameter | Type | Default | Description | |-----------|------|---------|-------------| | `value` | `T[]` | | Initial list items. | | `options.keyConfig` | `KeyConfig<T>` | auto-increment | String prefix or key callback. | | `options.watched` | `() => Cleanup` | `undefined` | Lifecycle callback tied to subscribers. | | `options.itemEquals` | `(a: T, b: T) => boolean` | `DEEP_EQUALITY` | Equality for default item signals. | | `options.createItem` | `(value: T) => S` | `createState` | Custom signal factory for each item. | Key methods: ```ts type List<T extends {}, S extends MutableSignal<T> = MutableSignal<T>> = { readonly length: number get(): T[] set(next: T[]): void update(fn: (prev: T[]) => T[]): void at(index: number): S | undefined byKey(key: string): S | undefined keys(): IterableIterator<string> keyAt(index: number): string | undefined indexOfKey(key: string): number add(value: T): string remove(keyOrIndex: string | number): void replace(key: string, value: T): void sort(compareFn?: (a: T, b: T) => number): void splice(start: number, deleteCount?: number, ...items: T[]): T[] deriveCollection<R extends {}>(callback: (sourceValue: T) => R): Collection<R> deriveCollection<R extends {}>(callback: (sourceValue: T, abort: AbortSignal) => Promise<R>): Collection<R> } ``` ## `createCollection` ```ts function createCollection<T extends {}, S extends Signal<T> = Signal<T>>( watched: CollectionCallback<T>, options?: CollectionOptions<T, S>, ): Collection<T, S> ``` | Parameter | Type | Default | Description | |-----------|------|---------|-------------| | `watched` | `CollectionCallback<T>` | | Starts the external source and receives `applyChanges`. | | `options.value` | `T[]` | `[]` | Initial collection value. | | `options.keyConfig` | `KeyConfig<T>` | auto-increment | Key strategy. | | `options.createItem` | `(value: T) => S` | `createState` | Custom item signal factory. | | `options.itemEquals` | `(a: T, b: T) => boolean` | `DEEP_EQUALITY` | Equality for default item signals. | Key methods: ```ts type Collection<T extends {}, S extends Signal<T> = Signal<T>> = { get(): T[] keys(): IterableIterator<string> at(index: number): S | undefined byKey(key: string): S | undefined keyAt(index: number): string | undefined indexOfKey(key: string): number deriveCollection<R extends {}>(callback: (sourceValue: T) => R): Collection<R> deriveCollection<R extends {}>(callback: (sourceValue: T, abort: AbortSignal) => Promise<R>): Collection<R> readonly length: number } ``` Related types: ```ts type StoreOptions = { watched?: () => Cleanup } type KeyConfig<T> = string | ((item: T) => string | undefined) type CollectionChanges<T> = { add?: T[]; change?: T[]; remove?: T[] } type CollectionCallback<T extends {}> = ( apply: (changes: CollectionChanges<T>) => void, ) => Cleanup ``` Usage: ```ts import { createCollection, createEffect, createList, createStore, } from '@zeix/cause-effect' const settings = createStore({ theme: 'light', pageSize: 20 }) const rows = createList([{ id: 'a', value: 1 }], { keyConfig: item => item.id }) const labels = rows.deriveCollection(item => `${item.id}:${item.value}`) createEffect(() => { console.log(settings.theme.get(), labels.get()) }) ``` ### Guards ```ts function isStore<T extends UnknownRecord>(value: unknown): value is Store<T> function isList<T extends {}, S extends MutableSignal<T> = MutableSignal<T>>(value: unknown): value is List<T, S> function isCollection<T extends {}, S extends Signal<T> = Signal<T>>(value: unknown): value is Collection<T, S> ``` Related pages: `/docs/composite-collections` and `/docs/guides/keyed-collections`.