{"version":3,"file":"createStore.mjs","sources":["../../../../src/lib/state/core/createStore.ts"],"sourcesContent":["/**\n * @file Store Factory\n * @description Creates Zustand stores with production-grade middleware stack:\n *              Immer + DevTools + SubscribeWithSelector + Persist\n */\n\nimport { create, type StateCreator } from 'zustand';\nimport { devtools, subscribeWithSelector, persist } from 'zustand/middleware';\nimport { immer } from 'zustand/middleware/immer';\nimport type { HydrationState, ResetState } from './types';\n\n// ============================================================================\n// Store Configuration\n// ============================================================================\n\n/**\n * App store configuration options\n */\nexport interface AppStoreConfig<TState> {\n  /** Store name for DevTools */\n  name: string;\n  /** Persistence configuration */\n  persist?: {\n    /** Storage key */\n    key: string;\n    /** State to persist (whitelist) */\n    partialize?: (state: TState) => Partial<TState>;\n    /** Storage version for migrations */\n    version?: number;\n    /** Migration functions */\n    migrate?: (persistedState: unknown, version: number) => TState;\n    /** Skip hydration */\n    skipHydration?: boolean;\n  };\n  /** Enable DevTools (default: true in dev) */\n  devtools?: boolean;\n  /** Custom DevTools options */\n  devtoolsOptions?: {\n    enabled?: boolean;\n    anonymousActionType?: string;\n    trace?: boolean;\n    traceLimit?: number;\n  };\n}\n\n// ============================================================================\n// Type Definitions\n// ============================================================================\n\n/**\n * Full middleware stack type for proper inference\n */\ntype FullMiddleware = [\n  ['zustand/immer', never],\n  ['zustand/devtools', never],\n  ['zustand/subscribeWithSelector', never],\n  ['zustand/persist', unknown],\n];\n\n/**\n * Middleware stack without persistence\n */\ntype NoPersistMiddleware = [\n  ['zustand/immer', never],\n  ['zustand/devtools', never],\n  ['zustand/subscribeWithSelector', never],\n];\n\n// ============================================================================\n// Store Factory\n// ============================================================================\n\n/**\n * Create a type-safe Zustand store with all middleware\n *\n * Middleware order (inside-out):\n * 1. immer - Enables immutable updates with mutable syntax\n * 2. devtools - Redux DevTools integration with action names\n * 3. subscribeWithSelector - Granular subscriptions for performance\n * 4. persist - Optional state persistence to localStorage\n *\n * @example\n * ```typescript\n * const useStore = createAppStore(\n *   (set, get) => ({\n *     count: 0,\n *     increment: () => set((state) => { state.count += 1 }, false, { type: 'increment' }),\n *   }),\n *   { name: 'CounterStore' }\n * );\n * ```\n */\nexport function createAppStore<TState extends object>(\n  initializer: StateCreator<TState & HydrationState & ResetState, FullMiddleware, [], TState>,\n  config: AppStoreConfig<TState>\n): ReturnType<typeof create<TState & HydrationState & ResetState>> {\n  const {\n    name,\n    persist: persistConfig,\n    devtools: enableDevtools = process.env['NODE_ENV'] === 'development',\n    devtoolsOptions = {},\n  } = config;\n\n  // Build initial state reference for reset\n  let initialState: TState | null = null;\n\n  const storeCreator: StateCreator<TState & HydrationState & ResetState, FullMiddleware> = (\n    set,\n    get,\n    api\n  ) => {\n    const sliceState = initializer(set, get, api);\n\n    // Capture initial state for reset capability\n    initialState = { ...sliceState };\n\n    return {\n      ...sliceState,\n\n      // Hydration tracking\n      _hasHydrated: !persistConfig,\n      _setHasHydrated: (hydrated: boolean) => {\n        set(\n          (state) => {\n            state._hasHydrated = hydrated;\n          },\n          false,\n          { type: '@@HYDRATION/SET_HYDRATED' }\n        );\n      },\n\n      // Reset capability for logout/clear\n      _reset: () => {\n        if (initialState) {\n          set(() => ({ ...initialState }) as TState & HydrationState & ResetState, true, {\n            type: '@@RESET/STORE',\n          });\n        }\n      },\n    };\n  };\n\n  // Apply middleware in correct order (inside-out)\n  // immer -> devtools -> subscribeWithSelector -> persist\n  if (persistConfig !== undefined) {\n    return create<TState & HydrationState & ResetState>()(\n      immer(\n        devtools(\n          subscribeWithSelector(\n            persist(storeCreator, {\n              name: persistConfig.key,\n              partialize: persistConfig.partialize as unknown as (\n                state: TState & HydrationState & ResetState\n              ) => Partial<TState & HydrationState & ResetState>,\n              version: persistConfig.version ?? 1,\n              migrate: persistConfig.migrate as unknown as (\n                persistedState: unknown,\n                version: number\n              ) => TState & HydrationState & ResetState,\n              skipHydration: persistConfig.skipHydration ?? false,\n              onRehydrateStorage: () => (state) => {\n                state?._setHasHydrated(true);\n              },\n            })\n          ),\n          {\n            name,\n            enabled: enableDevtools,\n            ...devtoolsOptions,\n          }\n        )\n      )\n    ) as unknown as ReturnType<typeof create<TState & HydrationState & ResetState>>;\n  }\n\n  // Without persistence - simpler middleware stack\n  return create<TState & HydrationState & ResetState>()(\n    immer(\n      devtools(\n        subscribeWithSelector(\n          storeCreator as unknown as StateCreator<\n            TState & HydrationState & ResetState,\n            NoPersistMiddleware\n          >\n        ),\n        {\n          name,\n          enabled: enableDevtools,\n          ...devtoolsOptions,\n        }\n      )\n    )\n  ) as unknown as ReturnType<typeof create<TState & HydrationState & ResetState>>;\n}\n\n// ============================================================================\n// Simple Store Factory (No Persistence)\n// ============================================================================\n\n/**\n * Create a simple Zustand store with Immer and DevTools\n * Use this for stores that don't need persistence\n *\n * @example\n * ```typescript\n * const useUIStore = createSimpleStore(\n *   (set) => ({\n *     isOpen: false,\n *     toggle: () => set((state) => { state.isOpen = !state.isOpen }, false, { type: 'toggle' }),\n *   }),\n *   'UIStore'\n * );\n * ```\n */\nexport function createSimpleStore<TState extends object>(\n  initializer: StateCreator<\n    TState,\n    [['zustand/immer', never], ['zustand/devtools', never]],\n    [],\n    TState\n  >,\n  name: string,\n  enableDevtools = process.env['NODE_ENV'] === 'development'\n): ReturnType<typeof create<TState>> {\n  return create<TState>()(\n    immer(\n      devtools(initializer, {\n        name,\n        enabled: enableDevtools,\n      })\n    )\n  ) as ReturnType<typeof create<TState>>;\n}\n\n// ============================================================================\n// Minimal Store Factory\n// ============================================================================\n\n/**\n * Create a minimal Zustand store with just Immer\n * Use this for simple local stores\n *\n * @example\n * ```typescript\n * const useLocalStore = createMinimalStore((set) => ({\n *   items: [],\n *   addItem: (item) => set((state) => { state.items.push(item) }),\n * }));\n * ```\n */\nexport function createMinimalStore<TState extends object>(\n  initializer: StateCreator<TState, [['zustand/immer', never]], [], TState>\n): ReturnType<typeof create<TState>> {\n  return create<TState>()(immer(initializer)) as ReturnType<typeof create<TState>>;\n}\n\n// ============================================================================\n// Store Utilities\n// ============================================================================\n\n/**\n * Wait for store hydration to complete\n */\nexport async function waitForHydration<TState extends HydrationState>(store: {\n  getState: () => TState;\n  subscribe: (\n    selector: (state: TState) => boolean,\n    callback: (value: boolean) => void\n  ) => () => void;\n}): Promise<void> {\n  return new Promise((resolve) => {\n    if (store.getState()._hasHydrated) {\n      resolve();\n      return;\n    }\n\n    const unsubscribe = store.subscribe(\n      (state) => state._hasHydrated,\n      (hydrated) => {\n        if (hydrated) {\n          unsubscribe();\n          resolve();\n        }\n      }\n    ) as () => void;\n  });\n}\n\n/**\n * Create a reset function for a store\n */\nexport function createStoreReset<TState extends ResetState>(store: {\n  getState: () => TState;\n}): () => void {\n  return () => {\n    store.getState()._reset();\n  };\n}\n"],"names":["createAppStore","initializer","config","name","persistConfig","enableDevtools","devtoolsOptions","initialState","storeCreator","set","get","api","sliceState","hydrated","state","create","immer","devtools","subscribeWithSelector","persist","createSimpleStore","createMinimalStore","createStoreReset","store"],"mappings":";;;AA4FO,SAASA,EACdC,GACAC,GACiE;AACjE,QAAM;AAAA,IACJ,MAAAC;AAAA,IACA,SAASC;AAAA,IACT,UAAUC,IAAiB,QAAQ,IAAI,aAAgB;AAAA,IACvD,iBAAAC,IAAkB,CAAA;AAAA,EAAC,IACjBJ;AAGJ,MAAIK,IAA8B;AAElC,QAAMC,IAAmF,CACvFC,GACAC,GACAC,MACG;AACH,UAAMC,IAAaX,EAAYQ,GAAKC,GAAKC,CAAG;AAG5C,WAAAJ,IAAe,EAAE,GAAGK,EAAA,GAEb;AAAA,MACL,GAAGA;AAAA;AAAA,MAGH,cAAc,CAACR;AAAA,MACf,iBAAiB,CAACS,MAAsB;AACtC,QAAAJ;AAAA,UACE,CAACK,MAAU;AACT,YAAAA,EAAM,eAAeD;AAAA,UACvB;AAAA,UACA;AAAA,UACA,EAAE,MAAM,2BAAA;AAAA,QAA2B;AAAA,MAEvC;AAAA;AAAA,MAGA,QAAQ,MAAM;AACZ,QAAIN,KACFE,EAAI,OAAO,EAAE,GAAGF,EAAA,IAAyD,IAAM;AAAA,UAC7E,MAAM;AAAA,QAAA,CACP;AAAA,MAEL;AAAA,IAAA;AAAA,EAEJ;AAIA,SAAIH,MAAkB,SACbW,EAAA;AAAA,IACLC;AAAA,MACEC;AAAA,QACEC;AAAA,UACEC,EAAQX,GAAc;AAAA,YACpB,MAAMJ,EAAc;AAAA,YACpB,YAAYA,EAAc;AAAA,YAG1B,SAASA,EAAc,WAAW;AAAA,YAClC,SAASA,EAAc;AAAA,YAIvB,eAAeA,EAAc,iBAAiB;AAAA,YAC9C,oBAAoB,MAAM,CAACU,MAAU;AACnC,cAAAA,GAAO,gBAAgB,EAAI;AAAA,YAC7B;AAAA,UAAA,CACD;AAAA,QAAA;AAAA,QAEH;AAAA,UACE,MAAAX;AAAA,UACA,SAASE;AAAA,UACT,GAAGC;AAAA,QAAA;AAAA,MACL;AAAA,IACF;AAAA,EACF,IAKGS,EAAA;AAAA,IACLC;AAAA,MACEC;AAAA,QACEC;AAAA,UACEV;AAAA,QAAA;AAAA,QAKF;AAAA,UACE,MAAAL;AAAA,UACA,SAASE;AAAA,UACT,GAAGC;AAAA,QAAA;AAAA,MACL;AAAA,IACF;AAAA,EACF;AAEJ;AAqBO,SAASc,EACdnB,GAMAE,GACAE,IAAiB,QAAQ,IAAI,aAAgB,eACV;AACnC,SAAOU,EAAA;AAAA,IACLC;AAAA,MACEC,EAAShB,GAAa;AAAA,QACpB,MAAAE;AAAA,QACA,SAASE;AAAA,MAAA,CACV;AAAA,IAAA;AAAA,EACH;AAEJ;AAkBO,SAASgB,EACdpB,GACmC;AACnC,SAAOc,EAAA,EAAiBC,EAAMf,CAAW,CAAC;AAC5C;AAqCO,SAASqB,EAA4CC,GAE7C;AACb,SAAO,MAAM;AACX,IAAAA,EAAM,SAAA,EAAW,OAAA;AAAA,EACnB;AACF;"}