import { serialize, type Scope } from "effector";


serialize(scope, params)

A companion method for fork. It allows us to get a serialized value for all the store states within a scope. The main purpose is an application state serialization on the server side during SSR.


Babel plugin or SWC plugin is required for using this method, as these plugins provide the SIDs for stores, which are required for stable state serialization.

You can find deep-dive explanation here


serialize(scope: Scope, { ignore?: Array<Store<any>>; onlyChanges?: boolean }): {[sid: string]: any}


  1. scope Scope: a scope object (forked instance)
  2. ignore Optional array of Store to be omitted during serialization (added 20.14.0)
  3. onlyChanges Optional boolean flag to ignore stores which didn’t change in fork (prevent default values from being carried over network)

Since effector 23.0.0 property onlyChanges is deprecated.


An object with store values using sids as a keys


If a store does not have a sid, its value will be omitted during serialization.


Serialize forked instance state

import { createDomain, fork, serialize } from "effector";

const domain = createDomain();
const $store = domain.createStore(42);
const scope = fork(domain);

console.log(serialize(scope)); // => {[sid]: 42}

Try it

Using with onlyChanges

With onlyChanges, this method will serialize only stores which were changed by some trigger during work or defined in values field by fork or hydrate(scope). Once being changed, a store will stay marked as changed in given scope even if it was turned back to the default state during work, otherwise client will not update that store on its side, which is unexpected and inconsistent. This allows us to hydrate client state several times, for example, during route changes in next.js

import { createDomain, fork, serialize, hydrate } from "effector";

const app = createDomain();

/** store which we want to hydrate by server */
const $title = app.createStore("dashboard");

/** store which is not used by server */
const $clientTheme = app.createStore("light");

/** scope in client app */
const clientScope = fork(app, {
  values: new Map([
    [$clientTheme, "dark"],
    [$title, "profile"],

/** server side scope of chats page created for each request */
const chatsPageScope = fork(app, {
  values: new Map([[$title, "chats"]]),

/** this object will contain only $title data
 * as $clientTheme never changed in server scope */
const chatsPageData = serialize(chatsPageScope, { onlyChanges: true });
// => {'-l644hw': 'chats'}

/** thereby, filling values from a server will touch only relevant stores */
hydrate(clientScope, { values: chatsPageData });

// => dark

Try it