UNPKG

supastash

Version:

Offline-first sync engine for Supabase in React Native using SQLite

124 lines (123 loc) 4.44 kB
let _config = { dbName: "supastash_db", supabaseClient: null, sqliteClient: null, sqliteClientType: null, excludeTables: { pull: [], push: [] }, pollingInterval: { pull: 30000, push: 30000, }, syncEngine: { push: true, pull: true, useFiltersFromStore: true, }, listeners: 250, debugMode: true, }; let _configured = false; /** * Initializes the Supastash client. * * This must be called **once** during app startup (e.g., in `_layout.tsx` or `App.tsx`) * before using any Supastash hooks or features. * * ⚠️ Pull sync is **disabled by default** to avoid unfiltered data fetches. * Enable it only if you've configured **Row Level Security (RLS)** on your Supabase tables. * The `useSupatashData` hook always performs filtered pull queries when `filter` is provided in the `options`, making it safe to use even when pull is disabled globally. * * @example * import { supabase } from "./supabase"; * import { openDatabaseAsync } from "expo-sqlite"; * import { configureSupastash, defineLocalSchema } from "supastash"; * * configureSupastash({ * dbName: "supastash_db", * supabaseClient: supabase, * sqliteClient: { openDatabaseAsync }, * sqliteClientType: "expo", * onSchemaInit: () => { * defineLocalSchema("users", { * id: "TEXT PRIMARY KEY", * name: "TEXT", * email: "TEXT", * created_at: "TIMESTAMP DEFAULT CURRENT_TIMESTAMP", * updated_at: "TIMESTAMP DEFAULT CURRENT_TIMESTAMP", * }); * }, * }); * * @param config - Configuration options for Supastash * @param config.dbName - SQLite database name (default: `"supastash_db"`) * @param config.supabaseClient - Supabase client instance (**required**) * @param config.sqliteClient - SQLite client adapter (**required**) * @param config.sqliteClientType - SQLite engine: `"expo" | "rn-storage" | "rn-nitro"` (**required**) * @param config.onSchemaInit - Optional callback to define local table schemas * @param config.debugMode - Enables debug logging (default: `false`) * @param config.listeners - Max number of active Realtime subscriptions (default: `250`) * @param config.excludeTables - Tables to exclude from sync (default: `{ pull: [], push: [] }`) * @param config.pollingInterval - Polling interval for sync (default: `{ pull: 30000, push: 30000 }`) * @param config.syncEngine - Control pull/push sync behavior (`push: true`, `pull: false` by default, `useFiltersFromStore: true` by default) */ export function configureSupastash(config) { _config = { ..._config, ...config, syncEngine: { ..._config.syncEngine, ...config.syncEngine, }, excludeTables: { pull: config.excludeTables?.pull ?? _config.excludeTables?.pull ?? [], push: config.excludeTables?.push ?? _config.excludeTables?.push ?? [], }, pollingInterval: { pull: config.pollingInterval?.pull ?? _config.pollingInterval?.pull ?? 30000, push: config.pollingInterval?.push ?? _config.pollingInterval?.push ?? 30000, }, }; _configured = true; } /** * Returns the current Supastash configuration. * * Throws an error if `configureSupastash` has not been called. * * @returns {SupastashConfig<T>} The active Supastash configuration * * @throws Will throw if Supastash is not configured or if essential values like * `supabaseClient` or `sqliteClient` are missing. * * @example * const config = getSupastashConfig(); * const dbName = config.dbName; */ export function getSupastashConfig() { return _config; } /** * Wrapper for `configureSupastash` that takes a strongly typed object containing * the Supastash config, including optional schema initialization. * * Useful for abstracting config logic into a central setup file. * * @param config.dbOptions - The Supastash configuration object * @param config.dbOptions.onSchemaInit - Optional callback to define the local schema * * @example * defineSupastashConfig({ * dbOptions: { * dbName: "supastash_db", * supabaseClient, * sqliteClient, * sqliteClientType: "expo", * onSchemaInit: () => { * defineLocalSchema("orders", { id: "TEXT PRIMARY KEY", status: "TEXT" }); * }, * }, * }); */ export function defineSupastashConfig(config) { configureSupastash(config.dbOptions); }