or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

docs

index.md
tile.json

tessl/npm-tanstack--query-sync-storage-persister

A persister for synchronous storages, to be used with TanStack/Query

Workspace
tessl
Visibility
Public
Created
Last updated
Describes
npmpkg:npm/@tanstack/query-sync-storage-persister@5.86.x

To install, run

npx @tessl/cli install tessl/npm-tanstack--query-sync-storage-persister@5.86.0

index.mddocs/

TanStack Query Sync Storage Persister

TanStack Query Sync Storage Persister provides a synchronous storage persister for TanStack Query that enables caching and persistence of query data to synchronous storage systems like localStorage or sessionStorage. It implements throttled persistence with configurable serialization, retry logic, and error handling.

Package Information

  • Package Name: @tanstack/query-sync-storage-persister
  • Package Type: npm
  • Language: TypeScript
  • Installation: npm install @tanstack/query-sync-storage-persister

Core Imports

import { createSyncStoragePersister } from "@tanstack/query-sync-storage-persister";

For CommonJS:

const { createSyncStoragePersister } = require("@tanstack/query-sync-storage-persister");

Basic Usage

import { createSyncStoragePersister } from "@tanstack/query-sync-storage-persister";
import { persistQueryClient } from "@tanstack/query-persist-client-core";
import { QueryClient } from "@tanstack/query-core";

// Create a query client
const queryClient = new QueryClient();

// Create a persister with localStorage (uses default key 'REACT_QUERY_OFFLINE_CACHE')
const persister = createSyncStoragePersister({
  storage: window.localStorage,
  throttleTime: 2000, // Throttle saves to 2 seconds
});

// Setup persistence
persistQueryClient({
  queryClient,
  persister,
  buster: "v1.0", // Cache buster string
});

Architecture

The package provides a single main export that creates a Persister object compatible with TanStack Query's persistence system:

  • Throttled Persistence: Automatically throttles storage operations to prevent excessive writes
  • Error Handling: Built-in retry mechanisms with configurable retry strategies
  • Serialization: Configurable serialization/deserialization for storage compatibility
  • Graceful Fallbacks: Returns no-op functions when storage is unavailable

Capabilities

Sync Storage Persister Creation

Creates a synchronous storage persister for TanStack Query persistence.

/**
 * @deprecated use `createAsyncStoragePersister` from `@tanstack/query-async-storage-persister` instead.
 */
function createSyncStoragePersister(
  options: CreateSyncStoragePersisterOptions
): Persister;

interface CreateSyncStoragePersisterOptions {
  /** The storage client used for setting and retrieving items from cache.
   * For SSR pass in `undefined`. Note that window.localStorage can be
   * `null` in Android WebViews depending on how they are configured.
   */
  storage: Storage | undefined | null;
  /** The key to use when storing the cache */
  key?: string;
  /** To avoid spamming,
   * pass a time in ms to throttle saving the cache to disk */
  throttleTime?: number;
  /**
   * How to serialize the data to storage.
   * @default `JSON.stringify`
   */
  serialize?: (client: PersistedClient) => string;
  /**
   * How to deserialize the data from storage.
   * @default `JSON.parse`
   */
  deserialize?: (cachedString: string) => PersistedClient;
  /** Retry strategy for handling storage errors */
  retry?: PersistRetryer;
}

Usage Examples:

import { createSyncStoragePersister } from "@tanstack/query-sync-storage-persister";
import { removeOldestQuery } from "@tanstack/query-persist-client-core";

// Basic usage with localStorage
const persister = createSyncStoragePersister({
  storage: window.localStorage,
});

// Custom configuration
const customPersister = createSyncStoragePersister({
  storage: window.sessionStorage,
  key: "custom-app-cache",
  throttleTime: 5000, // 5 second throttle
  serialize: (data) => JSON.stringify(data, null, 2),
  deserialize: (str) => JSON.parse(str),
  retry: removeOldestQuery, // Remove oldest queries when storage is full
});

// Server-side rendering safe (no storage)
const ssrPersister = createSyncStoragePersister({
  storage: undefined, // Returns no-op functions
});

Types

interface Storage {
  getItem: (key: string) => string | null;
  setItem: (key: string, value: string) => void;
  removeItem: (key: string) => void;
}

interface Persister {
  persistClient: (persistClient: PersistedClient) => Promisable<void>;
  restoreClient: () => Promisable<PersistedClient | undefined>;
  removeClient: () => Promisable<void>;
}

interface PersistedClient {
  timestamp: number;
  buster: string;
  clientState: DehydratedState;
}

type PersistRetryer = (props: {
  persistedClient: PersistedClient;
  error: Error;
  errorCount: number;
}) => PersistedClient | undefined;

type Promisable<T> = T | PromiseLike<T>;

// Imported from @tanstack/query-core
interface DehydratedState {
  mutations: Array<any>;
  queries: Array<any>;
}

Error Handling

When storage operations fail, the persister uses the configured retry strategy:

import { removeOldestQuery } from "@tanstack/query-persist-client-core";

const persister = createSyncStoragePersister({
  storage: window.localStorage,
  retry: removeOldestQuery, // Removes oldest cached queries when storage is full
});

If no retry strategy is provided and storage fails, the operation is silently ignored. When storage is not available (SSR, private browsing, etc.), the persister returns no-op functions that safely do nothing.

Common Use Cases

Browser Persistence

// Persist to localStorage with custom settings
const persister = createSyncStoragePersister({
  storage: window.localStorage,
  key: "my-app-v1.2",
  throttleTime: 1000,
});

Storage Full Handling

import { removeOldestQuery } from "@tanstack/query-persist-client-core";

// Handle storage quota exceeded errors
const persister = createSyncStoragePersister({
  storage: window.localStorage,
  retry: removeOldestQuery, // Remove old queries when storage is full
});

Custom Serialization

// Custom serialization for complex data types
const persister = createSyncStoragePersister({
  storage: window.localStorage,
  serialize: (data) => {
    // Custom serialization logic
    return JSON.stringify(data, (key, value) => {
      if (value instanceof Date) {
        return { __type: 'Date', value: value.toISOString() };
      }
      return value;
    });
  },
  deserialize: (str) => {
    // Custom deserialization logic
    return JSON.parse(str, (key, value) => {
      if (value && value.__type === 'Date') {
        return new Date(value.value);
      }
      return value;
    });
  },
});