### Install Reactive with Package Managers
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/installation.mdx
Provides installation commands for the Reactive library using popular package managers like npm, yarn, pnpm, and bun. This snippet demonstrates how to add the library to your project dependencies.
```jsx
import { PackageManagerTabs } from 'rspress/theme'
```
--------------------------------
### React Usage Example with @shined/reactive
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/introduction.md
Demonstrates how to integrate @shined/reactive into a React application for state management. It shows the creation of a store, mutation of state, and consumption of state within a React component using `create` and `useSnapshot`.
```tsx
import { create } from '@shined/reactive'
const store = create({ count: 1 })
const addOne = () => store.mutate.count++
function App() {
const count = store.useSnapshot((s) => s.count)
return (
Count is {count}
)
}
```
--------------------------------
### Custom Enhancer Function Example
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/enhancers/introduction.md
Demonstrates a custom enhancer function that takes a store object and returns a new object with an added `awesomeFeature` method. This showcases how enhancers can modify or extend the functionality of a store.
```tsx
function enhancer(store) {
// Perform some enhancement
// Return the enhanced object
return {
...store,
awesomeFeature() {
console.log('awesomeFeature');
}
};
}
export const enhancedStore = enhancer(create({ count: 1 }));
```
--------------------------------
### State Consumption Methods in @shined/reactive
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/introduction.md
Provides examples of consuming state from a @shined/reactive store using both React components and Vanilla JavaScript/TypeScript. It showcases the `useSnapshot` hook for React and the `snapshot` method for general JavaScript environments, including basic and selector-based access.
```typescript
// In React components
const { count } = store.useSnapshot()
const count = store.useSnapshot((s) => s.count)
// In Vanilla JavaScript/TypeScript
const { count } = store.snapshot()
const count = store.snapshot(s => s.count)
```
--------------------------------
### Enable Redux DevTools for Reactive Store
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/integrations/redux-devtools.mdx
This snippet demonstrates how to initialize a Reactive store and enable Redux DevTools integration. Ensure the Redux DevTools browser extension is installed. The `devtools` function takes the store instance and an options object, including a `name` for the store and an `enable` flag.
```tsx
import { create, devtools } from '@shined/reactive'
const store = create({ count: 1 })
devtools(store, { name: 'awesome-store', enable: true }) // Initialize the store and enable devtools
```
--------------------------------
### Optional Rendering Optimization with Selectors in @shined/reactive
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/introduction.md
Demonstrates the optional rendering optimization feature in @shined/reactive using selectors with the `useSnapshot` hook. It explains how to specify state to pick for granular re-renders and provides a comprehensive example with multiple selectors for different state properties.
```typescript
// Only re-renders when `count` changes, `s => s.count` is the selector, used to pick the specified state.
const count = store.useSnapshot((s) => s.count)
```
```typescript
import { create } from '@shined/reactive'
const store = create({
name: 'Bob',
age: 18,
hobbies: ['Swimming', 'Running'],
address: { city: { name: 'New York' } },
})
export default function App() {
// Will trigger re-render when any part of the store changes
const state = store.useSnapshot()
// Only re-renders when the `city` object in store changes
const { name: cityName } = store.useSnapshot((s) => s.address.city)
// Only re-renders when the `hobbies` object and `age` property in store change
const [hobbies, age] = store.useSnapshot((s) => [s.hobbies, s.age] as const)
// Only re-renders when the `name` in store changes
const name = store.useSnapshot((s) => s.name)
}
```
--------------------------------
### Access Store Snapshot in React Component
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/usage/react.md
Demonstrates using the `useSnapshot` hook to get reactive state within a React component. It shows basic usage, optimized rendering with selectors, and defining custom semantic hooks for cleaner component logic.
```typescript
import { store } from './store'
export default function App() {
// Use the snapshot in the store
const name = store.useSnapshot((s) => s.name)
return
{name}
}
```
```typescript
// All state changes in the store will trigger re-render
const snapshot = store.useSnapshot()
// Only re-render when `name` changes
const name = store.useSnapshot((s) => s.name)
// Only re-render when both `name` and `age` change
const [name, age] = store.useSnapshot((s) => [s.name, s.age] as const)
```
```typescript
import { store } from './store'
// Define semantic Hooks
export const useName = () => store.useSnapshot((s) => s.name)
// Then use it in the component
function App() {
const name = useName()
return
{name}
}
```
--------------------------------
### Get Store Snapshot
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/reference/basic/create.md
Retrieves a static copy (snapshot) of the current store state. This method is available when the `withSnapshot` enhancer is used. An optional selector function can be provided to get a specific slice of the state.
```tsx
const snapSlice = store.snapshot(selector?);
// Usage example
const snap = store.snapshot();
const count = store.snapshot(s => s.count);
```
--------------------------------
### Performance Comparison: Normal Object vs. Proxied Object Get
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/faq.md
Compares the performance of accessing a property on a normal JavaScript object versus a proxied object. This snippet demonstrates the significant overhead introduced by `Proxy` getters when performing a large number of read operations, useful for understanding performance bottlenecks with large datasets.
```javascript
const obj = { name: 'Reactive' };
const proxiedObj = new Proxy(obj, {});
console.time('Normal Object Get');
for(let i = 0; i < 100_000_000; i++) obj.name;
console.timeEnd('Normal Object Get'); // ~50ms, Chrome 131, MacBook Pro (M1 Pro + 16G)
console.time('Proxied Object Get');
for(let i = 0; i < 100_000_000; i++) proxiedObj.name;
console.timeEnd('Proxied Object Get'); // ~1000ms, Chrome 131, MacBook Pro (M1 Pro + 16G)
```
--------------------------------
### Get Snapshot of Reactive Store State in Vanilla JS
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/usage/vanilla.md
Retrieves the current state of the reactive store. For primitive types, direct reading is sufficient. For reference types, create derived objects to maintain immutability. For older versions, `getSnapshot` can be used.
```typescript
// For primitive data types, read directly
const userId = store.mutate.userId
// For reference types, create derived objects based on the existing `store.mutate` to follow the `immutable` principle
const namesToBeConsumed = store.mutate.list.map((item) => item.name);
// From version 0.2.0
const { name } = store.snapshot()
// For versions 0.1.4 and earlier
import { getSnapshot } from '@shined/reactive'
const { name } = getSnapshot(store.mutate)
```
--------------------------------
### Use Snapshot Hook in React - TypeScript
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/reference/internal/use-snapshot.md
Demonstrates how to use the `useSnapshot` hook from the '@shined/reactive' library in a TypeScript React component to get a snapshot of the store's state. It shows various ways to use the hook, including with and without selectors and options.
```tsx
import { useSnapshot } from '@shined/reactive'
useSnapshot(proxyState, selector?, options?);
// Example usage
useSnapshot(store.mutate);
useSnapshot(store.mutate, s => s.count);
useSnapshot(store.mutate, { sync: true });
useSnapshot(store.mutate, s => s.inputValue, { sync: true });
useSnapshot(store.mutate.subObject, subObject => subObject.subCount);
```
--------------------------------
### Read Store State Outside React Component
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/usage/react.md
Explains how to read the store's state outside of React components using `store.mutate` for direct access or `store.snapshot()` to get a snapshot. It emphasizes immutability when creating derivative objects.
```typescript
// For basic data types, read directly
const userId = store.mutate.userId
// For reference types, create a derivative object based on the existing `store.mutate`, to follow the `immutable` principle
const namesToBeConsumed = store.mutate.list.map((item) => item.name);
```
```typescript
// From version 0.2.0
const { name } = store.snapshot()
// Version 0.1.4 and earlier
import { getSnapshot } from '@shined/reactive'
const { name } = getSnapshot(store.mutate)
```
--------------------------------
### Get Immutable State Snapshots with snapshot
Source: https://context7.com/sheinsight/reactive/llms.txt
The `snapshot` function from `@shined/reactive/vanilla` returns a frozen, immutable snapshot of the current state. It can retrieve the entire state or a partial state using a selector function. Snapshots are cached and reused if the state hasn't changed, ensuring immutability and referential equality for unchanged states.
```typescript
import { snapshot } from '@shined/reactive/vanilla'
import { createVanilla } from '@shined/reactive/vanilla'
const store = createVanilla({
products: [
{ id: 1, name: 'Laptop', price: 999 },
{ id: 2, name: 'Mouse', price: 29 }
],
cart: { items: [], total: 0 }
})
// Get full state snapshot
const fullSnapshot = snapshot(store.mutate)
console.log(fullSnapshot)
// { products: [...], cart: {...} }
// Attempt to mutate snapshot fails (frozen object)
try {
fullSnapshot.cart.total = 100 // Error: Cannot assign to read-only property
} catch (e) {
console.log('Snapshots are immutable')
}
// Get partial snapshot with selector
const cartSnapshot = snapshot(store.mutate, s => s.cart)
console.log(cartSnapshot) // { items: [], total: 0 }
// Use in computations
function calculateTax(state) {
const snap = snapshot(state)
return snap.cart.total * 0.1
}
// Snapshots are cached and reused if state hasn't changed
const snap1 = snapshot(store.mutate)
const snap2 = snapshot(store.mutate)
console.log(snap1 === snap2) // true (same reference, cached)
store.mutate.cart.total = 100
const snap3 = snapshot(store.mutate)
console.log(snap1 === snap3) // false (different reference, state changed)
```
--------------------------------
### React useUpdateEffect for Side Effects on State Changes
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/reference/internal/use-subscribe.md
This example shows how to use `useUpdateEffect` from `react-use` to perform side effects when a specific state value changes. This is recommended over directly using `useSubscribe` for handling state-change-driven side effects. It takes a callback function and a dependency array, similar to `useEffect`.
```tsx
const count = useSnapshot(store.mutate, s => s.count);
// Execute side effects when count changes
useUpdateEffect(() => {
console.log('Count has changed', count);
}, [count]);
```
--------------------------------
### Create Vanilla Store with createVanilla
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/reference/basic/create-vanilla.md
Demonstrates the basic usage of `createVanilla` to initialize a store for Vanilla JS applications. This store includes built-in enhancers `withSubscribe` and `withSnapshot`.
```tsx
import { createVanilla } from '@shined/reactive';
const vanillaStore = createVanilla({ count: 0});
// vanillaStore.mutate
// vanillaStore.restore()
// vanillaStore.snapshot()
// vanillaStore.subscribe()
```
--------------------------------
### Using `create` Enhancer for React Stores
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/enhancers/introduction.md
Shows how to use the `create` method from `@shined/reactive` to initialize a store for React applications. It demonstrates accessing both the base VanillaStore properties (`mutate`, `restore`) and properties added by built-in enhancers like `subscribe`, `useSubscribe`, `snapshot`, and `useSnapshot`.
```tsx
import { create } from '@shined/reactive';
const store = create({ count: 1 });
// Vanilla Store common properties
store.mutate
store.restore
// Properties contributed by enhancers
store.subscribe
store.useSubscribe
store.snapshot
store.useSnapshot
```
--------------------------------
### createVanilla - Create Vanilla JavaScript Store
Source: https://context7.com/sheinsight/reactive/llms.txt
Creates a framework-agnostic reactive store without React dependencies for use in any JavaScript environment. Ideal for vanilla JS or other frameworks.
```APIDOC
## createVanilla - Create Vanilla JavaScript Store
### Description
Creates a framework-agnostic reactive store without React dependencies for use in any JavaScript environment. Ideal for vanilla JS or other frameworks.
### Method
Function Call (not an HTTP endpoint)
### Endpoint
N/A
### Parameters
N/A (This is a function call, not an API endpoint)
### Request Example
```javascript
import { createVanilla } from '@shined/reactive/vanilla'
const store = createVanilla({
temperature: 20,
settings: {
unit: 'celsius',
precision: 1
}
})
const unsubscribe = store.subscribe((changes) => {
console.log(`${changes.propsPath} changed from ${changes.previous} to ${changes.current}`)
document.getElementById('temp').textContent = changes.snapshot.temperature
})
store.mutate.temperature = 25
store.mutate.settings.unit = 'fahrenheit'
const currentState = store.snapshot()
console.log(currentState)
store.restore({ exclude: ['temperature'] })
unsubscribe()
```
### Response
N/A (This is a function call, not an API endpoint)
### Response Example
N/A
```
--------------------------------
### Using `createVanilla` Enhancer for Vanilla JS Stores
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/enhancers/introduction.md
Illustrates the usage of `createVanilla` from `@shined/reactive/vanilla` for creating stores in Vanilla JavaScript environments. It highlights accessing common properties (`mutate`, `restore`) and enhancer-contributed properties (`subscribe`, `snapshot`).
```tsx
import { createVanilla } from '@shined/reactive/vanilla';
const store = createVanilla({ count: 1 });
// Vanilla Store common properties
store.mutate
store.restore
// Properties contributed by enhancers
store.subscribe
store.snapshot
```
--------------------------------
### Create Reactive Store with Hooks for React
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/reference/basic/create.md
Initializes a reactive store for React applications. It accepts an initial state and can be enhanced with built-in functionalities. This is the primary function for setting up state management in a React context.
```tsx
import { create } from '@shined/reactive';
const store = create(initialState);
// Usage example
const store = create({ count: 0});
store.mutate
store.restore()
store.snapshot()
store.useSnapshot()
store.subscribe()
store.useSubscribe()
```
--------------------------------
### Create and Use Singleton Loading Instance (TypeScript)
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/reference/standalone/create-single-loading.md
Demonstrates how to create a singleton loading instance using `createSingleLoading`. It shows how to bind asynchronous functions, access loading state via `useLoading`, and execute asynchronous operations within components using `useAsyncFn`. This utility depends on `@shined/react-use`.
```tsx
import { createSingleLoading } from '@shined/reactive/create-single-loading'
const pageLoading = createSingleLoading(options)
const { set, get, bind, useLoading, useAsyncFn } = pageLoading
// Usage Example
// Create a single loading state
const pageLoading = createSingleLoading({
initialValue: false, // This is the default value
resetOnError: true, // This is the default value
})
// You can use the bind method outside of components to bind asynchronous functions while also binding the single loading state
const fetchDataOutside = pageLoading.bind(async () => {
await new Promise(resolve => setTimeout(resolve, 1000))
throw new Error('error')
})
function App() {
// Use useLoading to get the current loading state
const loading = pageLoading.useLoading()
const fetchFn = pageLoading.useAsyncFn(async () => {
// It also supports using useAsyncFn directly inside components to create asynchronous functions while binding the single loading state
})
return (
{loading &&
Loading...
}
)
}
```
--------------------------------
### State Mutation and Update Functions with @shined/reactive
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/introduction.md
Illustrates the free mutation and safe consumption pattern in @shined/reactive. It shows how to define a store and create functions to mutate specific parts of the state, such as incrementing a counter or updating a user object.
```typescript
export const store = create({
count: 1,
user: { name: 'Bob' }
})
export function increment() {
store.mutate.count++
}
export function updateUser() {
store.mutate.user = { name: 'Alice' }
}
```
--------------------------------
### Create a Reactive Store in Vanilla JS
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/usage/vanilla.md
Initializes a reactive store with a given state object. This store can be global or local. Ensure all APIs are imported from '/vanilla' for Vanilla JavaScript scenarios.
```typescript
import { create } from '@shined/reactive/vanilla'
const store = create({ name: 'Bob' })
```
--------------------------------
### Declare and Access Derived State with `withUseDerived` (TypeScript/React)
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/enhancers/builtins/with-use-derived.md
This snippet demonstrates how to use `withUseDerived` to add derived state properties to a reactive store. It shows how to define derived properties like `doubleCount` and `isHome` based on existing store state. The example illustrates accessing these derived states in both vanilla JavaScript and React using the `useDerived` hook for optimized rendering.
```tsx
import { create, withUseDerived } from '@shined/reactive'
const store = withUseDerived(
create({
count: 0,
tab: 'home' as 'home' | 'about',
}),
(s) => ({
doubleCount: s.count * 2,
isHome: s.tab === 'home',
}),
)
// In Vanilla JS
const isHome = store.derived().isHome
// In React, with rendering optimizations
const { isHome } = store.useDerived()
```
--------------------------------
### Subscribe to Store Changes with createVanilla (TypeScript)
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/enhancers/builtins/with-subscribe.md
This snippet demonstrates how to use the store.subscribe() method provided by the createVanilla utility to listen for and log any changes in the store's state. The subscribe method takes a callback function that receives an object detailing the changes.
```tsx
import { createVanilla } from '@shined/reactive'
const store = createVanilla({ count: 0 })
// Already built in, directly use the subscribe method to subscribe to the store's state changes
store.subscribe((changes) => {
console.log('store changed:', changes)
})
```
--------------------------------
### Create Vanilla JavaScript Store - TypeScript
Source: https://context7.com/sheinsight/reactive/llms.txt
Creates a framework-agnostic reactive store without React dependencies, suitable for any JavaScript environment. This function allows for direct state mutations and subscription to changes. It also supports restoring the state to its initial values, optionally excluding specific keys.
```typescript
import { createVanilla } from '@shined/reactive/vanilla'
// Create vanilla store
const store = createVanilla({
temperature: 20,
settings: {
unit: 'celsius',
precision: 1
}
})
// Subscribe to all changes
const unsubscribe = store.subscribe((changes) => {
console.log(`${changes.propsPath} changed from ${changes.previous} to ${changes.current}`)
// Update UI manually
document.getElementById('temp').textContent = changes.snapshot.temperature
})
// Mutate state directly
store.mutate.temperature = 25
store.mutate.settings.unit = 'fahrenheit'
// Get current state snapshot
const currentState = store.snapshot()
console.log(currentState) // { temperature: 25, settings: { unit: 'fahrenheit', precision: 1 } }
// Restore to initial state, excluding specific keys
store.restore({ exclude: ['temperature'] })
// Now: temperature is 25, but settings is restored to initial values
unsubscribe()
```
--------------------------------
### create - Create React Store with Hooks
Source: https://context7.com/sheinsight/reactive/llms.txt
Creates a reactive store with integrated React hooks for state management and subscriptions. This function is designed for use within React applications.
```APIDOC
## create - Create React Store with Hooks
### Description
Creates a reactive store with integrated React hooks for state management and subscriptions. This function is designed for use within React applications.
### Method
Function Call (not an HTTP endpoint)
### Endpoint
N/A
### Parameters
N/A (This is a function call, not an API endpoint)
### Request Example
```javascript
import { create } from '@shined/reactive'
const store = create({
count: 0,
user: { name: 'John', age: 25 },
items: ['apple', 'banana']
})
function Counter() {
const state = store.useSnapshot()
const count = store.useSnapshot(s => s.count)
const userName = store.useSnapshot(s => s.user.name)
return (
Count: {count}
User: {userName}
)
}
store.mutate.count = 10
store.mutate.user.age = 30
store.mutate.items.push('orange')
const snapshot = store.snapshot()
console.log(snapshot.count)
const unsubscribe = store.subscribe((changes) => {
console.log('Changed path:', changes.propsPath)
console.log('Previous value:', changes.previous)
console.log('Current value:', changes.current)
console.log('Full state:', changes.snapshot)
})
store.restore()
unsubscribe()
```
### Response
N/A (This is a function call, not an API endpoint)
### Response Example
N/A
```
--------------------------------
### Define Reactive Store and Mutations in store.ts
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/usage/react.md
This snippet demonstrates how to create a reactive store using `@shined/reactive` and define methods to mutate its state and fetch asynchronous data. It initializes a store with a 'name' and 'data' property, and provides functions for changing the name and fetching data from an API.
```tsx
import { create, devtools } from '@shined/reactive'
export const store = create({
name: 'Bob',
data: null,
})
// Define a method to change the name
export const changeName = () => {
store.mutate.name = 'Squirtle'
}
// Define a method to fetch data
export const fetchData = async () => {
const data = await fetch('https://api.example.com/data')
store.mutate.data = await data.json()
}
```
--------------------------------
### Create Reactive Store in TypeScript
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/usage/react.md
Defines how to create a reactive store using the `create` API from '@shined/reactive'. The initial state must be a pure object. It's recommended to export the store for external use.
```typescript
import { create } from '@shined/reactive'
// Create a store and specify the initial state, the state needs to be a `Pure Object`
export const store = create({
name: 'Bob',
info: {
age: 18,
hobbies: ['Swimming', 'Running'],
},
})
```
--------------------------------
### VanillaStore Type Definition
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/enhancers/introduction.md
Defines the TypeScript type for VanillaStore, which represents the initial, unenhanced state of a store. It includes `mutate` for state modification and `restore` to reset the state.
```typescript
export type VanillaStore = {
/**
* The mutable state object, whose changes will trigger subscribers.
*/
mutate: State
/**
* Restore to initial state.
*/
restore: () => void
}
```
--------------------------------
### Create Component-Local Reactive State with useReactive (TypeScript)
Source: https://context7.com/sheinsight/reactive/llms.txt
Demonstrates creating and managing component-local reactive state using the `useReactive` hook. It includes handling form inputs, triggering local subscriptions for validation based on state changes, and resetting form fields. Dependencies include `@shined/reactive`.
```typescript
import { useReactive } from '@shined/reactive'
function TodoForm() {
// Create local reactive state
const [state, mutate] = useReactive({
title: '',
description: '',
priority: 'medium',
tags: [],
errors: {}
})
// Local subscription for validation
state.useSubscribe?.((changes) => {
if (changes.propsPath === 'title') {
if (changes.current.length < 3) {
mutate.errors.title = 'Title too short'
} else {
delete mutate.errors.title
}
}
})
const handleSubmit = () => {
if (Object.keys(state.errors).length === 0) {
console.log('Valid form:', state)
// Reset form
mutate.title = ''
mutate.description = ''
mutate.tags = []
}
}
return (
)
}
// Complex local state with derived values
function Calculator() {
const [state, mutate] = useReactive({
a: 0,
b: 0,
operation: 'add'
})
// Compute result
const result = {
add: state.a + state.b,
subtract: state.a - state.b,
multiply: state.a * state.b,
divide: state.b !== 0 ? state.a / state.b : 0
}[state.operation]
return (
)
}
```
--------------------------------
### Illustrate Asynchronous Notification Interruption in React
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/faq.md
Provides a React component that simulates the internal asynchronous notification mechanism of the Reactive library using `Promise.resolve().then()` for state updates. This code helps visualize the input method composition interruption phenomenon.
```tsx
import { useState } from 'react'
export default function App() {
const [state, setState] = useState('')
return (
{
const value = e.target.value
Promise.resolve().then(() => setState(value))
}}
/>
)
}
```
--------------------------------
### Subscribe to Store Changes in Vanilla JS
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/usage/vanilla.md
Sets up a listener to receive notifications whenever the store's state changes. The callback function receives an object detailing the changes, allowing for side effects like syncing data.
```typescript
store.subscribe((changes) => {
// Do something when state changes, for example, sync `config` to disk
console.log(changes)
})
```
--------------------------------
### Subscribe to State Changes with Detailed Notifications
Source: https://context7.com/sheinsight/reactive/llms.txt
The `subscribe` function from `@shined/reactive/vanilla` allows subscribing to state mutations. It provides detailed information about changes, including path, previous and current values, and the complete snapshot. It supports both asynchronous (batched by default) and synchronous notifications.
```typescript
import { createVanilla, subscribe } from '@shined/reactive/vanilla'
const store = createVanilla({
user: {
profile: { name: 'Alice', email: 'alice@example.com' },
settings: { theme: 'dark', notifications: true }
},
lastUpdated: Date.now()
})
// Asynchronous subscription (batched, default)
const unsubAsync = subscribe(
store.mutate,
(changes) => {
console.log('Async update:', {
path: changes.propsPath, // e.g., "user.profile.name"
props: changes.props, // e.g., ['user', 'profile', 'name']
previous: changes.previous, // Previous value
current: changes.current, // New value
snapshot: changes.snapshot // Complete current state
})
// Send analytics
analytics.track('state_change', { path: changes.propsPath })
}
)
// Synchronous subscription (immediate)
const unsubSync = subscribe(
store.mutate,
(changes) => {
// Critical updates that must happen immediately
if (changes.propsPath.includes('settings')) {
applyThemeImmediately(changes.current)
}
},
true // sync = true for immediate notification
)
// Multiple mutations are batched in async mode
store.mutate.user.profile.name = 'Bob'
store.mutate.user.profile.email = 'bob@example.com'
store.mutate.lastUpdated = Date.now()
// Only triggers callback once in next microtask with last mutation
// Set global default for synchronous notifications
import { setGlobalNotifyInSync } from '@shined/reactive/vanilla'
setGlobalNotifyInSync(true) // All future subscriptions default to sync
// Clean up
unsubAsync()
unsubSync()
```
--------------------------------
### Restore Store to Initial State with @shined/reactive
Source: https://context7.com/sheinsight/reactive/llms.txt
Resets a reactive store to its initial state. Supports excluding specific keys from the restoration process. Useful for resetting forms or specific parts of the application state.
```typescript
import { create } from '@shined/reactive'
const store = create({
// User session data
user: { id: 1, name: 'Alice', email: 'alice@example.com' },
// Persistent preferences
preferences: { theme: 'dark', language: 'en' },
// Form data
formData: { title: '', description: '' },
// App state
currentTab: 'home',
notifications: []
})
// User updates state
store.mutate.user.name = 'Bob'
store.mutate.formData.title = 'New Post'
store.mutate.currentTab = 'settings'
store.mutate.notifications.push({ id: 1, text: 'Welcome!' })
// Restore everything to initial state
store.restore()
console.log(store.snapshot())
// All fields back to initial values
// Restore but keep user preferences
store.mutate.preferences.theme = 'light'
store.mutate.user.name = 'Charlie'
store.restore({ exclude: ['preferences'] })
console.log(store.snapshot())
// user, formData, currentTab, notifications reset
// preferences.theme remains 'light'
// Common pattern: Reset form while keeping user session
function handleFormCancel() {
store.restore({
exclude: ['user', 'preferences']
})
}
// Reset multiple independent stores
const uiStore = create({ sidebar: 'open', modal: null })
const dataStore = create({ items: [], filter: 'all' })
function handleLogout() {
uiStore.restore()
dataStore.restore()
// All stores reset to initial state
}
```
--------------------------------
### Subscribe to Store Changes with useSubscribe in React
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/reference/internal/use-subscribe.md
This snippet demonstrates how to use the `useSubscribe` hook from the `@shined/reactive` library to subscribe to changes in a store. The hook takes the store, a listener function, and optional configuration. The listener function can optionally receive the detected changes as an argument. The `sync: true` option ensures synchronous execution of the listener.
```tsx
import { useSubscribe } from '@shined/reactive'
useSnapshot(proxyState, listener, options?);
// Usage example
useSubscribe(store.mutate, () => {
console.log('Store has changed');
});
useSubscribe(store.mutate, changes => {
console.log('Store has changed', changes);
});
useSubscribe(store.mutate, () => {
console.log('Store has changed');
}, { sync: true });
```
--------------------------------
### Synchronous State Updates for Input Elements in React
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/faq.md
Demonstrates how to use `store.useSnapshot` with the `sync: true` option to ensure synchronous state updates, preventing conflicts with input method composition events in React. This is crucial for a smooth user experience when typing in input fields.
```tsx
const store = create({ inputValue: '' })
const updateInputValue = (value: string) => {
store.mutate.inputValue = value
}
function App() {
// Note that sync: true is used here to notify changes synchronously, avoiding input method composition interruption
const inputValue = store.useSnapshot((s) => s.inputValue, { sync: true })
return (
{
updateInputValue(e.target.value)
}}
/>
)
}
```
--------------------------------
### Create Global Loading State with createSingleLoading (TypeScript)
Source: https://context7.com/sheinsight/reactive/llms.txt
Manages a single global loading state for asynchronous operations. It offers automatic lifecycle management, hooks for React components, and direct control for vanilla JS/TS. Key options include 'initialValue' and 'resetOnError'.
```typescript
import { createSingleLoading } from '@shined/reactive/create-single-loading'
// Create loading state instance
const globalLoading = createSingleLoading({
initialValue: false,
resetOnError: true // Reset to false on error
})
// React component with async operation
function SubmitForm() {
const [formData, setFormData] = useState({ email: '' })
// Hook provides loading state and async function wrapper
const { execute, loading } = globalLoading.useAsyncFn(async () => {
const response = await fetch('/api/submit', {
method: 'POST',
body: JSON.stringify(formData)
})
if (!response.ok) throw new Error('Submission failed')
return response.json()
})
return (
)
}
// Multiple components share the same loading state
function LoadingIndicator() {
const isLoading = globalLoading.useLoading()
return isLoading ? : null
}
// Vanilla JS/TS usage
async function fetchData() {
// Manual control
globalLoading.set(true)
try {
const data = await fetch('/api/data').then(r => r.json())
return data
} finally {
globalLoading.set(false)
}
}
// Or bind function for automatic loading management
const fetchDataWithLoading = globalLoading.bind(async () => {
const data = await fetch('/api/data').then(r => r.json())
return data
})
// Call bound function - loading automatically managed
await fetchDataWithLoading()
// Check loading state in JS
if (globalLoading.get()) {
console.log('Something is loading...')
}
// Multiple async operations - last one controls loading state
const api = {
login: globalLoading.bind(async (creds) => { /* ... */ }),
logout: globalLoading.bind(async () => { /* ... */ }),
refresh: globalLoading.bind(async () => { /* ... */ })
}
```
--------------------------------
### Enable Redux DevTools for Reactive Stores
Source: https://context7.com/sheinsight/reactive/llms.txt
Integrates Redux DevTools with @shined/reactive stores for advanced debugging capabilities. It allows for state inspection, action tracking, and time-travel debugging. Options include naming stores, enabling/disabling the feature, setting max action history, and enabling trace logging. This functionality is particularly useful for complex state management scenarios.
```typescript
import { create, devtools } from '@shined/reactive'
const store = create({
count: 0,
history: []
})
// Enable devtools with options
const cleanup = devtools(store, {
name: 'Counter Store',
enable: true, // Toggle devtools on/off
maxAge: 50, // Max number of actions to keep
trace: true, // Enable stack trace
traceLimit: 25
})
// All mutations are tracked in Redux DevTools
store.mutate.count++ // Action: [set] count
store.mutate.history.push('incremented') // Action: [replace] history
// Example with multiple stores
const userStore = create({ name: 'Admin', role: 'admin' })
const uiStore = create({ sidebar: 'open', theme: 'dark' })
const cleanupUser = devtools(userStore, { name: 'User Store' })
const cleanupUI = devtools(uiStore, { name: 'UI Store' })
// Clean up when done
cleanup()
cleanupUser()
cleanupUI()
// Conditional devtools (only in development)
if (process.env.NODE_ENV === 'development') {
devtools(store, { name: 'Dev Store' })
}
```
--------------------------------
### Use Reactive Store and Mutations in React Component (app.ts)
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/usage/react.md
This snippet shows how to integrate the reactive store defined in 'store.ts' into a React component. It uses `store.useSnapshot` to subscribe to state changes and `useAsyncFn` from '@shined/react-use' to manage the asynchronous data fetching. Buttons are provided to trigger the `changeName` and `fetchData` functions.
```tsx
import { useAsyncFn } from '@shined/react-use'
import { store, changeName, fetchData } from './store'
export default function App() {
const [name, data] = store.useSnapshot((s) => [s.name, s.data] as const)
const fetchDataFn = useAsyncFn(fetchData)
return (
Name: {name}, Data: {JSON.stringify(data)}
)
}
```
--------------------------------
### Restore Reactive Store to Initial State in Vanilla JS
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/usage/vanilla.md
Resets the store to its original state using the `store.restore()` method. This function utilizes the `structuredClone` API and may require a polyfill for older environments.
```typescript
store.restore()
```
--------------------------------
### Create React Store with Hooks - TypeScript
Source: https://context7.com/sheinsight/reactive/llms.txt
Creates a reactive store with integrated React hooks for state management and subscriptions. This function allows for automatic change tracking and optimized re-renders in React components using selectors. It supports direct mutations, immutable snapshots, subscribing to changes, and restoring to initial state.
```typescript
import { create } from '@shined/reactive'
// Create store with initial state
const store = create({
count: 0,
user: { name: 'John', age: 25 },
items: ['apple', 'banana']
})
// React component using the store
function Counter() {
// Subscribe to entire state
const state = store.useSnapshot()
// Or use selector for optimized re-renders (only re-renders when count changes)
const count = store.useSnapshot(s => s.count)
const userName = store.useSnapshot(s => s.user.name)
return (
Count: {count}
User: {userName}
)
}
// Direct mutations outside components
store.mutate.count = 10
store.mutate.user.age = 30
store.mutate.items.push('orange')
// Get immutable snapshot
const snapshot = store.snapshot()
console.log(snapshot.count) // 10
// Subscribe to changes
const unsubscribe = store.subscribe((changes) => {
console.log('Changed path:', changes.propsPath)
console.log('Previous value:', changes.previous)
console.log('Current value:', changes.current)
console.log('Full state:', changes.snapshot)
})
// Restore to initial state
store.restore()
// Clean up
unsubscribe()
```
--------------------------------
### Subscribe to Store Changes
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/reference/basic/create.md
Allows subscribing to changes in the store's state. The `withSubscribe` enhancer must be enabled. A listener callback is executed on state changes. An optional selector can filter which changes trigger the listener. Returns an unsubscribe function.
```tsx
store.subscribe(listener, notifyInSync?, selector?);
// Usage example
store.subscribe(() => {
console.log(store.snapshot());
});
const unsubscribe = store.subscribe(() => {
console.log(store.snapshot());
}, true);
// Unsubscribe
unsubscribe()
```
--------------------------------
### React Hook for State Subscription with useSnapshot
Source: https://context7.com/sheinsight/reactive/llms.txt
The `useSnapshot` hook from `@shined/reactive` allows React components to subscribe to store changes. It supports full state subscription or optimized re-renders using selectors and custom equality functions. It also handles synchronous updates for specific use cases like input fields.
```typescript
import { create } from '@shined/reactive'
const store = create({
todos: [
{ id: 1, text: 'Learn React', completed: false },
{ id: 2, text: 'Use Reactive', completed: true }
],
filter: 'all'
})
function TodoList() {
// Full state subscription - re-renders on any change
const state = store.useSnapshot()
// Optimized: only re-renders when todos array changes
const todos = store.useSnapshot(s => s.todos)
// Optimized: only re-renders when filter changes
const filter = store.useSnapshot(s => s.filter)
// Derived value with memoization
const activeTodos = store.useSnapshot(s =>
s.todos.filter(t => !t.completed)
)
// Custom equality function for deep comparison
const firstTodo = store.useSnapshot(
s => s.todos[0],
{ isEqual: (a, b) => a?.id === b?.id && a?.text === b?.text }
)
// Synchronous updates (useful for input fields with IME)
const filterSync = store.useSnapshot(s => s.filter, { sync: true })
return (
)
}
```
--------------------------------
### Restore Reactive Store to Initial State in React Component
Source: https://github.com/sheinsight/reactive/blob/main/docs/en/guide/usage/react.md
This snippet illustrates how to restore the reactive store to its initial state within a React component. It utilizes the `useUnmount` hook from '@shined/react-use' to automatically call `store.restore()` when the component unmounts, and a button is provided for manual state reset.
```tsx
import { useUnmount } from '@shined/react-use'
import { store } from './store'
export default function App() {
useUnmount(store.restore)
return (
)
}
```
--------------------------------
### Immutable Updates with Produce Function in @shined/reactive/vanilla
Source: https://context7.com/sheinsight/reactive/llms.txt
Enables immutable state updates by creating a mutable draft of the current state. Changes are made to the draft, and a new immutable snapshot is returned without altering the original state. Useful for complex updates, previews, and time-travel functionality.
```typescript
import { createVanilla, produce } from '@shined/reactive/vanilla'
const store = createVanilla({
todos: [
{ id: 1, text: 'Learn Reactive', completed: false },
{ id: 2, text: 'Build App', completed: false }
],
metadata: { lastUpdated: Date.now(), version: 1 }
})
// Use produce for immutable updates
const newSnapshot = produce(store.mutate, (draft) => {
// Mutate draft freely
draft.todos[0].completed = true
draft.todos.push({ id: 3, text: 'Deploy', completed: false })
draft.metadata.lastUpdated = Date.now()
draft.metadata.version++
})
console.log(newSnapshot)
// Returns new immutable state snapshot
// Original store.mutate is unchanged
// Pattern: compute next state without committing
function previewStateChange() {
const preview = produce(store.mutate, (draft) => {
draft.todos.forEach(todo => todo.completed = true)
})
// Show preview to user
displayPreview(preview)
// Don't apply changes yet
}
// Pattern: validate then apply
function updateWithValidation(updates) {
const next = produce(store.mutate, (draft) => {
Object.assign(draft, updates)
})
if (isValid(next)) {
// Apply changes by assigning to store
Object.assign(store.mutate, next)
} else {
console.error('Invalid state')
}
}
// Pattern: time-travel / undo-redo
const history = []
function makeChange() {
// Save current state
history.push(produce(store.mutate, s => s))
// Make changes
store.mutate.todos.push({ id: 4, text: 'New Todo', completed: false })
}
function undo() {
if (history.length > 0) {
const previous = history.pop()
Object.assign(store.mutate, previous)
}
}
```