@blac/core 2.0.0-rc-14 → 2.0.0-rc.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (162) hide show
  1. package/dist/.tsbuildinfo +1 -0
  2. package/dist/Blac.d.ts +246 -0
  3. package/dist/Blac.d.ts.map +1 -0
  4. package/dist/Blac.js +625 -0
  5. package/dist/Blac.js.map +1 -0
  6. package/dist/Bloc.d.ts +41 -0
  7. package/dist/Bloc.d.ts.map +1 -0
  8. package/dist/Bloc.js +140 -0
  9. package/dist/Bloc.js.map +1 -0
  10. package/dist/BlocBase.d.ts +110 -0
  11. package/dist/BlocBase.d.ts.map +1 -0
  12. package/dist/BlocBase.js +287 -0
  13. package/dist/BlocBase.js.map +1 -0
  14. package/dist/Cubit.d.ts +25 -0
  15. package/dist/Cubit.d.ts.map +1 -0
  16. package/dist/Cubit.js +64 -0
  17. package/dist/Cubit.js.map +1 -0
  18. package/dist/adapter/BlacAdapter.d.ts +71 -0
  19. package/dist/adapter/BlacAdapter.d.ts.map +1 -0
  20. package/dist/adapter/BlacAdapter.js +373 -0
  21. package/dist/adapter/BlacAdapter.js.map +1 -0
  22. package/dist/adapter/ProxyFactory.d.ts +50 -0
  23. package/dist/adapter/ProxyFactory.d.ts.map +1 -0
  24. package/dist/adapter/ProxyFactory.js +150 -0
  25. package/dist/adapter/ProxyFactory.js.map +1 -0
  26. package/{src/adapter/index.ts → dist/adapter/index.d.ts} +1 -0
  27. package/dist/adapter/index.d.ts.map +1 -0
  28. package/dist/adapter/index.js +19 -0
  29. package/dist/adapter/index.js.map +1 -0
  30. package/dist/errors/BlacError.d.ts +38 -0
  31. package/dist/errors/BlacError.d.ts.map +1 -0
  32. package/dist/errors/BlacError.js +55 -0
  33. package/dist/errors/BlacError.js.map +1 -0
  34. package/dist/errors/ErrorManager.d.ts +39 -0
  35. package/dist/errors/ErrorManager.d.ts.map +1 -0
  36. package/dist/errors/ErrorManager.js +91 -0
  37. package/dist/errors/ErrorManager.js.map +1 -0
  38. package/dist/errors/handleError.d.ts +24 -0
  39. package/dist/errors/handleError.d.ts.map +1 -0
  40. package/dist/errors/handleError.js +62 -0
  41. package/dist/errors/handleError.js.map +1 -0
  42. package/dist/errors/index.d.ts +5 -0
  43. package/dist/errors/index.d.ts.map +1 -0
  44. package/dist/errors/index.js +13 -0
  45. package/dist/errors/index.js.map +1 -0
  46. package/{src/events.ts → dist/events.d.ts} +4 -2
  47. package/dist/events.d.ts.map +1 -0
  48. package/dist/events.js +17 -0
  49. package/dist/events.js.map +1 -0
  50. package/dist/index.cjs +38 -0
  51. package/dist/index.d.ts +17 -1303
  52. package/dist/index.d.ts.map +1 -0
  53. package/dist/index.js +38 -0
  54. package/dist/index.js.map +1 -0
  55. package/dist/lifecycle/BlocLifecycle.d.ts +51 -0
  56. package/dist/lifecycle/BlocLifecycle.d.ts.map +1 -0
  57. package/dist/lifecycle/BlocLifecycle.js +123 -0
  58. package/dist/lifecycle/BlocLifecycle.js.map +1 -0
  59. package/dist/lifecycle/index.d.ts +2 -0
  60. package/dist/lifecycle/index.d.ts.map +1 -0
  61. package/dist/lifecycle/index.js +18 -0
  62. package/dist/lifecycle/index.js.map +1 -0
  63. package/dist/plugins/BlocPluginRegistry.d.ts +58 -0
  64. package/dist/plugins/BlocPluginRegistry.d.ts.map +1 -0
  65. package/dist/plugins/BlocPluginRegistry.js +201 -0
  66. package/dist/plugins/BlocPluginRegistry.js.map +1 -0
  67. package/dist/plugins/SystemPluginRegistry.d.ts +79 -0
  68. package/dist/plugins/SystemPluginRegistry.d.ts.map +1 -0
  69. package/dist/plugins/SystemPluginRegistry.js +184 -0
  70. package/dist/plugins/SystemPluginRegistry.js.map +1 -0
  71. package/{src/plugins/index.ts → dist/plugins/index.d.ts} +1 -5
  72. package/dist/plugins/index.d.ts.map +1 -0
  73. package/dist/plugins/index.js +26 -0
  74. package/dist/plugins/index.js.map +1 -0
  75. package/dist/plugins/types.d.ts +103 -0
  76. package/dist/plugins/types.d.ts.map +1 -0
  77. package/dist/plugins/types.js +3 -0
  78. package/dist/plugins/types.js.map +1 -0
  79. package/dist/subscription/SubscriptionManager.d.ts +67 -0
  80. package/dist/subscription/SubscriptionManager.d.ts.map +1 -0
  81. package/dist/subscription/SubscriptionManager.js +317 -0
  82. package/dist/subscription/SubscriptionManager.js.map +1 -0
  83. package/{src/subscription/index.ts → dist/subscription/index.d.ts} +1 -0
  84. package/dist/subscription/index.d.ts.map +1 -0
  85. package/dist/subscription/index.js +19 -0
  86. package/dist/subscription/index.js.map +1 -0
  87. package/dist/subscription/types.d.ts +65 -0
  88. package/dist/subscription/types.d.ts.map +1 -0
  89. package/dist/subscription/types.js +3 -0
  90. package/dist/subscription/types.js.map +1 -0
  91. package/dist/testing.d.ts +85 -0
  92. package/dist/testing.d.ts.map +1 -0
  93. package/dist/testing.js +186 -0
  94. package/dist/testing.js.map +1 -0
  95. package/{src/types.ts → dist/types.d.ts} +11 -28
  96. package/dist/types.d.ts.map +1 -0
  97. package/dist/types.js +3 -0
  98. package/dist/types.js.map +1 -0
  99. package/dist/utils/BatchingManager.d.ts +28 -0
  100. package/dist/utils/BatchingManager.d.ts.map +1 -0
  101. package/dist/utils/BatchingManager.js +48 -0
  102. package/dist/utils/BatchingManager.js.map +1 -0
  103. package/dist/utils/RerenderLogger.d.ts +60 -0
  104. package/dist/utils/RerenderLogger.d.ts.map +1 -0
  105. package/dist/utils/RerenderLogger.js +205 -0
  106. package/dist/utils/RerenderLogger.js.map +1 -0
  107. package/dist/utils/generateInstanceId.d.ts +11 -0
  108. package/dist/utils/generateInstanceId.d.ts.map +1 -0
  109. package/dist/utils/generateInstanceId.js +50 -0
  110. package/dist/utils/generateInstanceId.js.map +1 -0
  111. package/dist/utils/shallowEqual.d.ts +9 -0
  112. package/dist/utils/shallowEqual.d.ts.map +1 -0
  113. package/dist/utils/shallowEqual.js +35 -0
  114. package/dist/utils/shallowEqual.js.map +1 -0
  115. package/dist/utils/uuid.d.ts +10 -0
  116. package/dist/utils/uuid.d.ts.map +1 -0
  117. package/dist/utils/uuid.js +24 -0
  118. package/dist/utils/uuid.js.map +1 -0
  119. package/package.json +17 -10
  120. package/dist/index.cjs.js +0 -11
  121. package/dist/index.cjs.js.map +0 -1
  122. package/dist/index.es.js +0 -2275
  123. package/dist/index.es.js.map +0 -1
  124. package/src/Blac.ts +0 -802
  125. package/src/Bloc.ts +0 -180
  126. package/src/BlocBase.ts +0 -398
  127. package/src/Cubit.ts +0 -68
  128. package/src/__tests__/Blac.config.test.ts +0 -79
  129. package/src/__tests__/Bloc.event.test.ts +0 -394
  130. package/src/__tests__/BlocBase.subscription.test.ts +0 -349
  131. package/src/__tests__/Cubit.test.ts +0 -462
  132. package/src/__tests__/memory-leaks.test.ts +0 -383
  133. package/src/__tests__/plugins.test.ts +0 -464
  134. package/src/adapter/BlacAdapter.ts +0 -467
  135. package/src/adapter/ProxyFactory.ts +0 -249
  136. package/src/adapter/__tests__/BlacAdapter.test.ts +0 -555
  137. package/src/adapter/__tests__/ProxyFactory.test.ts +0 -655
  138. package/src/errors/BlacError.ts +0 -69
  139. package/src/errors/ErrorManager.ts +0 -101
  140. package/src/errors/handleError.ts +0 -114
  141. package/src/errors/index.ts +0 -13
  142. package/src/index.ts +0 -26
  143. package/src/lifecycle/BlocLifecycle.ts +0 -156
  144. package/src/lifecycle/index.ts +0 -1
  145. package/src/plugins/BlocPluginRegistry.ts +0 -240
  146. package/src/plugins/SystemPluginRegistry.ts +0 -242
  147. package/src/plugins/__tests__/BlocPluginRegistry.test.ts +0 -450
  148. package/src/plugins/__tests__/SystemPluginRegistry.test.ts +0 -404
  149. package/src/plugins/types.ts +0 -129
  150. package/src/subscription/README.md +0 -132
  151. package/src/subscription/SubscriptionManager.ts +0 -395
  152. package/src/subscription/__tests__/SubscriptionManager.test.ts +0 -355
  153. package/src/subscription/types.ts +0 -90
  154. package/src/testing.ts +0 -246
  155. package/src/utils/BatchingManager.ts +0 -59
  156. package/src/utils/RerenderLogger.ts +0 -265
  157. package/src/utils/__tests__/generateInstanceId.test.ts +0 -104
  158. package/src/utils/__tests__/shallowEqual.test.ts +0 -171
  159. package/src/utils/__tests__/uuid.test.ts +0 -144
  160. package/src/utils/generateInstanceId.ts +0 -54
  161. package/src/utils/shallowEqual.ts +0 -40
  162. package/src/utils/uuid.ts +0 -22
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.cjs.js","sources":["../src/lifecycle/BlocLifecycle.ts","../src/plugins/SystemPluginRegistry.ts","../src/errors/BlacError.ts","../src/errors/ErrorManager.ts","../src/Blac.ts","../src/utils/uuid.ts","../src/errors/handleError.ts","../src/plugins/BlocPluginRegistry.ts","../src/subscription/SubscriptionManager.ts","../src/utils/BatchingManager.ts","../src/BlocBase.ts","../src/Bloc.ts","../src/Cubit.ts","../src/events.ts","../src/utils/shallowEqual.ts","../src/utils/generateInstanceId.ts","../src/utils/RerenderLogger.ts","../src/testing.ts","../src/adapter/ProxyFactory.ts","../src/adapter/BlacAdapter.ts"],"sourcesContent":["/**\n * Enum representing the lifecycle states of a Bloc instance\n */\nexport enum BlocLifecycleState {\n ACTIVE = 'active',\n DISPOSAL_REQUESTED = 'disposal_requested',\n DISPOSING = 'disposing',\n DISPOSED = 'disposed',\n}\n\nexport interface StateTransitionResult {\n success: boolean;\n currentState: BlocLifecycleState;\n previousState: BlocLifecycleState;\n}\n\n/**\n * Manages the lifecycle state transitions for Bloc instances.\n * Ensures atomic state transitions to prevent race conditions during disposal.\n */\nexport class BlocLifecycleManager {\n private disposalState = BlocLifecycleState.ACTIVE;\n private disposalLock = false;\n private disposalTimer?: NodeJS.Timeout | number;\n private disposalHandler?: (bloc: unknown) => void;\n\n get currentState(): BlocLifecycleState {\n return this.disposalState;\n }\n\n get isDisposed(): boolean {\n return this.disposalState === BlocLifecycleState.DISPOSED;\n }\n\n /**\n * Atomic state transition for disposal\n */\n atomicStateTransition(\n expectedState: BlocLifecycleState,\n newState: BlocLifecycleState,\n ): StateTransitionResult {\n if (this.disposalLock) {\n return {\n success: false,\n currentState: this.disposalState,\n previousState: this.disposalState,\n };\n }\n\n this.disposalLock = true;\n try {\n if (this.disposalState !== expectedState) {\n return {\n success: false,\n currentState: this.disposalState,\n previousState: this.disposalState,\n };\n }\n\n const previousState = this.disposalState;\n this.disposalState = newState;\n\n return {\n success: true,\n currentState: newState,\n previousState,\n };\n } finally {\n this.disposalLock = false;\n }\n }\n\n /**\n * Schedule disposal after a delay\n */\n scheduleDisposal(\n delay: number,\n canDispose: () => boolean,\n onDispose: () => void,\n ): void {\n // Cancel any existing disposal timer\n if (this.disposalTimer) {\n clearTimeout(this.disposalTimer as NodeJS.Timeout);\n this.disposalTimer = undefined;\n }\n\n const transitionResult = this.atomicStateTransition(\n BlocLifecycleState.ACTIVE,\n BlocLifecycleState.DISPOSAL_REQUESTED,\n );\n\n if (!transitionResult.success) {\n return;\n }\n\n this.disposalTimer = setTimeout(() => {\n if (\n canDispose() &&\n this.disposalState === BlocLifecycleState.DISPOSAL_REQUESTED\n ) {\n onDispose();\n } else {\n this.atomicStateTransition(\n BlocLifecycleState.DISPOSAL_REQUESTED,\n BlocLifecycleState.ACTIVE,\n );\n }\n }, delay);\n }\n\n /**\n * Cancel disposal if in disposal requested state\n */\n cancelDisposal(): boolean {\n if (this.disposalState === BlocLifecycleState.DISPOSAL_REQUESTED) {\n // Cancel disposal timer\n if (this.disposalTimer) {\n clearTimeout(this.disposalTimer as NodeJS.Timeout);\n this.disposalTimer = undefined;\n }\n\n // Transition back to active state\n const result = this.atomicStateTransition(\n BlocLifecycleState.DISPOSAL_REQUESTED,\n BlocLifecycleState.ACTIVE,\n );\n\n return result.success;\n }\n return false;\n }\n\n /**\n * Set disposal handler\n */\n setDisposalHandler(handler: (bloc: unknown) => void): void {\n this.disposalHandler = handler;\n }\n\n /**\n * Get disposal handler\n */\n getDisposalHandler(): ((bloc: unknown) => void) | undefined {\n return this.disposalHandler;\n }\n\n /**\n * Clear disposal timer\n */\n clearDisposalTimer(): void {\n if (this.disposalTimer) {\n clearTimeout(this.disposalTimer as NodeJS.Timeout);\n this.disposalTimer = undefined;\n }\n }\n}\n","import {\n BlacPlugin,\n PluginRegistry,\n PluginMetrics,\n ErrorContext,\n AdapterMetadata,\n} from './types';\nimport { BlocBase } from '../BlocBase';\nimport { Bloc } from '../Bloc';\n\n/**\n * Registry for system-wide plugins\n */\nexport class SystemPluginRegistry implements PluginRegistry<BlacPlugin> {\n private plugins = new Map<string, BlacPlugin>();\n private metrics = new Map<string, Map<string, PluginMetrics>>();\n private executionOrder: string[] = [];\n\n /**\n * Add a system plugin\n */\n add(plugin: BlacPlugin): void {\n if (this.plugins.has(plugin.name)) {\n throw new Error(`Plugin '${plugin.name}' is already registered`);\n }\n\n this.plugins.set(plugin.name, plugin);\n this.executionOrder.push(plugin.name);\n this.initializeMetrics(plugin.name);\n }\n\n /**\n * Remove a system plugin\n */\n remove(pluginName: string): boolean {\n const plugin = this.plugins.get(pluginName);\n if (!plugin) return false;\n\n this.plugins.delete(pluginName);\n this.metrics.delete(pluginName);\n this.executionOrder = this.executionOrder.filter(\n (name) => name !== pluginName,\n );\n\n return true;\n }\n\n /**\n * Get a plugin by name\n */\n get(pluginName: string): BlacPlugin | undefined {\n return this.plugins.get(pluginName);\n }\n\n /**\n * Get all plugins in execution order\n */\n getAll(): ReadonlyArray<BlacPlugin> {\n return this.executionOrder.map((name) => this.plugins.get(name)!);\n }\n\n /**\n * Clear all plugins\n */\n clear(): void {\n this.plugins.clear();\n this.metrics.clear();\n this.executionOrder = [];\n }\n\n /**\n * Execute a hook on all plugins\n */\n executeHook(\n hookName: keyof BlacPlugin,\n args: unknown[],\n errorHandler?: (error: Error, plugin: BlacPlugin) => void,\n ): void {\n for (const pluginName of this.executionOrder) {\n const plugin = this.plugins.get(pluginName)!;\n const hook = plugin[hookName] as Function | undefined;\n\n if (typeof hook !== 'function') continue;\n\n const startTime = performance.now();\n\n try {\n hook.apply(plugin, args);\n this.recordSuccess(pluginName, hookName as string, startTime);\n } catch (error) {\n this.recordError(pluginName, hookName as string, error as Error);\n\n if (errorHandler) {\n errorHandler(error as Error, plugin);\n } else {\n // Default: log and continue\n console.error(\n `Plugin '${pluginName}' error in hook '${hookName as string}':`,\n error,\n );\n }\n }\n }\n }\n\n /**\n * Bootstrap all plugins\n */\n bootstrap(): void {\n this.executeHook('beforeBootstrap', []);\n this.executeHook('afterBootstrap', []);\n }\n\n /**\n * Shutdown all plugins\n */\n shutdown(): void {\n this.executeHook('beforeShutdown', []);\n this.executeHook('afterShutdown', []);\n }\n\n /**\n * Notify plugins of bloc creation\n */\n notifyBlocCreated(bloc: BlocBase<any>): void {\n this.executeHook('onBlocCreated', [bloc]);\n }\n\n /**\n * Notify plugins of bloc disposal\n */\n notifyBlocDisposed(bloc: BlocBase<any>): void {\n this.executeHook('onBlocDisposed', [bloc]);\n }\n\n /**\n * Notify plugins of state change\n */\n notifyStateChanged(\n bloc: BlocBase<any>,\n previousState: any,\n currentState: any,\n ): void {\n this.executeHook('onStateChanged', [bloc, previousState, currentState]);\n }\n\n /**\n * Notify plugins of event addition\n */\n notifyEventAdded(bloc: Bloc<any, any>, event: any): void {\n this.executeHook('onEventAdded', [bloc, event]);\n }\n\n /**\n * Notify plugins of errors\n */\n notifyError(\n error: Error,\n bloc: BlocBase<unknown>,\n context: ErrorContext,\n ): void {\n this.executeHook('onError', [error, bloc, context], (hookError, plugin) => {\n // Double fault protection - if error handler fails, just log\n console.error(`Plugin '${plugin.name}' error handler failed:`, hookError);\n });\n }\n\n /**\n * Notify plugins of adapter lifecycle events\n */\n notifyAdapterCreated(adapter: any, metadata: AdapterMetadata): void {\n this.executeHook('onAdapterCreated', [adapter, metadata]);\n }\n\n notifyAdapterMount(adapter: any, metadata: AdapterMetadata): void {\n this.executeHook('onAdapterMount', [adapter, metadata]);\n }\n\n notifyAdapterUnmount(adapter: any, metadata: AdapterMetadata): void {\n this.executeHook('onAdapterUnmount', [adapter, metadata]);\n }\n\n notifyAdapterRender(adapter: any, metadata: AdapterMetadata): void {\n this.executeHook('onAdapterRender', [adapter, metadata]);\n }\n\n notifyAdapterDisposed(adapter: any, metadata: AdapterMetadata): void {\n this.executeHook('onAdapterDisposed', [adapter, metadata]);\n }\n\n /**\n * Get metrics for a plugin\n */\n getMetrics(pluginName: string): Map<string, PluginMetrics> | undefined {\n return this.metrics.get(pluginName);\n }\n\n private initializeMetrics(pluginName: string): void {\n this.metrics.set(pluginName, new Map());\n }\n\n private recordSuccess(\n pluginName: string,\n hookName: string,\n startTime: number,\n ): void {\n const pluginMetrics = this.metrics.get(pluginName)!;\n const hookMetrics = pluginMetrics.get(hookName) || {\n executionTime: 0,\n executionCount: 0,\n errorCount: 0,\n };\n\n const executionTime = performance.now() - startTime;\n\n pluginMetrics.set(hookName, {\n ...hookMetrics,\n executionTime: hookMetrics.executionTime + executionTime,\n executionCount: hookMetrics.executionCount + 1,\n lastExecutionTime: executionTime,\n });\n }\n\n private recordError(\n pluginName: string,\n hookName: string,\n error: Error,\n ): void {\n const pluginMetrics = this.metrics.get(pluginName)!;\n const hookMetrics = pluginMetrics.get(hookName) || {\n executionTime: 0,\n executionCount: 0,\n errorCount: 0,\n };\n\n pluginMetrics.set(hookName, {\n ...hookMetrics,\n errorCount: hookMetrics.errorCount + 1,\n lastError: error,\n });\n }\n}\n","export enum ErrorCategory {\n LIFECYCLE = 'LIFECYCLE',\n STATE = 'STATE',\n PLUGIN = 'PLUGIN',\n VALIDATION = 'VALIDATION',\n DISPOSAL = 'DISPOSAL',\n CONSUMER = 'CONSUMER',\n}\n\nexport enum ErrorSeverity {\n FATAL = 'FATAL', // System cannot continue\n ERROR = 'ERROR', // Operation failed but system continues\n WARNING = 'WARNING', // Potential issue but operation succeeded\n INFO = 'INFO', // Informational, not an error\n}\n\nexport type BlacErrorContext = {\n blocName?: string;\n blocId?: string;\n consumerId?: string;\n pluginName?: string;\n operation?: string;\n metadata?: Record<string, unknown>;\n};\n\nexport class BlacError extends Error {\n constructor(\n message: string,\n public readonly category: ErrorCategory,\n public readonly severity: ErrorSeverity,\n public readonly context?: BlacErrorContext,\n public readonly cause?: unknown,\n ) {\n super(message);\n this.name = 'BlacError';\n\n // Ensure proper prototype chain\n Object.setPrototypeOf(this, BlacError.prototype);\n }\n\n toString(): string {\n const contextStr = this.context\n ? ` [${Object.entries(this.context)\n .filter(([_, v]) => v !== undefined)\n .map(([k, v]) => `${k}: ${v}`)\n .join(', ')}]`\n : '';\n\n return `${this.name} [${this.severity}/${this.category}]: ${this.message}${contextStr}`;\n }\n}\n\nexport type ErrorHandler = (error: BlacError) => void;\n\nexport type ErrorHandlingStrategy = {\n shouldPropagate: (error: BlacError) => boolean;\n shouldLog: (error: BlacError) => boolean;\n handle: (error: BlacError) => void;\n};\n\nexport const DefaultErrorStrategy: ErrorHandlingStrategy = {\n shouldPropagate: (error) => error.severity === ErrorSeverity.FATAL,\n shouldLog: (error) => error.severity !== ErrorSeverity.INFO,\n handle: (error) => {\n if (DefaultErrorStrategy.shouldLog(error)) {\n console.error(error.toString(), error.cause);\n }\n },\n};\n","import {\n BlacError,\n ErrorHandler,\n ErrorHandlingStrategy,\n DefaultErrorStrategy,\n} from './BlacError';\n\n/**\n * Centralized error management system for BlaC framework.\n * Handles error processing, logging, and propagation strategies.\n */\nexport class ErrorManager {\n private static instance: ErrorManager;\n private handlers: Set<ErrorHandler> = new Set();\n private strategy: ErrorHandlingStrategy = DefaultErrorStrategy;\n\n /**\n * Get the singleton instance of ErrorManager\n */\n static getInstance(): ErrorManager {\n if (!ErrorManager.instance) {\n ErrorManager.instance = new ErrorManager();\n }\n return ErrorManager.instance;\n }\n\n /**\n * Set a custom error handling strategy\n */\n setStrategy(strategy: ErrorHandlingStrategy): void {\n this.strategy = strategy;\n }\n\n /**\n * Add a custom error handler that will be called for all errors\n */\n addHandler(handler: ErrorHandler): void {\n this.handlers.add(handler);\n }\n\n /**\n * Remove a previously added error handler\n */\n removeHandler(handler: ErrorHandler): void {\n this.handlers.delete(handler);\n }\n\n /**\n * Process an error through all handlers and apply the configured strategy\n */\n handle(error: BlacError): void {\n // Always notify handlers first\n this.handlers.forEach((handler) => {\n try {\n handler(error);\n } catch (handlerError) {\n // Prevent handler errors from breaking error handling\n console.error('Error in error handler:', handlerError);\n }\n });\n\n // Apply strategy\n this.strategy.handle(error);\n\n // Propagate if needed\n if (this.strategy.shouldPropagate(error)) {\n throw error;\n }\n }\n\n /**\n * Convenience method for wrapping operations with error handling\n */\n wrap<T>(operation: () => T, errorFactory: (error: unknown) => BlacError): T {\n try {\n return operation();\n } catch (error) {\n const blacError = errorFactory(error);\n this.handle(blacError);\n // Will only reach here if strategy says not to propagate\n return undefined as T;\n }\n }\n\n /**\n * Async version of wrap\n */\n async wrapAsync<T>(\n operation: () => Promise<T>,\n errorFactory: (error: unknown) => BlacError,\n ): Promise<T> {\n try {\n return await operation();\n } catch (error) {\n const blacError = errorFactory(error);\n this.handle(blacError);\n // Will only reach here if strategy says not to propagate\n return undefined as T;\n }\n }\n}\n","import { BlocBase, BlocInstanceId } from './BlocBase';\nimport { BlocLifecycleState } from './lifecycle/BlocLifecycle';\nimport {\n BlocBaseAbstract,\n BlocConstructor,\n BlocHookDependencyArrayFn,\n BlocState,\n} from './types';\nimport { SystemPluginRegistry } from './plugins/SystemPluginRegistry';\nimport { BlacError, ErrorCategory, ErrorSeverity } from './errors/BlacError';\nimport { ErrorManager } from './errors/ErrorManager';\n\n/**\n * Configuration options for the Blac instance\n */\nexport interface BlacConfig {\n /**\n * Whether to enable proxy dependency tracking for automatic re-render optimization.\n * When false, state changes always cause re-renders unless dependencies are manually specified.\n * Default: true\n */\n proxyDependencyTracking?: boolean;\n}\n\nexport interface GetBlocOptions<B extends BlocBase<unknown>> {\n id?: string;\n selector?: BlocHookDependencyArrayFn<BlocState<B>>;\n constructorParams?: ConstructorParameters<BlocConstructor<B>>[];\n onMount?: (bloc: B) => void;\n instanceRef?: string;\n throwIfNotFound?: boolean;\n /** Force creation of a new instance for isolated blocs, bypassing instance lookup */\n forceNewInstance?: boolean;\n}\n\n/**\n * Interface for Blac instance management\n */\nexport interface BlacInstanceManager {\n getInstance(): Blac;\n setInstance(instance: Blac): void;\n resetInstance(): void;\n}\n\n/**\n * Default singleton implementation of BlacInstanceManager\n */\nclass SingletonBlacManager implements BlacInstanceManager {\n private static _instance: Blac;\n\n getInstance(): Blac {\n if (!SingletonBlacManager._instance) {\n SingletonBlacManager._instance = new Blac({\n __unsafe_ignore_singleton: true,\n });\n }\n return SingletonBlacManager._instance;\n }\n\n setInstance(instance: Blac): void {\n SingletonBlacManager._instance = instance;\n }\n\n resetInstance(): void {\n const oldInstance = SingletonBlacManager._instance;\n SingletonBlacManager._instance = new Blac({\n __unsafe_ignore_singleton: true,\n });\n\n // Transfer any keep-alive blocs to the new instance\n if (oldInstance) {\n for (const bloc of oldInstance.keepAliveBlocs) {\n SingletonBlacManager._instance.keepAliveBlocs.add(bloc);\n SingletonBlacManager._instance.uidRegistry.set(bloc.uid, bloc);\n }\n }\n }\n}\n\n/**\n * Global instance manager (can be replaced for testing or different patterns)\n */\nlet instanceManager: BlacInstanceManager = new SingletonBlacManager();\n\n/**\n * Sets a custom instance manager (useful for testing or advanced patterns)\n */\nexport function setBlacInstanceManager(manager: BlacInstanceManager): void {\n instanceManager = manager;\n}\n\n/**\n * Main Blac class that manages the state management system.\n * Can work with singleton pattern or dependency injection.\n * Handles bloc lifecycle, and instance tracking.\n *\n * Key responsibilities:\n * - Managing bloc instances (creation, disposal, lookup)\n * - Handling isolated and non-isolated blocs\n * - Providing logging and debugging capabilities\n */\nexport class Blac {\n static get instance(): Blac {\n return instanceManager.getInstance();\n }\n /** Timestamp when the instance was created */\n createdAt = Date.now();\n private errorManager = ErrorManager.getInstance();\n static get getAllBlocs() {\n return Blac.instance.getAllBlocs;\n }\n\n /** Private static configuration */\n private static _config: BlacConfig = {\n proxyDependencyTracking: true,\n };\n\n /** Get current configuration */\n static get config(): Readonly<BlacConfig> {\n return { ...this._config };\n }\n\n /**\n * Set or update Blac configuration\n * @param config - Partial configuration to merge with existing config\n * @throws Error if configuration is invalid\n */\n static setConfig(config: Partial<BlacConfig>): void {\n // Validate config\n if (\n config.proxyDependencyTracking !== undefined &&\n typeof config.proxyDependencyTracking !== 'boolean'\n ) {\n const error = new BlacError(\n 'BlacConfig.proxyDependencyTracking must be a boolean',\n ErrorCategory.VALIDATION,\n ErrorSeverity.FATAL,\n );\n this.instance.errorManager.handle(error);\n }\n\n // Merge with existing config\n this._config = {\n ...this._config,\n ...config,\n };\n\n // Log config update if logging is enabled\n if (this.enableLog) {\n this.instance.log('Blac config updated:', this._config);\n }\n }\n /** Map storing all registered bloc instances by their class name and ID */\n blocInstanceMap: Map<string, BlocBase<unknown>> = new Map();\n /** Map storing isolated bloc instances grouped by their constructor */\n // Using BlocConstructor<BlocBase<unknown>> would break type inference when storing\n // different bloc types in the same map. The 'any' allows proper polymorphic storage\n // while maintaining type safety at usage sites through the BlocConstructor constraint.\n isolatedBlocMap: Map<BlocConstructor<any>, BlocBase<unknown>[]> = new Map();\n /** Map for O(1) lookup of isolated blocs by UID */\n isolatedBlocIndex: Map<string, BlocBase<unknown>> = new Map();\n /** Map tracking UIDs to prevent memory leaks */\n uidRegistry: Map<string, BlocBase<unknown>> = new Map();\n /** Set of keep-alive blocs for controlled cleanup */\n keepAliveBlocs: Set<BlocBase<unknown>> = new Set();\n /** Flag to control whether changes should be posted to document */\n postChangesToDocument = false;\n /** System plugin registry */\n readonly plugins = new SystemPluginRegistry();\n\n /**\n * Creates a new Blac instance.\n * @param options - Configuration options including singleton control\n */\n constructor(options: { __unsafe_ignore_singleton?: boolean } = {}) {\n const { __unsafe_ignore_singleton = false } = options;\n if (!__unsafe_ignore_singleton) {\n return Blac.instance;\n }\n instanceManager.setInstance(this);\n\n // Bootstrap plugins on creation\n this.plugins.bootstrap();\n }\n\n /** Flag to enable/disable logging */\n static enableLog = false;\n static logLevel: 'warn' | 'log' = 'warn';\n static logSpy: ((...args: unknown[]) => void) | null = null;\n\n /**\n * Logs messages to console when logging is enabled\n * @param args - Arguments to log\n */\n log = (...args: unknown[]) => {\n if (Blac.logSpy) {\n Blac.logSpy(args);\n }\n if (Blac.enableLog && Blac.logLevel === 'warn') {\n // Logging disabled - console.warn removed\n }\n if (Blac.enableLog && Blac.logLevel === 'log') {\n // Logging disabled - console.log removed\n }\n };\n static get log() {\n return Blac.instance.log;\n }\n\n /**\n * Gets the current Blac instance\n * @returns The Blac instance\n */\n static getInstance(): Blac {\n return instanceManager.getInstance();\n }\n\n /**\n * Logs a warning message\n * @param message - Warning message\n * @param args - Additional arguments\n */\n warn = (message: string, ...args: unknown[]) => {\n console.warn(message, ...args);\n };\n static get warn() {\n return Blac.instance.warn;\n }\n /**\n * Logs an error message\n * @param message - Error message\n * @param args - Additional arguments\n */\n error = (message: string, ...args: unknown[]) => {\n if (Blac.enableLog) {\n console.error(message, ...args);\n }\n };\n static get error() {\n return Blac.instance.error;\n }\n\n /**\n * Resets the Blac instance to a new one, disposing non-keepAlive blocs\n * from the old instance.\n */\n resetInstance = (): void => {\n this.log('Reset Blac instance');\n\n // Create snapshots to avoid concurrent modification issues\n const oldBlocInstanceMap = new Map(this.blocInstanceMap);\n const oldIsolatedBlocMap = new Map(this.isolatedBlocMap);\n\n // Dispose non-keepAlive blocs from the current instance\n // Use disposeBloc method to ensure proper cleanup\n oldBlocInstanceMap.forEach((bloc) => {\n // TODO: Type assertion for private property access (see explanation above)\n if (\n !bloc._keepAlive &&\n (bloc as any)._disposalState === BlocLifecycleState.ACTIVE\n ) {\n this.disposeBloc(bloc);\n }\n });\n\n oldIsolatedBlocMap.forEach((blocArray) => {\n blocArray.forEach((bloc) => {\n // TODO: Type assertion for private property access (see explanation above)\n if (\n !bloc._keepAlive &&\n (bloc as any)._disposalState === BlocLifecycleState.ACTIVE\n ) {\n this.disposeBloc(bloc);\n }\n });\n });\n\n // Clear registries (keep-alive blocs will be re-added by instance manager)\n this.blocInstanceMap.clear();\n this.isolatedBlocMap.clear();\n this.isolatedBlocIndex.clear();\n\n // Use instance manager to reset\n instanceManager.resetInstance();\n };\n static resetInstance = (): void => {\n instanceManager.resetInstance();\n };\n\n /**\n * Disposes of a bloc instance by removing it from the appropriate registry\n * @param bloc - The bloc instance to dispose\n */\n disposeBloc = (bloc: BlocBase<unknown>): void => {\n // Check if bloc is already disposed to prevent double disposal\n // TODO: Type assertion needed to access private _disposalState property from external class.\n // This is safe because we know BlocBase has this property, but TypeScript can't verify\n // private property access across class boundaries. Alternative would be to make\n // _disposalState protected, but that would expose internal implementation details.\n const currentState = (bloc as any)._disposalState;\n const validStatesForDisposal = [\n BlocLifecycleState.ACTIVE,\n BlocLifecycleState.DISPOSAL_REQUESTED,\n ];\n\n if (!validStatesForDisposal.includes(currentState)) {\n this.log(\n `[${bloc._name}:${String(bloc._id)}] disposeBloc called on bloc in invalid state: ${currentState}`,\n );\n return;\n }\n\n const base = bloc.constructor as unknown as BlocBaseAbstract;\n const key = this.createBlocInstanceMapKey(bloc._name, bloc._id);\n this.log(\n `[${bloc._name}:${String(bloc._id)}] disposeBloc called. Isolated: ${String(base.isolated)}`,\n );\n\n // First dispose the bloc to prevent further operations\n bloc.dispose();\n\n // Notify plugins of bloc disposal\n this.plugins.notifyBlocDisposed(bloc);\n\n // Then clean up from registries\n if (base.isolated) {\n this.unregisterIsolatedBlocInstance(bloc);\n this.blocInstanceMap.delete(key);\n } else {\n this.unregisterBlocInstance(bloc);\n }\n\n this.log('dispatched bloc', bloc);\n };\n static get disposeBloc() {\n return Blac.instance.disposeBloc;\n }\n\n /**\n * Creates a unique key for a bloc instance in the map based on the bloc class name and instance ID\n * @param blocClassName - The name of the bloc class\n * @param id - The instance ID\n * @returns A unique key string in the format \"className:id\"\n */\n createBlocInstanceMapKey(blocClassName: string, id: BlocInstanceId): string {\n return `${blocClassName}:${String(id)}`;\n }\n\n /**\n * Unregister a bloc instance from the main registry\n * @param bloc - The bloc instance to unregister\n */\n unregisterBlocInstance(bloc: BlocBase<unknown>): void {\n const key = this.createBlocInstanceMapKey(bloc._name, bloc._id);\n this.blocInstanceMap.delete(key);\n\n // Clean up UID tracking\n this.uidRegistry.delete(bloc.uid);\n\n // Remove from keep-alive set\n this.keepAliveBlocs.delete(bloc);\n }\n\n /**\n * Registers a bloc instance in the main registry\n * @param bloc - The bloc instance to register\n */\n registerBlocInstance(bloc: BlocBase<unknown>): void {\n const key = this.createBlocInstanceMapKey(bloc._name, bloc._id);\n this.blocInstanceMap.set(key, bloc);\n\n // Track UID for cleanup\n this.uidRegistry.set(bloc.uid, bloc);\n\n // Track keep-alive blocs\n if (bloc._keepAlive) {\n this.keepAliveBlocs.add(bloc);\n }\n }\n\n /**\n * Finds a registered bloc instance by its class and ID\n * @param blocClass - The bloc class to search for\n * @param id - The instance ID\n * @returns The found bloc instance or undefined if not found\n */\n findRegisteredBlocInstance<B extends BlocConstructor<any>>(\n blocClass: B,\n id: BlocInstanceId,\n ): InstanceType<B> | undefined {\n const base = blocClass as unknown as BlocBaseAbstract;\n if (base.isolated) return undefined;\n\n const key = this.createBlocInstanceMapKey(blocClass.name, id);\n const found = this.blocInstanceMap.get(key) as InstanceType<B> | undefined;\n\n // Don't return disposed blocs\n if (found && (found as any).isDisposed) {\n return undefined;\n }\n\n return found;\n }\n\n /**\n * Registers an isolated bloc instance in the isolated registry\n * @param bloc - The isolated bloc instance to register\n */\n registerIsolatedBlocInstance(bloc: BlocBase<unknown>): void {\n const blocClass = bloc.constructor as BlocConstructor<any>;\n const blocs = this.isolatedBlocMap.get(blocClass);\n if (blocs) {\n blocs.push(bloc);\n } else {\n this.isolatedBlocMap.set(blocClass, [bloc]);\n }\n\n // Add to isolated index for O(1) lookups\n this.isolatedBlocIndex.set(bloc.uid, bloc);\n\n // Track UID for cleanup\n this.uidRegistry.set(bloc.uid, bloc);\n\n // Track keep-alive blocs\n if (bloc._keepAlive) {\n this.keepAliveBlocs.add(bloc);\n }\n }\n\n /**\n * Unregister an isolated bloc instance from the isolated registry\n * @param bloc - The isolated bloc instance to unregister\n */\n unregisterIsolatedBlocInstance(bloc: BlocBase<unknown>): void {\n const blocClass = bloc.constructor;\n const blocs = this.isolatedBlocMap.get(blocClass as BlocConstructor<any>);\n\n // Ensure both data structures are synchronized\n let wasRemoved = false;\n\n if (blocs) {\n const index = blocs.findIndex((b) => b.uid === bloc.uid);\n if (index !== -1) {\n blocs.splice(index, 1);\n wasRemoved = true;\n }\n\n if (blocs.length === 0) {\n this.isolatedBlocMap.delete(blocClass as BlocConstructor<any>);\n }\n }\n\n // Always try to remove from isolated index, even if not found in map\n const wasInIndex = this.isolatedBlocIndex.delete(bloc.uid);\n\n // Clean up UID tracking\n this.uidRegistry.delete(bloc.uid);\n\n // Remove from keep-alive set\n this.keepAliveBlocs.delete(bloc);\n\n // Log inconsistency for debugging\n if (wasRemoved !== wasInIndex) {\n this.warn(\n `[Blac] Inconsistent state detected during isolated bloc cleanup for ${bloc._name}:${bloc.uid}. ` +\n `Map removal: ${wasRemoved}, Index removal: ${wasInIndex}`,\n );\n }\n }\n\n /**\n * Finds an isolated bloc instance by its class and ID (O(n) lookup)\n */\n findIsolatedBlocInstance<B extends BlocConstructor<any>>(\n blocClass: B,\n id: BlocInstanceId,\n ): InstanceType<B> | undefined {\n const base = blocClass as unknown as BlocBaseAbstract;\n if (!base.isolated) return undefined;\n\n const blocs = this.isolatedBlocMap.get(blocClass);\n if (!blocs) {\n return undefined;\n }\n // Find the specific bloc by ID within the isolated array\n const found = blocs.find((b) => b._id === id && !(b as any).isDisposed) as\n | InstanceType<B>\n | undefined;\n return found;\n }\n\n /**\n * Finds an isolated bloc instance by UID (O(1) lookup)\n */\n findIsolatedBlocInstanceByUid<B extends BlocBase<unknown>>(\n uid: string,\n ): B | undefined {\n return this.isolatedBlocIndex.get(uid) as B | undefined;\n }\n\n /**\n * Creates a new bloc instance and registers it in the appropriate registry\n * @param blocClass - The bloc class to instantiate\n * @param id - The instance ID\n * @param props - Properties to pass to the bloc constructor\n * @param instanceRef - Optional reference string for the instance\n * @returns The newly created bloc instance\n */\n createNewBlocInstance<B extends BlocConstructor<BlocBase<any>>>(\n blocClass: B,\n id: BlocInstanceId,\n options: GetBlocOptions<InstanceType<B>> = {},\n ): InstanceType<B> {\n const { constructorParams, instanceRef } = options;\n const newBloc = new blocClass(constructorParams) as InstanceType<B>;\n newBloc.blacInstance = this;\n newBloc._instanceRef = instanceRef;\n newBloc._id = id;\n\n // Set up disposal handler to break circular dependency\n newBloc.setDisposalHandler((bloc) => this.disposeBloc(bloc));\n\n if (newBloc.isIsolated) {\n this.registerIsolatedBlocInstance(newBloc);\n } else {\n this.registerBlocInstance(newBloc);\n }\n\n // Plugins are activated in constructor\n\n // Notify system plugins of bloc creation\n this.plugins.notifyBlocCreated(newBloc);\n\n return newBloc;\n }\n\n activateBloc = (bloc: BlocBase<unknown>): void => {\n // Don't activate disposed blocs\n if ((bloc as any)._disposalState !== BlocLifecycleState.ACTIVE) {\n this.log(\n `[${bloc._name}:${String(bloc._id)}] activateBloc called on disposed bloc. Ignoring.`,\n );\n return;\n }\n\n const base = bloc.constructor as unknown as BlocConstructor<BlocBase<any>>;\n const isIsolated = bloc.isIsolated;\n\n let found = isIsolated\n ? this.findIsolatedBlocInstance(base, bloc._id)\n : this.findRegisteredBlocInstance(base, bloc._id);\n if (found) {\n return;\n }\n\n this.log(\n `[${bloc._name}:${String(bloc._id)}] activateBloc called. Isolated: ${String(bloc.isIsolated)}`,\n );\n if (bloc.isIsolated) {\n this.registerIsolatedBlocInstance(bloc);\n } else {\n this.registerBlocInstance(bloc);\n }\n };\n static get activateBloc() {\n return Blac.instance.activateBloc;\n }\n\n /**\n * Gets or creates a bloc instance based on the provided class and options.\n * If a bloc with the given ID exists, it will be returned. Otherwise, a new instance will be created.\n *\n * @param blocClass - The bloc class to get or create\n * @param options - Options including:\n * - id: The instance ID (defaults to class name if not provided)\n * - props: Properties to pass to the bloc constructor\n * - instanceRef: Optional reference string for the instance\n * @returns The bloc instance\n */\n getBloc = <B extends BlocConstructor<BlocBase<any>>>(\n blocClass: B,\n options: GetBlocOptions<InstanceType<B>> = {},\n ): InstanceType<B> => {\n const { id, forceNewInstance } = options;\n const base = blocClass as unknown as BlocBaseAbstract;\n const blocId = id ?? blocClass.name;\n this.log(`[${blocClass.name}:${String(blocId)}] (getBloc) Called:`, {\n options,\n base,\n });\n\n // Skip instance lookup if forceNewInstance is true for isolated blocs\n if (!forceNewInstance) {\n if (base.isolated) {\n const isolatedBloc = this.findIsolatedBlocInstance<B>(\n blocClass,\n options.instanceRef ?? blocId,\n );\n if (isolatedBloc) {\n return isolatedBloc;\n } else {\n if (options.throwIfNotFound) {\n throw new Error(`Isolated bloc ${blocClass.name} not found`);\n }\n }\n } else {\n const registeredBloc = this.findRegisteredBlocInstance(\n blocClass,\n blocId,\n );\n if (registeredBloc) {\n return registeredBloc;\n } else {\n if (options.throwIfNotFound) {\n throw new Error(`Registered bloc ${blocClass.name} not found`);\n }\n }\n }\n }\n\n const bloc = this.createNewBlocInstance(blocClass, blocId, options);\n this.log(\n `[${blocClass.name}:${String(blocId)}] (getBloc) No existing instance found. Creating new one.`,\n options,\n bloc,\n );\n\n if (!bloc) {\n throw new Error(\n `[getBloc] Failed to create bloc instance for ${blocClass.name}. This should never happen.`,\n );\n }\n\n return bloc;\n };\n static get getBloc() {\n return Blac.instance.getBloc;\n }\n\n /**\n * Gets all instances of a specific bloc class\n * @param blocClass - The bloc class to search for\n * @param options - Options including:\n * - searchIsolated: Whether to search in isolated blocs (defaults to bloc's isolated property)\n * @returns Array of matching bloc instances\n */\n getAllBlocs = <B extends BlocConstructor<any>>(\n blocClass: B,\n options: {\n searchIsolated?: boolean;\n } = {},\n ): InstanceType<B>[] => {\n const results: InstanceType<B>[] = [];\n\n // Search non-isolated blocs\n this.blocInstanceMap.forEach((blocInstance) => {\n if (blocInstance.constructor === blocClass) {\n // Strict constructor check\n results.push(blocInstance as InstanceType<B>);\n }\n });\n\n // Optionally search isolated blocs\n if (options.searchIsolated !== false) {\n const isolatedBlocs = this.isolatedBlocMap.get(blocClass);\n if (isolatedBlocs) {\n results.push(...isolatedBlocs.map((bloc) => bloc as InstanceType<B>));\n }\n }\n\n return results;\n };\n\n /**\n * Disposes all keep-alive blocs of a specific type\n * @param blocClass - The bloc class to dispose\n */\n disposeKeepAliveBlocs = <B extends BlocConstructor<any>>(\n blocClass?: B,\n ): void => {\n const toDispose: BlocBase<unknown>[] = [];\n\n for (const bloc of this.keepAliveBlocs) {\n if (!blocClass || bloc.constructor === blocClass) {\n toDispose.push(bloc);\n }\n }\n\n toDispose.forEach((bloc) => bloc.dispose());\n };\n static get disposeKeepAliveBlocs() {\n return Blac.instance.disposeKeepAliveBlocs;\n }\n\n /**\n * Disposes all blocs matching a pattern\n * @param predicate - Function to test each bloc for disposal\n */\n disposeBlocs = (predicate: (bloc: BlocBase<unknown>) => boolean): void => {\n const toDispose: BlocBase<unknown>[] = [];\n\n // Check registered blocs\n for (const bloc of this.blocInstanceMap.values()) {\n if (predicate(bloc)) {\n toDispose.push(bloc);\n }\n }\n\n // Check isolated blocs\n for (const blocs of this.isolatedBlocMap.values()) {\n for (const bloc of blocs) {\n if (predicate(bloc)) {\n toDispose.push(bloc);\n }\n }\n }\n\n toDispose.forEach((bloc) => bloc.dispose());\n };\n static get disposeBlocs() {\n return Blac.instance.disposeBlocs;\n }\n\n /**\n * Gets memory usage statistics for debugging\n */\n getMemoryStats = () => {\n return {\n totalBlocs: this.uidRegistry.size,\n registeredBlocs: this.blocInstanceMap.size,\n isolatedBlocs: Array.from(this.isolatedBlocMap.values()).reduce(\n (sum, arr) => sum + arr.length,\n 0,\n ),\n keepAliveBlocs: this.keepAliveBlocs.size,\n isolatedBlocTypes: this.isolatedBlocMap.size,\n };\n };\n static get getMemoryStats() {\n return Blac.instance.getMemoryStats;\n }\n\n /**\n * Validates subscription references and cleans up orphaned blocs\n */\n validateConsumers = (): void => {\n for (const bloc of this.uidRegistry.values()) {\n // Check if bloc should be disposed after validation\n // TODO: Type assertion for private property access (see explanation above)\n if (\n bloc.subscriptionCount === 0 &&\n !bloc._keepAlive &&\n (bloc as any)._disposalState === BlocLifecycleState.ACTIVE\n ) {\n // Schedule disposal for blocs with no subscriptions\n setTimeout(() => {\n // Double-check conditions before disposal\n // TODO: Type assertion for private property access (see explanation above)\n if (\n bloc.subscriptionCount === 0 &&\n !bloc._keepAlive &&\n (bloc as any)._disposalState === BlocLifecycleState.ACTIVE\n ) {\n this.disposeBloc(bloc);\n }\n }, 1000); // Give a grace period\n }\n }\n };\n static get validateConsumers() {\n return Blac.instance.validateConsumers;\n }\n\n /**\n * Bootstrap the Blac instance and all plugins\n */\n bootstrap(): void {\n this.plugins.bootstrap();\n }\n\n /**\n * Shutdown the Blac instance and all plugins\n */\n shutdown(): void {\n this.plugins.shutdown();\n\n // Dispose all non-keepAlive blocs\n for (const bloc of this.blocInstanceMap.values()) {\n if (!bloc._keepAlive) {\n this.disposeBloc(bloc);\n }\n }\n\n for (const blocs of this.isolatedBlocMap.values()) {\n for (const bloc of blocs) {\n if (!bloc._keepAlive) {\n this.disposeBloc(bloc);\n }\n }\n }\n }\n}\n","/**\n * Cross-platform UUID v4 generator that works in all environments including React Native/Hermes\n * Falls back to crypto.randomUUID() when available, otherwise uses Math.random()\n */\n\n/**\n * Generates a UUID v4 string compatible with all JavaScript environments\n * @returns A UUID v4 string in the format xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx\n */\nexport function generateUUID(): string {\n // Try to use crypto.randomUUID() if available (Node.js 16+, modern browsers)\n if (typeof crypto !== 'undefined' && crypto.randomUUID) {\n return crypto.randomUUID();\n }\n\n // Fallback implementation for React Native/Hermes and older environments\n return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, function (c) {\n const r = (Math.random() * 16) | 0;\n const v = c === 'x' ? r : (r & 0x3) | 0x8;\n return v.toString(16);\n });\n}\n","import {\n BlacError,\n ErrorCategory,\n ErrorSeverity,\n BlacErrorContext,\n} from './BlacError';\nimport { ErrorManager } from './ErrorManager';\n\n/**\n * Standard error handling helper for BlaC\n *\n * Usage:\n * - For fatal errors that should propagate: handleError.fatal(...)\n * - For recoverable errors: handleError.error(...)\n * - For warnings: handleError.warn(...)\n */\nexport const handleError = {\n fatal: (\n message: string,\n category: ErrorCategory,\n context?: BlacErrorContext,\n cause?: unknown,\n ): never => {\n const error = new BlacError(\n message,\n category,\n ErrorSeverity.FATAL,\n context,\n cause,\n );\n ErrorManager.getInstance().handle(error);\n // This will always throw due to FATAL severity\n throw error;\n },\n\n error: (\n message: string,\n category: ErrorCategory,\n context?: BlacErrorContext,\n cause?: unknown,\n ): void => {\n const error = new BlacError(\n message,\n category,\n ErrorSeverity.ERROR,\n context,\n cause,\n );\n ErrorManager.getInstance().handle(error);\n },\n\n warn: (\n message: string,\n category: ErrorCategory,\n context?: BlacErrorContext,\n cause?: unknown,\n ): void => {\n const error = new BlacError(\n message,\n category,\n ErrorSeverity.WARNING,\n context,\n cause,\n );\n ErrorManager.getInstance().handle(error);\n },\n\n info: (\n message: string,\n category: ErrorCategory,\n context?: BlacErrorContext,\n ): void => {\n const error = new BlacError(message, category, ErrorSeverity.INFO, context);\n ErrorManager.getInstance().handle(error);\n },\n\n /**\n * Wraps a function to catch and handle errors\n */\n wrap: <T>(\n fn: () => T,\n category: ErrorCategory,\n context?: BlacErrorContext,\n severity: ErrorSeverity = ErrorSeverity.ERROR,\n ): T | undefined => {\n try {\n return fn();\n } catch (cause) {\n const message = cause instanceof Error ? cause.message : String(cause);\n const error = new BlacError(message, category, severity, context, cause);\n ErrorManager.getInstance().handle(error);\n return undefined;\n }\n },\n\n /**\n * Wraps an async function to catch and handle errors\n */\n wrapAsync: async <T>(\n fn: () => Promise<T>,\n category: ErrorCategory,\n context?: BlacErrorContext,\n severity: ErrorSeverity = ErrorSeverity.ERROR,\n ): Promise<T | undefined> => {\n try {\n return await fn();\n } catch (cause) {\n const message = cause instanceof Error ? cause.message : String(cause);\n const error = new BlacError(message, category, severity, context, cause);\n ErrorManager.getInstance().handle(error);\n return undefined;\n }\n },\n};\n","import { BlocPlugin, PluginRegistry, ErrorContext } from './types';\nimport { handleError } from '../errors/handleError';\nimport { ErrorCategory } from '../errors/BlacError';\n\n/**\n * Registry for bloc-specific plugins\n */\nexport class BlocPluginRegistry<TState, TEvent = never>\n implements PluginRegistry<BlocPlugin<TState, TEvent>>\n{\n private plugins = new Map<string, BlocPlugin<TState, TEvent>>();\n private executionOrder: string[] = [];\n private attached = false;\n\n /**\n * Add a bloc plugin\n */\n add(plugin: BlocPlugin<TState, TEvent>): void {\n if (this.plugins.has(plugin.name)) {\n throw new Error(`Plugin '${plugin.name}' is already registered`);\n }\n\n // Validate capabilities\n if (plugin.capabilities) {\n this.validateCapabilities(plugin);\n }\n\n this.plugins.set(plugin.name, plugin);\n this.executionOrder.push(plugin.name);\n }\n\n /**\n * Remove a bloc plugin\n */\n remove(pluginName: string): boolean {\n const plugin = this.plugins.get(pluginName);\n if (!plugin) return false;\n\n // Call onDetach if attached\n if (this.attached && plugin.onDetach) {\n handleError.wrap(() => plugin.onDetach!(), ErrorCategory.PLUGIN, {\n pluginName,\n operation: 'onDetach',\n });\n }\n\n this.plugins.delete(pluginName);\n this.executionOrder = this.executionOrder.filter(\n (name) => name !== pluginName,\n );\n\n return true;\n }\n\n /**\n * Get a plugin by name\n */\n get(pluginName: string): BlocPlugin<TState, TEvent> | undefined {\n return this.plugins.get(pluginName);\n }\n\n /**\n * Get all plugins in execution order\n */\n getAll(): ReadonlyArray<BlocPlugin<TState, TEvent>> {\n return this.executionOrder.map((name) => this.plugins.get(name)!);\n }\n\n /**\n * Clear all plugins\n */\n clear(): void {\n // Detach all plugins first\n if (this.attached) {\n for (const plugin of this.getAll()) {\n if (plugin.onDetach) {\n handleError.wrap(() => plugin.onDetach!(), ErrorCategory.PLUGIN, {\n pluginName: plugin.name,\n operation: 'onDetach',\n });\n }\n }\n }\n\n this.plugins.clear();\n this.executionOrder = [];\n this.attached = false;\n }\n\n /**\n * Attach all plugins to a bloc\n */\n attach(bloc: any): void {\n if (this.attached) {\n throw new Error('Plugins are already attached');\n }\n\n for (const plugin of this.getAll()) {\n if (plugin.onAttach) {\n try {\n plugin.onAttach(bloc);\n } catch (error) {\n console.error(`Plugin '${plugin.name}' error in onAttach:`, error);\n // Remove failing plugin\n this.remove(plugin.name);\n }\n }\n }\n\n this.attached = true;\n }\n\n /**\n * Transform state through all plugins\n */\n transformState(previousState: TState, nextState: TState): TState {\n let transformedState = nextState;\n\n for (const plugin of this.getAll()) {\n if (plugin.transformState && this.canTransformState(plugin)) {\n try {\n transformedState = plugin.transformState(\n previousState,\n transformedState,\n );\n } catch (error) {\n console.error(\n `Plugin '${plugin.name}' error in transformState:`,\n error,\n );\n // Continue with untransformed state\n }\n }\n }\n\n return transformedState;\n }\n\n /**\n * Transform event through all plugins\n */\n transformEvent(event: TEvent): TEvent | null {\n let transformedEvent: TEvent | null = event;\n\n for (const plugin of this.getAll()) {\n if (transformedEvent === null) break;\n\n if (plugin.transformEvent && this.canInterceptEvents(plugin)) {\n try {\n transformedEvent = plugin.transformEvent(transformedEvent);\n } catch (error) {\n console.error(\n `Plugin '${plugin.name}' error in transformEvent:`,\n error,\n );\n // Continue with untransformed event\n }\n }\n }\n\n return transformedEvent;\n }\n\n /**\n * Notify plugins of state change\n */\n notifyStateChange(previousState: TState, currentState: TState): void {\n for (const plugin of this.getAll()) {\n if (plugin.onStateChange && this.canReadState(plugin)) {\n try {\n plugin.onStateChange(previousState, currentState);\n } catch (error) {\n console.error(\n `Plugin '${plugin.name}' error in onStateChange:`,\n error,\n );\n }\n }\n }\n }\n\n /**\n * Notify plugins of event\n */\n notifyEvent(event: TEvent): void {\n for (const plugin of this.getAll()) {\n if (plugin.onEvent && this.canReadState(plugin)) {\n try {\n plugin.onEvent(event);\n } catch (error) {\n console.error(`Plugin '${plugin.name}' error in onEvent:`, error);\n }\n }\n }\n }\n\n /**\n * Notify plugins of error\n */\n notifyError(error: Error, context: ErrorContext): void {\n for (const plugin of this.getAll()) {\n if (plugin.onError) {\n try {\n plugin.onError(error, context);\n } catch (hookError) {\n console.error(`Plugin '${plugin.name}' error in onError:`, hookError);\n }\n }\n }\n }\n\n private validateCapabilities(plugin: BlocPlugin<TState, TEvent>): void {\n const caps = plugin.capabilities!;\n\n // Validate logical constraints\n if (caps.transformState && !caps.readState) {\n throw new Error(\n `Plugin '${plugin.name}': transformState requires readState capability`,\n );\n }\n\n if (caps.interceptEvents && !caps.readState) {\n throw new Error(\n `Plugin '${plugin.name}': interceptEvents requires readState capability`,\n );\n }\n }\n\n private canReadState(plugin: BlocPlugin<TState, TEvent>): boolean {\n return !plugin.capabilities || plugin.capabilities.readState !== false;\n }\n\n private canTransformState(plugin: BlocPlugin<TState, TEvent>): boolean {\n return !plugin.capabilities || plugin.capabilities.transformState === true;\n }\n\n private canInterceptEvents(plugin: BlocPlugin<TState, TEvent>): boolean {\n return !plugin.capabilities || plugin.capabilities.interceptEvents === true;\n }\n}\n","import { BlocBase } from '../BlocBase';\nimport { Blac } from '../Blac';\nimport { generateUUID } from '../utils/uuid';\nimport {\n Subscription,\n SubscriptionOptions,\n SubscriptionManagerStats,\n} from './types';\n\n/**\n * Unified subscription manager that replaces the dual consumer/observer system.\n * Handles all state change subscriptions with a single, consistent interface.\n */\nexport class SubscriptionManager<S = unknown> {\n private subscriptions = new Map<string, Subscription<S>>();\n private pathToSubscriptions = new Map<string, Set<string>>();\n private weakRefCleanupScheduled = false;\n private totalNotifications = 0;\n\n constructor(private bloc: BlocBase<S>) {}\n\n /**\n * Subscribe to state changes\n */\n subscribe(options: SubscriptionOptions<S>): () => void {\n const id = `${options.type}-${generateUUID()}`;\n\n const subscription: Subscription<S> = {\n id,\n type: options.type,\n selector: options.selector,\n equalityFn: options.equalityFn || Object.is,\n notify: options.notify,\n priority: options.priority ?? 0,\n weakRef: options.weakRef,\n dependencies: new Set(),\n metadata: {\n lastNotified: Date.now(),\n hasRendered: false,\n accessCount: 0,\n firstAccessTime: Date.now(),\n },\n };\n\n // Initialize selector value if provided\n if (subscription.selector) {\n try {\n subscription.lastValue = subscription.selector(\n this.bloc.state,\n this.bloc,\n );\n } catch (error) {\n Blac.error(`SubscriptionManager: Error in selector for ${id}:`, error);\n }\n }\n\n this.subscriptions.set(id, subscription);\n\n Blac.log(\n `[${this.bloc._name}:${this.bloc._id}] Subscription added: ${id}. Total: ${this.subscriptions.size}`,\n );\n\n // Cancel disposal if bloc is in disposal_requested state\n (this.bloc as any)._cancelDisposalIfRequested();\n\n // Return unsubscribe function\n return () => this.unsubscribe(id);\n }\n\n /**\n * Unsubscribe by ID\n */\n unsubscribe(id: string): void {\n const subscription = this.subscriptions.get(id);\n if (!subscription) return;\n\n // Remove from path dependencies\n if (subscription.dependencies) {\n for (const path of subscription.dependencies) {\n const subs = this.pathToSubscriptions.get(path);\n if (subs) {\n subs.delete(id);\n if (subs.size === 0) {\n this.pathToSubscriptions.delete(path);\n }\n }\n }\n }\n\n this.subscriptions.delete(id);\n\n Blac.log(\n `[${this.bloc._name}:${this.bloc._id}] Subscription removed: ${id}. Remaining: ${this.subscriptions.size}`,\n );\n\n // Check if bloc should be disposed\n this.bloc.checkDisposal();\n }\n\n /**\n * Notify all subscriptions of state change\n */\n notify(newState: S, oldState: S, action?: unknown): void {\n // Clean up dead weak references if needed\n this.cleanupDeadReferences();\n\n // Sort subscriptions by priority (descending)\n const sortedSubscriptions = Array.from(this.subscriptions.values()).sort(\n (a, b) => (b.priority ?? 0) - (a.priority ?? 0),\n );\n\n for (const subscription of sortedSubscriptions) {\n // Check if WeakRef is still alive\n if (subscription.weakRef && !subscription.weakRef.deref()) {\n this.scheduleWeakRefCleanup();\n continue;\n }\n\n let shouldNotify = false;\n let newValue: unknown;\n let oldValue: unknown;\n\n if (subscription.selector) {\n // Use selector to determine if notification is needed\n try {\n newValue = subscription.selector(newState, this.bloc);\n oldValue = subscription.lastValue;\n\n const equalityFn = subscription.equalityFn || Object.is;\n shouldNotify = !equalityFn(oldValue, newValue);\n\n if (shouldNotify) {\n subscription.lastValue = newValue;\n }\n } catch (error) {\n Blac.error(\n `SubscriptionManager: Error in selector for ${subscription.id}:`,\n error,\n );\n continue;\n }\n } else {\n // No selector - check if tracked dependencies changed\n if (subscription.dependencies && subscription.dependencies.size > 0) {\n // Check which paths changed between old and new state\n const changedPaths = this.getChangedPaths(oldState, newState);\n shouldNotify = this.shouldNotifyForPaths(\n subscription.id,\n changedPaths,\n );\n if ((Blac.config as any).logLevel === 'debug') {\n Blac.log(\n `[SubscriptionManager] Subscription ${subscription.id} dependencies:`,\n Array.from(subscription.dependencies),\n );\n Blac.log(\n `[SubscriptionManager] Changed paths:`,\n Array.from(changedPaths),\n );\n Blac.log(`[SubscriptionManager] Should notify:`, shouldNotify);\n }\n } else {\n // No tracked dependencies, always notify\n shouldNotify = true;\n }\n newValue = newState;\n oldValue = oldState;\n }\n\n if (shouldNotify) {\n try {\n subscription.notify(newValue, oldValue, action);\n this.totalNotifications++;\n\n if (subscription.metadata) {\n subscription.metadata.lastNotified = Date.now();\n subscription.metadata.hasRendered = true;\n }\n } catch (error) {\n Blac.error(\n `SubscriptionManager: Error in notify for ${subscription.id}:`,\n error,\n );\n }\n }\n }\n }\n\n /**\n * Track a path access for a subscription\n */\n trackAccess(subscriptionId: string, path: string, value?: unknown): void {\n const subscription = this.subscriptions.get(subscriptionId);\n if (!subscription) return;\n\n // Update dependencies\n if (!subscription.dependencies) {\n subscription.dependencies = new Set();\n }\n subscription.dependencies.add(path);\n\n // Update path-to-subscription mapping\n let subs = this.pathToSubscriptions.get(path);\n if (!subs) {\n subs = new Set();\n this.pathToSubscriptions.set(path, subs);\n }\n subs.add(subscriptionId);\n\n // Update metadata\n if (subscription.metadata) {\n subscription.metadata.accessCount =\n (subscription.metadata.accessCount || 0) + 1;\n subscription.metadata.lastAccessTime = Date.now();\n }\n }\n\n /**\n * Get the paths that changed between two states\n */\n private getChangedPaths(\n oldState: any,\n newState: any,\n path = '',\n ): Set<string> {\n const changedPaths = new Set<string>();\n\n if (oldState === newState) return changedPaths;\n\n // Handle primitives\n if (\n typeof oldState !== 'object' ||\n typeof newState !== 'object' ||\n oldState === null ||\n newState === null\n ) {\n if (path) changedPaths.add(path);\n return changedPaths;\n }\n\n // Get all keys from both objects\n const allKeys = new Set([\n ...Object.keys(oldState),\n ...Object.keys(newState),\n ]);\n\n for (const key of allKeys) {\n const fullPath = path ? `${path}.${key}` : key;\n const oldValue = oldState[key];\n const newValue = newState[key];\n\n if (oldValue !== newValue) {\n changedPaths.add(fullPath);\n\n // For nested objects, get all nested changed paths\n if (\n typeof oldValue === 'object' &&\n typeof newValue === 'object' &&\n oldValue !== null &&\n newValue !== null\n ) {\n const nestedChanges = this.getChangedPaths(\n oldValue,\n newValue,\n fullPath,\n );\n nestedChanges.forEach((p) => changedPaths.add(p));\n }\n }\n }\n\n return changedPaths;\n }\n\n /**\n * Check if a subscription should be notified based on changed paths\n */\n shouldNotifyForPaths(\n subscriptionId: string,\n changedPaths: Set<string>,\n ): boolean {\n const subscription = this.subscriptions.get(subscriptionId);\n if (!subscription || !subscription.dependencies) return true;\n\n // Check if any tracked dependencies match changed paths\n for (const trackedPath of subscription.dependencies) {\n // Handle class getter dependencies (_class.propertyName)\n if (trackedPath.startsWith('_class.')) {\n // For class getters, we need to notify on any state change\n // since we can't determine which state properties the getter depends on\n // This is conservative but ensures correctness\n if (changedPaths.size > 0) {\n return true;\n }\n continue;\n }\n\n // Check direct path matches\n if (changedPaths.has(trackedPath)) return true;\n\n // Check nested paths\n for (const changedPath of changedPaths) {\n if (\n changedPath.startsWith(trackedPath + '.') ||\n trackedPath.startsWith(changedPath + '.')\n ) {\n return true;\n }\n }\n }\n\n return false;\n }\n\n /**\n * Get statistics about subscriptions\n */\n getStats(): SubscriptionManagerStats {\n let consumerCount = 0;\n let observerCount = 0;\n\n for (const sub of this.subscriptions.values()) {\n if (sub.type === 'consumer') consumerCount++;\n else observerCount++;\n }\n\n return {\n activeSubscriptions: this.subscriptions.size,\n consumerCount,\n observerCount,\n totalNotifications: this.totalNotifications,\n trackedDependencies: this.pathToSubscriptions.size,\n };\n }\n\n /**\n * Clear all subscriptions\n */\n clear(): void {\n this.subscriptions.clear();\n this.pathToSubscriptions.clear();\n }\n\n /**\n * Get subscription by ID\n */\n getSubscription(id: string): Subscription<S> | undefined {\n return this.subscriptions.get(id);\n }\n\n /**\n * Check if there are any active subscriptions\n */\n get hasSubscriptions(): boolean {\n return this.subscriptions.size > 0;\n }\n\n /**\n * Get count of active subscriptions\n */\n get size(): number {\n return this.subscriptions.size;\n }\n\n /**\n * Clean up subscriptions with dead weak references\n */\n private cleanupDeadReferences(): void {\n if (!this.weakRefCleanupScheduled) return;\n\n const deadIds: string[] = [];\n\n for (const [id, subscription] of this.subscriptions) {\n if (subscription.weakRef && !subscription.weakRef.deref()) {\n deadIds.push(id);\n }\n }\n\n for (const id of deadIds) {\n this.unsubscribe(id);\n }\n\n this.weakRefCleanupScheduled = false;\n }\n\n /**\n * Schedule weak reference cleanup for next tick\n */\n private scheduleWeakRefCleanup(): void {\n if (this.weakRefCleanupScheduled) return;\n\n this.weakRefCleanupScheduled = true;\n queueMicrotask(() => this.cleanupDeadReferences());\n }\n}\n","/**\n * Manages batching of state updates to optimize performance\n */\nexport class BatchingManager<S> {\n private pendingUpdates: Array<{\n newState: S;\n oldState: S;\n action?: unknown;\n }> = [];\n private isBatching = false;\n\n /**\n * Execute a callback with batched updates\n */\n batchUpdates(\n callback: () => void,\n onFlush: (finalUpdate: {\n newState: S;\n oldState: S;\n action?: unknown;\n }) => void,\n ): void {\n if (this.isBatching) {\n callback();\n return;\n }\n\n this.isBatching = true;\n this.pendingUpdates = [];\n\n try {\n callback();\n\n if (this.pendingUpdates.length > 0) {\n const finalUpdate = this.pendingUpdates[this.pendingUpdates.length - 1];\n onFlush(finalUpdate);\n }\n } finally {\n this.isBatching = false;\n this.pendingUpdates = [];\n }\n }\n\n /**\n * Add an update to the batch\n */\n addUpdate(update: { newState: S; oldState: S; action?: unknown }): void {\n if (this.isBatching) {\n this.pendingUpdates.push(update);\n }\n }\n\n /**\n * Check if currently batching\n */\n get isCurrentlyBatching(): boolean {\n return this.isBatching;\n }\n}\n","import { generateUUID } from './utils/uuid';\nimport { BlocPlugin } from './plugins/types';\nimport { BlocPluginRegistry } from './plugins/BlocPluginRegistry';\nimport { SubscriptionManager } from './subscription/SubscriptionManager';\nimport {\n BlocLifecycleManager,\n BlocLifecycleState,\n StateTransitionResult,\n} from './lifecycle/BlocLifecycle';\nimport { BatchingManager } from './utils/BatchingManager';\nimport type { Blac } from './Blac';\n\nexport type BlocInstanceId = string | number | undefined;\n\ninterface BlocStaticProperties {\n isolated: boolean;\n keepAlive: boolean;\n plugins?: BlocPlugin<any, any>[];\n}\n\n/**\n * Base class for both Blocs and Cubits using unified subscription model.\n */\nexport abstract class BlocBase<S> {\n public uid = generateUUID();\n blacInstance?: Blac;\n\n static isolated = false;\n get isIsolated() {\n return this._isolated;\n }\n\n static keepAlive = false;\n get isKeepAlive() {\n return this._keepAlive;\n }\n\n public _isolated = false;\n public _id: BlocInstanceId;\n public _instanceRef?: string;\n public _name: string;\n\n /**\n * Unified subscription manager for all state notifications\n */\n public _subscriptionManager: SubscriptionManager<S>;\n\n _state: S;\n private _lifecycleManager = new BlocLifecycleManager();\n private _batchingManager = new BatchingManager<S>();\n _keepAlive = false;\n public lastUpdate?: number;\n\n _plugins = new BlocPluginRegistry<S, any>();\n\n onDispose?: () => void;\n\n /**\n * Creates a new BlocBase instance with unified subscription management\n */\n constructor(initialState: S) {\n this._state = initialState;\n this._id = this.constructor.name;\n this._name = this.constructor.name;\n\n // Initialize unified subscription system\n this._subscriptionManager = new SubscriptionManager(this as any);\n\n // Access static properties\n const Constructor = this.constructor as typeof BlocBase &\n BlocStaticProperties;\n\n this._keepAlive =\n typeof Constructor.keepAlive === 'boolean'\n ? Constructor.keepAlive\n : false;\n this._isolated =\n typeof Constructor.isolated === 'boolean' ? Constructor.isolated : false;\n\n // Initialize plugin registry\n this._plugins = new BlocPluginRegistry<S, any>();\n\n // Register static plugins\n if (Constructor.plugins && Array.isArray(Constructor.plugins)) {\n for (const plugin of Constructor.plugins) {\n this._plugins.add(plugin);\n }\n }\n\n // Attach all plugins\n this._plugins.attach(this);\n }\n\n /**\n * Returns the current state\n */\n get state(): S {\n if (this._lifecycleManager.isDisposed) {\n return this._state; // Return last known state for disposed blocs\n }\n return this._state;\n }\n\n /**\n * Subscribe to all state changes\n */\n subscribe(callback: (state: S) => void): () => void {\n return this._subscriptionManager.subscribe({\n type: 'observer',\n notify: (state) => callback(state as S),\n });\n }\n\n /**\n * Subscribe with a selector for optimized updates\n */\n subscribeWithSelector<T>(\n selector: (state: S) => T,\n callback: (value: T) => void,\n equalityFn?: (a: T, b: T) => boolean,\n ): () => void {\n return this._subscriptionManager.subscribe({\n type: 'consumer',\n selector: selector as any,\n equalityFn: equalityFn as any,\n notify: (value) => callback(value as T),\n });\n }\n\n /**\n * Subscribe with React component reference for automatic cleanup\n */\n subscribeComponent(\n componentRef: WeakRef<object>,\n callback: () => void,\n ): () => void {\n return this._subscriptionManager.subscribe({\n type: 'consumer',\n weakRef: componentRef,\n notify: callback,\n });\n }\n\n /**\n * Get current subscription count\n */\n get subscriptionCount(): number {\n return this._subscriptionManager.size;\n }\n\n /**\n * Track property access for a subscription\n */\n trackAccess(subscriptionId: string, path: string, value?: unknown): void {\n this._subscriptionManager.trackAccess(subscriptionId, path, value);\n }\n\n /**\n * Emit a new state\n */\n protected emit(newState: S, action?: unknown): void {\n this._pushState(newState, this._state, action);\n }\n\n /**\n * Internal state push method used by Bloc\n */\n _pushState(newState: S, oldState: S, action?: unknown): void {\n // Validate state emission conditions\n if (this._lifecycleManager.currentState !== BlocLifecycleState.ACTIVE) {\n this.blacInstance?.error(\n `[${this._name}:${this._id}] Attempted state update on ${this._lifecycleManager.currentState} bloc. Update ignored.`,\n );\n return;\n }\n\n if (newState === undefined) {\n return; // Silent failure for undefined states\n }\n\n this._state = newState;\n\n // Apply plugins\n const transformedState = this._plugins.transformState(\n oldState,\n newState,\n ) as S;\n this._state = transformedState;\n\n // Notify plugins of state change\n this._plugins.notifyStateChange(oldState, transformedState);\n\n // Notify system plugins of state change\n this.blacInstance?.plugins.notifyStateChanged(\n this as any,\n oldState,\n transformedState,\n );\n\n // Handle batching\n if (this._batchingManager.isCurrentlyBatching) {\n this._batchingManager.addUpdate({\n newState: transformedState,\n oldState,\n action,\n });\n return;\n }\n\n // Notify all subscriptions\n this._subscriptionManager.notify(transformedState, oldState, action);\n this.lastUpdate = Date.now();\n }\n\n _batchUpdates(callback: () => void): void {\n this._batchingManager.batchUpdates(callback, (finalUpdate) => {\n this._subscriptionManager.notify(\n finalUpdate.newState,\n finalUpdate.oldState,\n finalUpdate.action,\n );\n });\n }\n\n /**\n * Add a plugin\n */\n addPlugin(plugin: BlocPlugin<S, any>): void {\n this._plugins.add(plugin);\n\n // If plugins are already attached (bloc is active), attach the new plugin\n if ((this._plugins as any).attached && plugin.onAttach) {\n try {\n plugin.onAttach(this);\n } catch (error) {\n console.error(`Plugin '${plugin.name}' error in onAttach:`, error);\n }\n }\n }\n\n /**\n * Remove a plugin\n */\n removePlugin(plugin: BlocPlugin<S, any>): void {\n this._plugins.remove(plugin.name);\n }\n\n /**\n * Get all plugins\n */\n get plugins(): ReadonlyArray<BlocPlugin<S, any>> {\n return this._plugins.getAll();\n }\n\n /**\n * Disposal management\n */\n get isDisposed(): boolean {\n return this._lifecycleManager.isDisposed;\n }\n\n /**\n * Atomic state transition for disposal\n */\n _atomicStateTransition(\n expectedState: BlocLifecycleState,\n newState: BlocLifecycleState,\n ): StateTransitionResult {\n return this._lifecycleManager.atomicStateTransition(\n expectedState,\n newState,\n );\n }\n\n /**\n * Dispose the bloc and clean up resources\n */\n async dispose(): Promise<void> {\n const transitionResult = this._lifecycleManager.atomicStateTransition(\n BlocLifecycleState.ACTIVE,\n BlocLifecycleState.DISPOSING,\n );\n\n if (!transitionResult.success) {\n if (\n this._lifecycleManager.currentState ===\n BlocLifecycleState.DISPOSAL_REQUESTED\n ) {\n this._lifecycleManager.atomicStateTransition(\n BlocLifecycleState.DISPOSAL_REQUESTED,\n BlocLifecycleState.DISPOSING,\n );\n } else {\n return;\n }\n }\n\n try {\n // Clear subscriptions\n this._subscriptionManager.clear();\n\n // Call disposal hook\n if (this.onDispose) {\n this.onDispose();\n }\n\n // Notify plugins of disposal\n for (const plugin of this._plugins.getAll()) {\n try {\n if ('onDispose' in plugin && typeof plugin.onDispose === 'function') {\n plugin.onDispose(this as any);\n }\n } catch (error) {\n console.error('Plugin disposal error:', error);\n }\n }\n\n // Call disposal handler\n const handler = this._lifecycleManager.getDisposalHandler();\n if (handler) {\n handler(this as any);\n }\n } finally {\n this._lifecycleManager.atomicStateTransition(\n BlocLifecycleState.DISPOSING,\n BlocLifecycleState.DISPOSED,\n );\n }\n }\n\n /**\n * Schedule disposal when no subscriptions remain\n */\n _scheduleDisposal(): void {\n const shouldDispose =\n this._subscriptionManager.size === 0 && !this._keepAlive;\n\n if (!shouldDispose) {\n return;\n }\n\n this._lifecycleManager.scheduleDisposal(\n 16,\n () => this._subscriptionManager.size === 0 && !this._keepAlive,\n () => this.dispose(),\n );\n }\n\n /**\n * Set disposal handler\n */\n setDisposalHandler(handler: (bloc: BlocBase<unknown>) => void): void {\n this._lifecycleManager.setDisposalHandler(\n handler as (bloc: unknown) => void,\n );\n }\n\n /**\n * Check if disposal should be scheduled (called by subscription manager)\n */\n checkDisposal(): void {\n if (\n this._subscriptionManager.size === 0 &&\n !this._keepAlive &&\n this._lifecycleManager.currentState === BlocLifecycleState.ACTIVE\n ) {\n this._scheduleDisposal();\n }\n }\n\n /**\n * Cancel disposal if bloc is in disposal_requested state\n */\n _cancelDisposalIfRequested(): void {\n this.blacInstance?.log(\n `[${this._name}:${this._id}] _cancelDisposalIfRequested called. Current state: ${this._lifecycleManager.currentState}`,\n );\n\n const success = this._lifecycleManager.cancelDisposal();\n\n if (success) {\n this.blacInstance?.log(\n `[${this._name}:${this._id}] Disposal cancelled - new subscription added`,\n );\n } else if (\n this._lifecycleManager.currentState ===\n BlocLifecycleState.DISPOSAL_REQUESTED\n ) {\n this.blacInstance?.warn(\n `[${this._name}:${this._id}] Failed to cancel disposal. Current state: ${this._lifecycleManager.currentState}`,\n );\n } else if (this._lifecycleManager.isDisposed) {\n this.blacInstance?.error(\n `[${this._name}:${this._id}] Cannot cancel disposal - bloc is already disposed`,\n );\n }\n }\n}\n","import { Blac } from './Blac';\nimport { BlocBase } from './BlocBase';\nimport { BlocEventConstraint } from './types';\n\nexport abstract class Bloc<\n S, // State type\n A extends BlocEventConstraint = BlocEventConstraint, // Base Action/Event type with proper constraints\n> extends BlocBase<S> {\n readonly eventHandlers: Map<\n new (...args: any[]) => A,\n (event: A, emit: (newState: S) => void) => void | Promise<void>\n > = new Map();\n\n /**\n * @internal\n * Event queue to ensure sequential processing of async events\n */\n private _eventQueue: A[] = [];\n\n /**\n * @internal\n * Flag indicating if an event is currently being processed\n */\n private _isProcessingEvent = false;\n\n /**\n * Registers an event handler for a specific event type.\n * This method is typically called in the constructor of a derived Bloc class.\n * @param eventConstructor The constructor of the event to handle (e.g., LoadDataEvent).\n * @param handler A function that processes the event and can emit new states.\n * The 'event' parameter in the handler will be typed to the specific eventConstructor.\n */\n protected on<E extends A>(\n eventConstructor: new (...args: any[]) => E,\n handler: (event: E, emit: (newState: S) => void) => void | Promise<void>,\n ): void {\n if (this.eventHandlers.has(eventConstructor)) {\n Blac.warn(\n `[Bloc ${this._name}:${String(this._id)}] Handler for event '${eventConstructor.name}' already registered. It will be overwritten.`,\n );\n }\n this.eventHandlers.set(\n eventConstructor,\n handler as (\n event: A,\n emit: (newState: S) => void,\n ) => void | Promise<void>,\n );\n }\n\n /**\n * Dispatches an action/event to the Bloc.\n * Events are queued and processed sequentially to prevent race conditions.\n * @param action The action/event instance to be processed.\n */\n public add = async (action: A): Promise<void> => {\n // Transform event through plugins\n let transformedAction: A | null = action;\n try {\n transformedAction = (this._plugins as any).transformEvent(action);\n } catch (error) {\n console.error('Error transforming event:', error);\n // Continue with original event if transformation fails\n }\n\n // If event was cancelled by plugin, don't process it\n if (transformedAction === null) {\n return;\n }\n\n // Notify bloc plugins of event\n try {\n (this._plugins as any).notifyEvent(transformedAction);\n } catch (error) {\n console.error('Error notifying plugins of event:', error);\n }\n\n // Notify system plugins of event\n Blac.instance.plugins.notifyEventAdded(this as any, transformedAction);\n\n this._eventQueue.push(transformedAction);\n\n if (!this._isProcessingEvent) {\n await this._processEventQueue();\n }\n };\n\n /**\n * @internal\n * Processes events from the queue sequentially\n */\n private async _processEventQueue(): Promise<void> {\n if (this._isProcessingEvent) {\n return;\n }\n\n this._isProcessingEvent = true;\n\n try {\n while (this._eventQueue.length > 0) {\n const action = this._eventQueue.shift()!;\n await this._processEvent(action);\n }\n } finally {\n this._isProcessingEvent = false;\n }\n }\n\n /**\n * @internal\n * Processes a single event\n */\n private async _processEvent(action: A): Promise<void> {\n const eventConstructor = action.constructor as new (...args: any[]) => A;\n const handler = this.eventHandlers.get(eventConstructor);\n\n if (handler) {\n const emit = (newState: S): void => {\n const previousState = this.state; // State just before this specific emission\n this._pushState(newState, previousState, action);\n };\n\n try {\n await handler(action, emit);\n } catch (error) {\n const constructorName =\n (action.constructor as { name?: string }).name ||\n 'UnnamedConstructor';\n const errorContext = {\n blocName: this._name,\n blocId: String(this._id),\n eventType: constructorName,\n currentState: this.state,\n action: action,\n timestamp: new Date().toISOString(),\n };\n\n Blac.error(\n `[Bloc ${this._name}:${String(this._id)}] Error in event handler for '${constructorName}':`,\n error,\n 'Context:',\n errorContext,\n );\n\n // Notify plugins of the error\n if (error instanceof Error) {\n try {\n this._plugins.notifyError(error, {\n phase: 'event-processing',\n operation: 'handler',\n metadata: { event: action },\n });\n\n Blac.instance.plugins.notifyError(error, this as any, {\n phase: 'event-processing',\n operation: 'handler',\n metadata: { event: action },\n });\n } catch (pluginError) {\n console.error('Error notifying plugins:', pluginError);\n }\n }\n\n if (error instanceof Error && error.name === 'CriticalError') {\n throw error;\n }\n }\n } else {\n const constructorName =\n (action.constructor as { name?: string }).name || 'UnnamedConstructor';\n Blac.warn(\n `[Bloc ${this._name}:${String(this._id)}] No handler registered for action type: '${constructorName}'.`,\n 'Registered handlers:',\n Array.from(this.eventHandlers.keys()).map((k) => k.name),\n 'Action was:',\n action,\n );\n }\n }\n}\n","import { Blac } from './Blac';\nimport { BlocBase } from './BlocBase';\n\n/**\n * A Cubit is a simpler version of a Bloc that doesn't handle events.\n * It manages state and provides methods to update it.\n * @template S - The type of state this Cubit manages\n */\nexport abstract class Cubit<S> extends BlocBase<S> {\n /**\n * Updates the current state and notifies all observers of the change.\n * If the new state is identical to the current state (using Object.is),\n * no update will occur.\n * @param state - The new state to set\n */\n emit(state: S): void {\n if (Object.is(state, this.state)) {\n return;\n }\n\n const oldState = this.state;\n const newState = state;\n this._pushState(newState, oldState);\n }\n\n /**\n * Partially updates the current state by merging it with the provided state patch.\n * This method is only applicable when the state is an object type.\n *\n * @param statePatch - A partial state object containing only the properties to update\n * @param ignoreChangeCheck - If true, skips checking if the state has actually changed\n * @throws {TypeError} If the state is not an object type\n */\n patch(\n statePatch: S extends object ? Partial<S> : S,\n ignoreChangeCheck = false,\n ): void {\n if (typeof this.state !== 'object' || this.state === null) {\n Blac.warn(\n 'Cubit.patch: was called on a cubit where the state is not an object. This is a no-op.',\n );\n return;\n }\n\n let changes = false;\n if (!ignoreChangeCheck) {\n for (const key in statePatch) {\n if (Object.prototype.hasOwnProperty.call(statePatch, key)) {\n const s = this.state;\n const current = s[key as keyof S];\n if (!Object.is(statePatch[key as keyof S], current)) {\n changes = true;\n break;\n }\n }\n }\n } else {\n changes = true;\n }\n\n if (changes) {\n this.emit({\n ...this.state,\n ...(statePatch as Partial<S>),\n } as S);\n }\n }\n}\n","/**\n * Event fired when props are updated on a Bloc or Cubit instance.\n * This is primarily used internally by the framework to notify\n * about prop changes in React components.\n * @template P - The type of props being updated\n */\nexport class PropsUpdated<P = any> {\n constructor(public readonly props: P) {}\n}\n","/**\n * Performs a shallow equality comparison between two values.\n * For objects, it checks if all top-level properties are equal using Object.is.\n * @param a First value to compare\n * @param b Second value to compare\n * @returns true if values are shallowly equal, false otherwise\n */\nexport function shallowEqual(a: any, b: any): boolean {\n if (Object.is(a, b)) {\n return true;\n }\n\n if (\n typeof a !== 'object' ||\n a === null ||\n typeof b !== 'object' ||\n b === null\n ) {\n return false;\n }\n\n const keysA = Object.keys(a);\n const keysB = Object.keys(b);\n\n if (keysA.length !== keysB.length) {\n return false;\n }\n\n for (let i = 0; i < keysA.length; i++) {\n const key = keysA[i];\n if (\n !Object.prototype.hasOwnProperty.call(b, key) ||\n !Object.is(a[key], b[key])\n ) {\n return false;\n }\n }\n\n return true;\n}\n","/**\n * Generates a deterministic instance ID from static props by extracting primitive values\n *\n * Rules:\n * 1. Only considers primitive types: string, number, boolean, null, undefined\n * 2. Ignores complex types: objects, arrays, functions, symbols\n * 3. Sorts keys alphabetically for deterministic output\n * 4. Returns undefined if no primitives found (caller should use default ID)\n */\nexport function generateInstanceIdFromProps(\n props: unknown,\n): string | undefined {\n if (!props || typeof props !== 'object') {\n return undefined;\n }\n\n const primitives: Array<[string, unknown]> = [];\n\n // Extract primitive values\n for (const [key, value] of Object.entries(props)) {\n const type = typeof value;\n if (\n type === 'string' ||\n type === 'number' ||\n type === 'boolean' ||\n value === null ||\n value === undefined\n ) {\n primitives.push([key, value]);\n }\n }\n\n // No primitives found\n if (primitives.length === 0) {\n return undefined;\n }\n\n // Sort by key for deterministic output\n primitives.sort(([a], [b]) => a.localeCompare(b));\n\n // Create instance ID\n const parts: string[] = [];\n for (const [key, value] of primitives) {\n if (value === null) {\n parts.push(`${key}:null`);\n } else if (value === undefined) {\n parts.push(`${key}:undefined`);\n } else {\n parts.push(`${key}:${String(value)}`);\n }\n }\n\n return parts.join('|');\n}\n","import { Blac } from '../Blac';\nimport { BlocBase } from '../BlocBase';\n\nexport interface RerenderInfo {\n componentName: string;\n blocName: string;\n blocId: string;\n renderCount: number;\n reason: RerenderReason;\n timestamp: number;\n duration?: number;\n stackTrace?: string;\n}\n\nexport interface RerenderReason {\n type:\n | 'state-change'\n | 'dependency-change'\n | 'mount'\n | 'props-change'\n | 'unknown';\n changedPaths?: string[];\n oldValues?: Record<string, any>;\n newValues?: Record<string, any>;\n dependencies?: string[];\n description?: string;\n}\n\n/**\n * Utility class for logging component rerenders with detailed debugging information\n */\nexport class RerenderLogger {\n private static componentRenderCounts = new Map<string, number>();\n private static lastRenderTimestamps = new Map<string, number>();\n private static groupedLogs = new Map<string, RerenderInfo[]>();\n private static groupTimeouts = new Map<string, NodeJS.Timeout>();\n\n /**\n * Log a component rerender with detailed information\n */\n static logRerender(info: RerenderInfo): void {\n // RerenderLogger is now controlled by the RenderLoggingPlugin\n // This method is called by the plugin which already handles configuration\n const config = (Blac as any)._config?.rerenderLogging;\n if (!config) return;\n\n // Parse config\n const loggingConfig = this.parseConfig(config);\n if (!loggingConfig.enabled) return;\n\n // Apply filter if provided\n if (\n loggingConfig.filter &&\n !loggingConfig.filter({\n componentName: info.componentName,\n blocName: info.blocName,\n })\n ) {\n return;\n }\n\n // Track render count\n const key = `${info.componentName}-${info.blocId}`;\n const currentCount = this.componentRenderCounts.get(key) || 0;\n this.componentRenderCounts.set(key, currentCount + 1);\n info.renderCount = currentCount + 1;\n\n // Calculate duration if possible\n const lastTimestamp = this.lastRenderTimestamps.get(key);\n if (lastTimestamp) {\n info.duration = info.timestamp - lastTimestamp;\n }\n this.lastRenderTimestamps.set(key, info.timestamp);\n\n // Add stack trace if requested\n if (loggingConfig.includeStackTrace && loggingConfig.level === 'detailed') {\n info.stackTrace = new Error().stack;\n }\n\n // Handle grouping\n if (loggingConfig.groupRerenders) {\n this.logGrouped(info, loggingConfig);\n } else {\n this.logImmediate(info, loggingConfig);\n }\n }\n\n /**\n * Parse the logging configuration\n */\n private static parseConfig(config: any) {\n if (config === true) {\n return { enabled: true, level: 'normal' as const };\n }\n if (typeof config === 'string') {\n return {\n enabled: true,\n level:\n config === 'minimal' ? ('minimal' as const) : ('detailed' as const),\n };\n }\n return {\n enabled: config.enabled,\n level: config.level || ('normal' as const),\n filter: config.filter,\n includeStackTrace: config.includeStackTrace,\n groupRerenders: config.groupRerenders,\n };\n }\n\n /**\n * Log immediately without grouping\n */\n private static logImmediate(\n info: RerenderInfo,\n config: ReturnType<typeof RerenderLogger.parseConfig>,\n ): void {\n const message = this.formatMessage(info, config.level!);\n\n if (config.level === 'detailed') {\n console.group(message.header);\n if (message.details) console.log(message.details);\n if (message.values) console.table(message.values);\n if (info.stackTrace) console.log('Stack trace:', info.stackTrace);\n console.groupEnd();\n } else {\n console.log(message.header, message.details || '');\n }\n }\n\n /**\n * Log with grouping (batch multiple rerenders)\n */\n private static logGrouped(\n info: RerenderInfo,\n config: ReturnType<typeof RerenderLogger.parseConfig>,\n ): void {\n const groupKey = `${info.componentName}-${info.blocId}`;\n\n // Clear existing timeout\n const existingTimeout = this.groupTimeouts.get(groupKey);\n if (existingTimeout) {\n clearTimeout(existingTimeout);\n }\n\n // Add to group\n const group = this.groupedLogs.get(groupKey) || [];\n group.push(info);\n this.groupedLogs.set(groupKey, group);\n\n // Set new timeout\n const timeout = setTimeout(() => {\n const logs = this.groupedLogs.get(groupKey) || [];\n this.groupedLogs.delete(groupKey);\n this.groupTimeouts.delete(groupKey);\n\n if (logs.length === 1) {\n this.logImmediate(logs[0], config);\n } else {\n console.group(\n `🔄 ${info.componentName} rendered ${logs.length} times (${info.blocName})`,\n );\n logs.forEach((log, index) => {\n const message = this.formatMessage(log, config.level!);\n console.log(` ${index + 1}. ${message.details || message.header}`);\n });\n console.groupEnd();\n }\n }, 50); // 50ms debounce\n\n this.groupTimeouts.set(groupKey, timeout);\n }\n\n /**\n * Format the log message based on level\n */\n private static formatMessage(\n info: RerenderInfo,\n level: 'minimal' | 'normal' | 'detailed',\n ) {\n const emoji = this.getReasonEmoji(info.reason.type);\n\n if (level === 'minimal') {\n return {\n header: `${emoji} ${info.componentName} #${info.renderCount}`,\n details: null,\n values: null,\n };\n }\n\n const header = `${emoji} ${info.componentName} rerender #${info.renderCount} (${info.blocName})`;\n\n let details = `Reason: ${info.reason.description || info.reason.type}`;\n\n if (info.duration !== undefined) {\n details += ` | Time since last: ${info.duration}ms`;\n }\n\n if (\n level === 'normal' &&\n info.reason.changedPaths &&\n info.reason.changedPaths.length > 0\n ) {\n details += ` | Changed: ${info.reason.changedPaths.join(', ')}`;\n }\n\n let values: Record<string, { old: any; new: any }> | null = null;\n if (\n level === 'detailed' &&\n info.reason.changedPaths &&\n info.reason.changedPaths.length > 0\n ) {\n values = {};\n info.reason.changedPaths.forEach((path) => {\n values![path] = {\n old: info.reason.oldValues?.[path],\n new: info.reason.newValues?.[path],\n };\n });\n\n // If we have values to show in detailed mode, ensure they're not empty\n if (Object.keys(values).length === 0) {\n values = null;\n }\n }\n\n return { header, details, values };\n }\n\n /**\n * Get emoji for reason type\n */\n private static getReasonEmoji(type: RerenderReason['type']): string {\n switch (type) {\n case 'state-change':\n return '📊';\n case 'dependency-change':\n return '🔗';\n case 'mount':\n return '🚀';\n case 'props-change':\n return '📦';\n default:\n return '🔄';\n }\n }\n\n /**\n * Clear all tracking data\n */\n static clear(): void {\n this.componentRenderCounts.clear();\n this.lastRenderTimestamps.clear();\n this.groupedLogs.clear();\n this.groupTimeouts.forEach((timeout) => clearTimeout(timeout));\n this.groupTimeouts.clear();\n }\n\n /**\n * Get render count for a component\n */\n static getRenderCount(componentName: string, blocId: string): number {\n return this.componentRenderCounts.get(`${componentName}-${blocId}`) || 0;\n }\n}\n","import { Blac } from './Blac';\nimport { Bloc } from './Bloc';\nimport { BlocBase } from './BlocBase';\nimport { Cubit } from './Cubit';\nimport { BlocEventConstraint } from './types';\n\n/**\n * Test utilities for Blac state management\n */\nexport class BlocTest {\n private static originalInstance: Blac;\n\n /**\n * Sets up a clean test environment\n */\n static setUp(): void {\n this.originalInstance = Blac.instance;\n Blac.resetInstance();\n Blac.enableLog = false; // Disable logging in tests by default\n }\n\n /**\n * Tears down the test environment and restores original state\n */\n static tearDown(): void {\n Blac.resetInstance();\n // Note: Cannot restore original instance due to singleton pattern\n // Tests should use setUp/tearDown properly to manage state\n }\n\n /**\n * Creates a test bloc with automatic cleanup\n */\n static createBloc<T extends BlocBase<any>>(\n BlocClass: new (...args: any[]) => T,\n ...args: any[]\n ): T {\n const bloc = new BlocClass(...args);\n Blac.activateBloc(bloc);\n return bloc;\n }\n\n /**\n * Waits for a bloc to emit a specific state\n */\n static async waitForState<T extends BlocBase<S>, S>(\n bloc: T,\n predicate: (state: S) => boolean,\n timeout = 5000,\n ): Promise<S> {\n return new Promise<S>((resolve, reject) => {\n const timeoutId = setTimeout(() => {\n reject(\n new Error(\n `Timeout waiting for state matching predicate after ${timeout}ms`,\n ),\n );\n }, timeout);\n\n const unsubscribe = bloc.subscribe((newState: S) => {\n if (predicate(newState)) {\n clearTimeout(timeoutId);\n unsubscribe();\n resolve(newState);\n }\n });\n\n // Check current state immediately\n if (predicate(bloc.state)) {\n clearTimeout(timeoutId);\n unsubscribe();\n resolve(bloc.state);\n }\n });\n }\n\n /**\n * Expects a bloc to emit specific states in order\n */\n static async expectStates<T extends BlocBase<S>, S>(\n bloc: T,\n expectedStates: S[],\n timeout = 5000,\n ): Promise<void> {\n const receivedStates: S[] = [];\n\n return new Promise<void>((resolve, reject) => {\n const timeoutId = setTimeout(() => {\n reject(\n new Error(\n `Timeout waiting for states. Expected: ${JSON.stringify(expectedStates)}, ` +\n `Received: ${JSON.stringify(receivedStates)}`,\n ),\n );\n }, timeout);\n\n const unsubscribe = bloc.subscribe((newState: S) => {\n receivedStates.push(newState);\n\n // Check if we have all expected states\n if (receivedStates.length === expectedStates.length) {\n clearTimeout(timeoutId);\n unsubscribe();\n\n // Verify all states match using deep equality\n for (let i = 0; i < expectedStates.length; i++) {\n const expected = expectedStates[i];\n const received = receivedStates[i];\n\n // Use JSON comparison for deep equality\n if (JSON.stringify(expected) !== JSON.stringify(received)) {\n reject(\n new Error(\n `State mismatch at index ${i}. Expected: ${JSON.stringify(expected)}, ` +\n `Received: ${JSON.stringify(received)}`,\n ),\n );\n return;\n }\n }\n\n resolve();\n }\n });\n });\n }\n}\n\n/**\n * Mock Bloc for testing\n */\nexport class MockBloc<\n S,\n A extends BlocEventConstraint = BlocEventConstraint,\n> extends Bloc<S, A> {\n private mockHandlers = new Map<\n string,\n (event: A, emit: (newState: S) => void) => void | Promise<void>\n >();\n\n constructor(initialState: S) {\n super(initialState);\n }\n\n /**\n * Mock an event handler for testing\n */\n mockEventHandler<E extends A>(\n eventConstructor: new (...args: any[]) => E,\n handler: (event: E, emit: (newState: S) => void) => void | Promise<void>,\n ): void {\n // Use the on method to register the mock handler\n this.on(eventConstructor, handler);\n }\n\n /**\n * Get the number of registered handlers\n */\n getHandlerCount(): number {\n return this.eventHandlers.size;\n }\n\n /**\n * Check if a handler is registered for an event type\n */\n hasHandler(eventConstructor: new (...args: any[]) => A): boolean {\n return this.eventHandlers.has(eventConstructor);\n }\n}\n\n/**\n * Mock Cubit for testing\n */\nexport class MockCubit<S> extends Cubit<S> {\n private stateHistory: S[] = [];\n\n constructor(initialState: S) {\n super(initialState);\n this.stateHistory.push(initialState);\n }\n\n /**\n * Override emit to track state history\n */\n emit(newState: S): void {\n this.stateHistory.push(newState);\n super.emit(newState);\n }\n\n /**\n * Get the history of all states\n */\n getStateHistory(): S[] {\n return [...this.stateHistory];\n }\n\n /**\n * Clear state history\n */\n clearStateHistory(): void {\n this.stateHistory = [this.state];\n }\n}\n\n/**\n * Memory leak detector for tests\n */\nexport class MemoryLeakDetector {\n private initialStats: ReturnType<typeof Blac.getMemoryStats>;\n\n constructor() {\n this.initialStats = Blac.getMemoryStats();\n }\n\n /**\n * Check for memory leaks and return a report\n */\n checkForLeaks(): {\n hasLeaks: boolean;\n report: string;\n stats: ReturnType<typeof Blac.getMemoryStats>;\n } {\n const currentStats = Blac.getMemoryStats();\n const hasLeaks =\n currentStats.registeredBlocs > this.initialStats.registeredBlocs ||\n currentStats.isolatedBlocs > this.initialStats.isolatedBlocs ||\n currentStats.keepAliveBlocs > this.initialStats.keepAliveBlocs;\n\n const report = `\nMemory Leak Detection Report:\n- Initial registered blocs: ${this.initialStats.registeredBlocs}\n- Current registered blocs: ${currentStats.registeredBlocs}\n- Initial isolated blocs: ${this.initialStats.isolatedBlocs} \n- Current isolated blocs: ${currentStats.isolatedBlocs}\n- Initial keep-alive blocs: ${this.initialStats.keepAliveBlocs}\n- Current keep-alive blocs: ${currentStats.keepAliveBlocs}\n- Potential leaks detected: ${hasLeaks ? 'YES' : 'NO'}\n `.trim();\n\n return {\n hasLeaks,\n report,\n stats: currentStats,\n };\n }\n}\n","import { BlocBase } from '../BlocBase';\n\ninterface ConsumerTracker {\n trackAccess: (\n consumerRef: object,\n type: 'state' | 'class',\n path: string,\n value?: any,\n ) => void;\n}\n\n// Minimal cache for backward compatibility\nconst proxyCache = new WeakMap<object, WeakMap<object, any>>();\n\n// Minimal stats for backward compatibility\nconst stats = {\n stateProxiesCreated: 0,\n classProxiesCreated: 0,\n cacheHits: 0,\n cacheMisses: 0,\n totalProxiesCreated: 0,\n};\n\n/**\n * Creates a proxy for state objects that tracks property access\n */\nexport const createStateProxy = <T extends object>(\n target: T,\n consumerRef: object,\n consumerTracker: ConsumerTracker,\n path = '',\n): T => {\n if (\n !consumerRef ||\n !consumerTracker ||\n typeof target !== 'object' ||\n target === null\n ) {\n return target;\n }\n\n // Check cache for backward compatibility with tests\n if (!path) {\n // Only cache root objects\n let refCache = proxyCache.get(target);\n if (!refCache) {\n refCache = new WeakMap();\n proxyCache.set(target, refCache);\n }\n\n const cached = refCache.get(consumerRef);\n if (cached) {\n stats.cacheHits++;\n return cached;\n }\n stats.cacheMisses++;\n }\n\n const proxy = new Proxy(target, {\n get(obj: T, prop: string | symbol): any {\n // Handle symbols and special properties\n if (typeof prop === 'symbol' || prop === 'constructor') {\n return Reflect.get(obj, prop);\n }\n\n const fullPath = path ? `${path}.${prop}` : prop;\n const value = Reflect.get(obj, prop);\n const isObject = value && typeof value === 'object';\n\n // Track access with value for primitives\n consumerTracker.trackAccess(\n consumerRef,\n 'state',\n fullPath,\n isObject ? undefined : value,\n );\n\n // Recursively proxy nested objects and arrays\n if (\n isObject &&\n (Array.isArray(value) ||\n Object.getPrototypeOf(value) === Object.prototype)\n ) {\n return createStateProxy(value, consumerRef, consumerTracker, fullPath);\n }\n\n return value;\n },\n\n set: () => false, // State should be immutable\n deleteProperty: () => false, // State properties should not be deleted\n });\n\n // Cache root proxies\n if (!path) {\n const refCache = proxyCache.get(target)!;\n refCache.set(consumerRef, proxy);\n stats.stateProxiesCreated++;\n stats.totalProxiesCreated++;\n }\n\n return proxy;\n};\n\n/**\n * Creates a proxy for bloc instances that tracks getter access\n */\nexport const createBlocProxy = <T extends object>(\n target: T,\n consumerRef: object,\n consumerTracker: ConsumerTracker,\n): T => {\n if (!consumerRef || !consumerTracker) {\n return target;\n }\n\n // Check cache\n let refCache = proxyCache.get(target);\n if (!refCache) {\n refCache = new WeakMap();\n proxyCache.set(target, refCache);\n }\n\n const cached = refCache.get(consumerRef);\n if (cached) {\n stats.cacheHits++;\n return cached;\n }\n stats.cacheMisses++;\n\n const proxy = new Proxy(target, {\n get(obj: T, prop: string | symbol): any {\n const value = Reflect.get(obj, prop);\n\n // Only track getters, not methods or regular properties\n const descriptor = findPropertyDescriptor(obj, prop);\n if (descriptor?.get) {\n // Track getter access with value for primitives\n const isPrimitive = value !== null && typeof value !== 'object';\n consumerTracker.trackAccess(\n consumerRef,\n 'class',\n String(prop),\n isPrimitive ? value : undefined,\n );\n }\n\n return value;\n },\n });\n\n // Cache proxy\n refCache.set(consumerRef, proxy);\n stats.classProxiesCreated++;\n stats.totalProxiesCreated++;\n\n return proxy;\n};\n\n/**\n * Helper to find property descriptor in prototype chain\n */\nconst findPropertyDescriptor = (\n obj: any,\n prop: string | symbol,\n maxDepth = 10,\n): PropertyDescriptor | undefined => {\n let current = obj;\n let depth = 0;\n\n while (current && depth < maxDepth) {\n const descriptor = Object.getOwnPropertyDescriptor(current, prop);\n if (descriptor) return descriptor;\n\n current = Object.getPrototypeOf(current);\n depth++;\n }\n\n return undefined;\n};\n\n// Export compatibility functions for easier migration\nexport const ProxyFactory = {\n createStateProxy: (options: {\n target: any;\n consumerRef: object;\n consumerTracker: ConsumerTracker;\n path?: string;\n }) =>\n createStateProxy(\n options.target,\n options.consumerRef,\n options.consumerTracker,\n options.path,\n ),\n\n createClassProxy: (options: {\n target: any;\n consumerRef: object;\n consumerTracker: ConsumerTracker;\n }) =>\n createBlocProxy(\n options.target,\n options.consumerRef,\n options.consumerTracker,\n ),\n\n getProxyState: <B extends BlocBase<any>>(options: {\n state: any;\n consumerRef: object;\n consumerTracker: ConsumerTracker;\n }) =>\n createStateProxy(\n options.state,\n options.consumerRef,\n options.consumerTracker,\n ),\n\n getProxyBlocInstance: <B extends BlocBase<any>>(options: {\n blocInstance: B;\n consumerRef: object;\n consumerTracker: ConsumerTracker;\n }) =>\n createBlocProxy(\n options.blocInstance,\n options.consumerRef,\n options.consumerTracker,\n ),\n\n // Compatibility functions that return expected structure\n getStats: () => ({\n ...stats,\n propertyAccesses: 0,\n nestedProxiesCreated: 0,\n cacheEfficiency:\n stats.cacheHits + stats.cacheMisses > 0\n ? `${((stats.cacheHits / (stats.cacheHits + stats.cacheMisses)) * 100).toFixed(1)}%`\n : 'N/A',\n lifetime: '0ms',\n proxiesPerSecond: 'N/A',\n }),\n resetStats: () => {\n stats.stateProxiesCreated = 0;\n stats.classProxiesCreated = 0;\n stats.cacheHits = 0;\n stats.cacheMisses = 0;\n stats.totalProxiesCreated = 0;\n },\n};\n","import { Blac } from '../Blac';\nimport { BlocBase } from '../BlocBase';\nimport { BlocConstructor, BlocState } from '../types';\nimport { generateUUID } from '../utils/uuid';\nimport { generateInstanceIdFromProps } from '../utils/generateInstanceId';\nimport { ProxyFactory } from './ProxyFactory';\n\nexport interface AdapterOptions<B extends BlocBase<any>> {\n instanceId?: string;\n dependencies?: (bloc: B) => unknown[];\n staticProps?: any;\n onMount?: (bloc: B) => void;\n onUnmount?: (bloc: B) => void;\n}\n\n/**\n * BlacAdapter orchestrates the connection between Bloc instances and React components.\n * It manages dependency tracking, lifecycle hooks, and proxy creation.\n */\nexport class BlacAdapter<B extends BlocConstructor<BlocBase<any>>> {\n public readonly id = `adapter-${generateUUID()}`;\n public readonly blocConstructor: B;\n public readonly componentRef: { current: object } = { current: {} };\n public blocInstance!: InstanceType<B>;\n\n unmountTime: number = 0;\n mountTime: number = 0;\n\n // Subscription management\n private subscriptionId?: string;\n private unsubscribe?: () => void;\n\n // Dependency tracking\n private dependencyValues?: unknown[];\n private isUsingDependencies: boolean = false;\n private trackedPaths = new Set<string>();\n private pendingTrackedPaths = new Set<string>(); // Paths tracked before subscription exists\n\n // Proxy caching\n private cachedStateProxy?: BlocState<InstanceType<B>>;\n private cachedBlocProxy?: InstanceType<B>;\n private lastProxiedState?: BlocState<InstanceType<B>>;\n\n // Lifecycle state\n private hasMounted = false;\n private mountCount = 0;\n\n // Rerender tracking\n private lastState?: BlocState<InstanceType<B>>;\n private lastDependencyValues?: unknown[];\n private componentName?: string;\n private renderCount = 0;\n private lastDependenciesFn?: (bloc: InstanceType<B>) => unknown[];\n\n options?: AdapterOptions<InstanceType<B>>;\n\n constructor(\n instanceProps: { componentRef: { current: object }; blocConstructor: B },\n options?: typeof this.options,\n ) {\n this.options = options;\n this.blocConstructor = instanceProps.blocConstructor;\n this.componentRef = instanceProps.componentRef;\n this.isUsingDependencies = !!options?.dependencies;\n\n // Initialize bloc instance\n this.updateBlocInstance();\n\n // Initialize dependency values if using dependencies\n if (this.isUsingDependencies && options?.dependencies) {\n this.dependencyValues = options.dependencies(this.blocInstance);\n }\n\n // Notify plugins\n const metadata = this.getAdapterMetadata();\n Blac.getInstance().plugins.notifyAdapterCreated(this, metadata);\n }\n\n trackAccess(\n consumerRef: object,\n type: 'state' | 'class',\n path: string,\n value?: any,\n ): void {\n const fullPath = type === 'class' ? `_class.${path}` : path;\n this.trackedPaths.add(fullPath);\n\n if (this.subscriptionId) {\n this.blocInstance.trackAccess(this.subscriptionId, fullPath, value);\n } else {\n // No subscription ID yet - store for later\n this.pendingTrackedPaths.add(fullPath);\n if ((Blac.config as any).logLevel === 'debug') {\n Blac.log(`[BlacAdapter] trackAccess storing pending path: ${path}`);\n }\n }\n }\n\n updateBlocInstance(): InstanceType<B> {\n // Determine the instance ID\n let instanceId = this.options?.instanceId;\n\n // If no explicit instanceId provided but staticProps exist, generate from them\n if (!instanceId && this.options?.staticProps) {\n const generatedId = generateInstanceIdFromProps(this.options.staticProps);\n if (generatedId) {\n instanceId = generatedId;\n }\n }\n\n this.blocInstance = Blac.instance.getBloc<B>(this.blocConstructor, {\n constructorParams: this.options?.staticProps,\n id: instanceId,\n instanceRef: this.id,\n });\n return this.blocInstance;\n }\n\n createSubscription = (options: { onChange: () => void }) => {\n // If using manual dependencies, create a selector-based subscription\n if (this.isUsingDependencies && this.options?.dependencies) {\n this.unsubscribe = this.blocInstance.subscribeWithSelector(\n (_state) => this.options!.dependencies!(this.blocInstance),\n (newValues) => {\n const hasChanged = this.hasDependencyValuesChanged(\n this.dependencyValues,\n newValues as unknown[],\n );\n\n if (hasChanged) {\n this.dependencyValues = newValues as unknown[];\n options.onChange();\n }\n },\n );\n } else {\n // Create a component subscription with weak reference\n const weakRef = new WeakRef(this.componentRef.current);\n this.unsubscribe = this.blocInstance.subscribeComponent(\n weakRef,\n options.onChange,\n );\n\n // Get the subscription ID for tracking\n const subscriptions = (this.blocInstance._subscriptionManager as any)\n .subscriptions as Map<string, any>;\n this.subscriptionId = Array.from(subscriptions.keys()).pop();\n\n // Apply any pending tracked paths\n if (this.subscriptionId && this.pendingTrackedPaths.size > 0) {\n for (const path of this.pendingTrackedPaths) {\n this.blocInstance.trackAccess(this.subscriptionId, path);\n }\n this.pendingTrackedPaths.clear();\n }\n }\n\n // Don't call onChange initially - let React handle the initial render\n\n return () => {\n if (this.unsubscribe) {\n this.unsubscribe();\n this.unsubscribe = undefined;\n this.subscriptionId = undefined;\n }\n };\n };\n\n hasDependencyValuesChanged = (\n oldValues: unknown[] | undefined,\n newValues: unknown[],\n ): boolean => {\n if (!oldValues) return true;\n if (oldValues.length !== newValues.length) return true;\n\n for (let i = 0; i < oldValues.length; i++) {\n if (!Object.is(oldValues[i], newValues[i])) {\n return true;\n }\n }\n\n return false;\n };\n\n getStateProxy = (): BlocState<InstanceType<B>> => {\n // If using manual dependencies or proxy tracking is disabled, return raw state\n if (this.isUsingDependencies || !Blac.config.proxyDependencyTracking) {\n return this.blocInstance.state;\n }\n\n // Return cached proxy if state hasn't changed\n const currentState = this.blocInstance.state;\n if (this.cachedStateProxy && this.lastProxiedState === currentState) {\n return this.cachedStateProxy;\n }\n\n // Create new proxy for new state\n this.lastProxiedState = currentState;\n this.cachedStateProxy = this.createStateProxy({ target: currentState });\n return this.cachedStateProxy!;\n };\n\n getBlocProxy = (): InstanceType<B> => {\n // If using manual dependencies or proxy tracking is disabled, return raw bloc\n if (this.isUsingDependencies || !Blac.config.proxyDependencyTracking) {\n return this.blocInstance;\n }\n\n // Return cached proxy if bloc instance hasn't changed\n if (this.cachedBlocProxy) {\n return this.cachedBlocProxy;\n }\n\n // Create and cache proxy\n this.cachedBlocProxy = this.createClassProxy({ target: this.blocInstance });\n return this.cachedBlocProxy;\n };\n\n createStateProxy = <T extends object>(props: { target: T }): T => {\n return ProxyFactory.createStateProxy({\n target: props.target,\n consumerRef: this.componentRef.current,\n consumerTracker: this as any,\n });\n };\n\n createClassProxy = <T extends object>(props: { target: T }): T => {\n return ProxyFactory.createClassProxy({\n target: props.target,\n consumerRef: this.componentRef.current,\n consumerTracker: this as any,\n });\n };\n\n // Lifecycle methods\n mount = () => {\n this.hasMounted = true;\n this.mountCount++;\n this.mountTime = Date.now();\n\n // Call onMount hook\n if (this.options?.onMount) {\n this.options.onMount(this.blocInstance);\n }\n\n // Refresh dependencies if using manual tracking\n if (this.isUsingDependencies && this.options?.dependencies) {\n this.dependencyValues = this.options.dependencies(this.blocInstance);\n }\n\n // Notify plugins\n const metadata = this.getAdapterMetadata();\n Blac.getInstance().plugins.notifyAdapterMount(this, metadata);\n };\n\n unmount = () => {\n this.unmountTime = Date.now();\n\n // Cancel subscription\n if (this.unsubscribe) {\n this.unsubscribe();\n this.unsubscribe = undefined;\n this.subscriptionId = undefined;\n }\n\n // Call onUnmount hook\n if (this.options?.onUnmount) {\n try {\n this.options.onUnmount(this.blocInstance);\n } catch (error) {\n console.error('Error in onUnmount hook:', error);\n }\n }\n\n // Notify plugins\n const metadata = this.getAdapterMetadata();\n Blac.getInstance().plugins.notifyAdapterUnmount(this, metadata);\n };\n\n // Reset tracking for next render\n resetTracking(): void {\n // Clear tracked paths from previous render\n this.trackedPaths.clear();\n this.pendingTrackedPaths.clear();\n\n // Clear subscription dependencies to track only current render\n if (this.subscriptionId) {\n const subscription = (\n this.blocInstance._subscriptionManager as any\n ).subscriptions.get(this.subscriptionId);\n if (subscription && subscription.dependencies) {\n // Clear old dependencies - we'll track new ones in this render\n subscription.dependencies.clear();\n }\n }\n }\n\n // Set component name for rerender logging\n setComponentName(name: string): void {\n this.componentName = name;\n }\n\n // Notify plugins about render\n notifyRender(): void {\n this.renderCount++;\n\n // Update dependency values if using manual tracking\n if (this.isUsingDependencies && this.options?.dependencies) {\n this.lastDependencyValues = this.dependencyValues;\n this.dependencyValues = this.options.dependencies(this.blocInstance);\n }\n\n const metadata = this.getAdapterMetadata();\n Blac.getInstance().plugins.notifyAdapterRender(this, metadata);\n }\n\n // Get adapter metadata for plugins\n private getAdapterMetadata(): any {\n return {\n componentName: this.componentName,\n blocInstance: this.blocInstance,\n renderCount: this.renderCount,\n trackedPaths: Array.from(this.trackedPaths),\n isUsingDependencies: this.isUsingDependencies,\n lastState: this.lastState,\n lastDependencyValues: this.lastDependencyValues,\n currentDependencyValues: this.dependencyValues,\n };\n }\n\n // Get value at a dot-notated path\n private getValueAtPath(obj: any, path: string): any {\n const parts = path.split('.');\n let current = obj;\n\n for (const part of parts) {\n if (current == null) return undefined;\n current = current[part];\n }\n\n return current;\n }\n\n // Get paths that changed between states\n private getStateChangedPaths(oldState: any, newState: any): string[] {\n const changedPaths: string[] = [];\n\n // Only check tracked paths if we have any\n if (this.trackedPaths.size > 0) {\n for (const path of this.trackedPaths) {\n // Skip class property paths\n if (path.startsWith('_class.')) continue;\n\n const oldValue = this.getValueAtPath(oldState, path);\n const newValue = this.getValueAtPath(newState, path);\n\n if (!Object.is(oldValue, newValue)) {\n changedPaths.push(path);\n }\n }\n } else {\n // No tracked paths - do deep comparison to find what changed\n if (oldState !== newState) {\n const deepChanges = this.getDeepChangedPaths(oldState, newState);\n if (deepChanges.length > 0) {\n return deepChanges;\n }\n changedPaths.push('(entire state)');\n }\n }\n\n return changedPaths;\n }\n\n // Deep comparison to find all changed paths\n private getDeepChangedPaths(\n oldObj: any,\n newObj: any,\n basePath: string = '',\n ): string[] {\n const changes: string[] = [];\n\n // Handle null/undefined\n if (oldObj === newObj) return changes;\n if (oldObj == null || newObj == null) {\n changes.push(basePath || '(root)');\n return changes;\n }\n\n // Handle primitives\n if (typeof oldObj !== 'object' || typeof newObj !== 'object') {\n if (oldObj !== newObj) {\n changes.push(basePath || '(root)');\n }\n return changes;\n }\n\n // Handle arrays\n if (Array.isArray(oldObj) || Array.isArray(newObj)) {\n if (\n !Array.isArray(oldObj) ||\n !Array.isArray(newObj) ||\n oldObj.length !== newObj.length\n ) {\n changes.push(basePath || '(root)');\n return changes;\n }\n // Compare array elements\n for (let i = 0; i < oldObj.length; i++) {\n const elementPath = basePath ? `${basePath}[${i}]` : `[${i}]`;\n changes.push(\n ...this.getDeepChangedPaths(oldObj[i], newObj[i], elementPath),\n );\n }\n return changes;\n }\n\n // Handle objects\n const allKeys = new Set([...Object.keys(oldObj), ...Object.keys(newObj)]);\n for (const key of allKeys) {\n const keyPath = basePath ? `${basePath}.${key}` : key;\n\n if (!(key in oldObj)) {\n changes.push(`${keyPath} (added)`);\n } else if (!(key in newObj)) {\n changes.push(`${keyPath} (removed)`);\n } else {\n const oldVal = oldObj[key];\n const newVal = newObj[key];\n\n // Use Object.is for comparison\n if (!Object.is(oldVal, newVal)) {\n // For primitives and different object references, record the change\n if (\n typeof oldVal !== 'object' ||\n typeof newVal !== 'object' ||\n oldVal === null ||\n newVal === null\n ) {\n changes.push(keyPath);\n } else {\n // For objects/arrays, recurse deeper\n const deeperChanges = this.getDeepChangedPaths(\n oldVal,\n newVal,\n keyPath,\n );\n if (deeperChanges.length > 0) {\n changes.push(...deeperChanges);\n } else {\n // Objects are different references but have same content\n changes.push(keyPath);\n }\n }\n }\n }\n }\n\n return changes;\n }\n\n // Get last rerender reason\n getLastRerenderReason(): any {\n // This method is deprecated - render reason is now handled by the RenderLoggingPlugin\n return undefined;\n }\n}\n"],"names":["BlocLifecycleState","BlocLifecycleManager","expectedState","newState","previousState","delay","canDispose","onDispose","handler","SystemPluginRegistry","plugin","pluginName","name","hookName","args","errorHandler","hook","startTime","error","bloc","currentState","event","context","hookError","adapter","metadata","pluginMetrics","hookMetrics","executionTime","ErrorCategory","ErrorSeverity","BlacError","message","category","severity","cause","contextStr","_","v","k","DefaultErrorStrategy","ErrorManager","strategy","handlerError","operation","errorFactory","blacError","SingletonBlacManager","Blac","instance","oldInstance","instanceManager","setBlacInstanceManager","manager","config","options","__unsafe_ignore_singleton","oldBlocInstanceMap","oldIsolatedBlocMap","blocArray","base","key","blocClassName","id","blocClass","found","blocs","wasRemoved","index","b","wasInIndex","uid","constructorParams","instanceRef","newBloc","forceNewInstance","blocId","isolatedBloc","registeredBloc","results","blocInstance","isolatedBlocs","toDispose","predicate","sum","arr","generateUUID","c","r","handleError","fn","BlocPluginRegistry","nextState","transformedState","transformedEvent","caps","SubscriptionManager","subscription","path","subs","oldState","action","sortedSubscriptions","a","shouldNotify","newValue","oldValue","changedPaths","subscriptionId","value","allKeys","fullPath","p","trackedPath","changedPath","consumerCount","observerCount","sub","deadIds","BatchingManager","callback","onFlush","finalUpdate","update","BlocBase","initialState","Constructor","state","selector","equalityFn","componentRef","Bloc","eventConstructor","transformedAction","emit","constructorName","errorContext","pluginError","Cubit","statePatch","ignoreChangeCheck","changes","current","PropsUpdated","props","shallowEqual","keysA","keysB","generateInstanceIdFromProps","primitives","type","parts","RerenderLogger","info","loggingConfig","currentCount","lastTimestamp","groupKey","existingTimeout","group","timeout","logs","log","level","emoji","header","details","values","componentName","BlocTest","BlocClass","resolve","reject","timeoutId","unsubscribe","expectedStates","receivedStates","i","expected","received","MockBloc","MockCubit","MemoryLeakDetector","currentStats","hasLeaks","report","proxyCache","stats","createStateProxy","target","consumerRef","consumerTracker","refCache","cached","proxy","obj","prop","isObject","createBlocProxy","findPropertyDescriptor","isPrimitive","maxDepth","depth","descriptor","ProxyFactory","BlacAdapter","instanceProps","instanceId","generatedId","_state","newValues","weakRef","subscriptions","oldValues","part","deepChanges","oldObj","newObj","basePath","elementPath","keyPath","oldVal","newVal","deeperChanges"],"mappings":"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"}