@omerdlw/base-framework 1.0.1 → 1.0.2

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 (141) hide show
  1. package/dist/atoms/index.d.ts +0 -1
  2. package/dist/atoms/index.d.ts.map +1 -1
  3. package/dist/atoms/index.js +1 -64
  4. package/dist/atoms/index.js.map +1 -1
  5. package/dist/error/index.js +22 -25
  6. package/dist/error/index.js.map +1 -1
  7. package/dist/hooks/index.d.ts +2 -0
  8. package/dist/hooks/index.d.ts.map +1 -1
  9. package/dist/hooks/index.js +97 -4
  10. package/dist/hooks/index.js.map +1 -1
  11. package/dist/hooks/types.d.ts +11 -0
  12. package/dist/hooks/types.d.ts.map +1 -1
  13. package/dist/hooks/use-controllable-state.d.ts +1 -1
  14. package/dist/hooks/use-controllable-state.d.ts.map +1 -1
  15. package/dist/hooks/use-hotkey.d.ts +1 -1
  16. package/dist/hooks/use-hotkey.d.ts.map +1 -1
  17. package/dist/index.js +10811 -10696
  18. package/dist/index.js.map +1 -1
  19. package/dist/kernel/adapters.d.ts.map +1 -1
  20. package/dist/kernel/index.d.ts +1 -0
  21. package/dist/kernel/index.d.ts.map +1 -1
  22. package/dist/kernel/index.js +13 -84
  23. package/dist/kernel/index.js.map +1 -1
  24. package/dist/kernel/installed.d.ts.map +1 -1
  25. package/dist/kernel/page-controller.d.ts.map +1 -1
  26. package/dist/kernel/provider.d.ts.map +1 -1
  27. package/dist/modules/ambient/constants.d.ts +1 -1
  28. package/dist/modules/ambient/constants.d.ts.map +1 -1
  29. package/dist/modules/ambient/index.js +180 -326
  30. package/dist/modules/ambient/index.js.map +1 -1
  31. package/dist/modules/ambient/module.d.ts.map +1 -1
  32. package/dist/modules/background/constants.d.ts +4 -2
  33. package/dist/modules/background/constants.d.ts.map +1 -1
  34. package/dist/modules/background/context.d.ts +3 -0
  35. package/dist/modules/background/context.d.ts.map +1 -1
  36. package/dist/modules/background/hooks.d.ts +1 -1
  37. package/dist/modules/background/index.d.ts +2 -2
  38. package/dist/modules/background/index.d.ts.map +1 -1
  39. package/dist/modules/background/index.js +1172 -1270
  40. package/dist/modules/background/index.js.map +1 -1
  41. package/dist/modules/background/overlay.d.ts +1 -1
  42. package/dist/modules/background/overlay.d.ts.map +1 -1
  43. package/dist/modules/background/types.d.ts +1 -1
  44. package/dist/modules/background/types.d.ts.map +1 -1
  45. package/dist/modules/context-menu/constants.d.ts +1 -1
  46. package/dist/modules/context-menu/constants.d.ts.map +1 -1
  47. package/dist/modules/context-menu/context.d.ts.map +1 -1
  48. package/dist/modules/context-menu/hooks.d.ts.map +1 -1
  49. package/dist/modules/context-menu/index.js +135 -240
  50. package/dist/modules/context-menu/index.js.map +1 -1
  51. package/dist/modules/controls/constants.d.ts +1 -1
  52. package/dist/modules/controls/constants.d.ts.map +1 -1
  53. package/dist/modules/controls/hooks.d.ts +1 -1
  54. package/dist/modules/controls/index.js +31 -165
  55. package/dist/modules/controls/index.js.map +1 -1
  56. package/dist/modules/controls/types.d.ts +1 -1
  57. package/dist/modules/controls/types.d.ts.map +1 -1
  58. package/dist/modules/dock/cards.d.ts +1 -1
  59. package/dist/modules/dock/constants.d.ts +1 -1
  60. package/dist/modules/dock/constants.d.ts.map +1 -1
  61. package/dist/modules/dock/context.d.ts +10 -6
  62. package/dist/modules/dock/context.d.ts.map +1 -1
  63. package/dist/modules/dock/hooks.d.ts +4 -4
  64. package/dist/modules/dock/hooks.d.ts.map +1 -1
  65. package/dist/modules/dock/index.d.ts +1 -1
  66. package/dist/modules/dock/index.d.ts.map +1 -1
  67. package/dist/modules/dock/index.js +2063 -2083
  68. package/dist/modules/dock/index.js.map +1 -1
  69. package/dist/modules/dock/runtime/dock.d.ts.map +1 -1
  70. package/dist/modules/dock/types.d.ts +1 -1
  71. package/dist/modules/dock/types.d.ts.map +1 -1
  72. package/dist/modules/index.js +10193 -10350
  73. package/dist/modules/index.js.map +1 -1
  74. package/dist/modules/loading/constants.d.ts +4 -2
  75. package/dist/modules/loading/constants.d.ts.map +1 -1
  76. package/dist/modules/loading/context.d.ts +3 -0
  77. package/dist/modules/loading/context.d.ts.map +1 -1
  78. package/dist/modules/loading/hooks.d.ts +1 -1
  79. package/dist/modules/loading/hooks.d.ts.map +1 -1
  80. package/dist/modules/loading/index.d.ts +2 -2
  81. package/dist/modules/loading/index.d.ts.map +1 -1
  82. package/dist/modules/loading/index.js +121 -225
  83. package/dist/modules/loading/index.js.map +1 -1
  84. package/dist/modules/loading/types.d.ts +1 -1
  85. package/dist/modules/loading/types.d.ts.map +1 -1
  86. package/dist/modules/media/constants.d.ts +2 -1
  87. package/dist/modules/media/constants.d.ts.map +1 -1
  88. package/dist/modules/media/context.d.ts +3 -0
  89. package/dist/modules/media/context.d.ts.map +1 -1
  90. package/dist/modules/media/index.d.ts +2 -2
  91. package/dist/modules/media/index.d.ts.map +1 -1
  92. package/dist/modules/media/index.js +61 -218
  93. package/dist/modules/media/index.js.map +1 -1
  94. package/dist/modules/modal/constants.d.ts +1 -1
  95. package/dist/modules/modal/constants.d.ts.map +1 -1
  96. package/dist/modules/modal/context.d.ts.map +1 -1
  97. package/dist/modules/modal/hooks.d.ts +2 -2
  98. package/dist/modules/modal/index.js +31 -293
  99. package/dist/modules/modal/index.js.map +1 -1
  100. package/dist/modules/notification/constants.d.ts +4 -2
  101. package/dist/modules/notification/constants.d.ts.map +1 -1
  102. package/dist/modules/notification/context.d.ts +4 -0
  103. package/dist/modules/notification/context.d.ts.map +1 -1
  104. package/dist/modules/notification/hooks.d.ts +1 -1
  105. package/dist/modules/notification/index.d.ts +2 -3
  106. package/dist/modules/notification/index.d.ts.map +1 -1
  107. package/dist/modules/notification/index.js +65 -151
  108. package/dist/modules/notification/index.js.map +1 -1
  109. package/dist/modules/notification/module.d.ts.map +1 -1
  110. package/dist/provider.js +255 -257
  111. package/dist/provider.js.map +1 -1
  112. package/dist/theme.d.ts +1 -0
  113. package/dist/theme.d.ts.map +1 -1
  114. package/dist/theme.js +2 -2
  115. package/dist/theme.js.map +1 -1
  116. package/dist/utils/dom.d.ts +2 -0
  117. package/dist/utils/dom.d.ts.map +1 -1
  118. package/dist/utils/index.d.ts +1 -1
  119. package/dist/utils/index.d.ts.map +1 -1
  120. package/dist/utils/index.js +28 -19
  121. package/dist/utils/index.js.map +1 -1
  122. package/docs/modules/loading.md +1 -1
  123. package/package.json +48 -2
  124. package/dist/hooks/use-async-action.d.ts +0 -3
  125. package/dist/hooks/use-async-action.d.ts.map +0 -1
  126. package/dist/hooks/use-debounce.d.ts +0 -2
  127. package/dist/hooks/use-debounce.d.ts.map +0 -1
  128. package/dist/hooks/use-intersection-observer.d.ts +0 -4
  129. package/dist/hooks/use-intersection-observer.d.ts.map +0 -1
  130. package/dist/hooks/use-media-query.d.ts +0 -2
  131. package/dist/hooks/use-media-query.d.ts.map +0 -1
  132. package/dist/hooks/use-mounted.d.ts +0 -2
  133. package/dist/hooks/use-mounted.d.ts.map +0 -1
  134. package/dist/hooks/use-server-action.d.ts +0 -4
  135. package/dist/hooks/use-server-action.d.ts.map +0 -1
  136. package/dist/hooks/use-storage-state.d.ts +0 -5
  137. package/dist/hooks/use-storage-state.d.ts.map +0 -1
  138. package/dist/modules/theme.d.ts +0 -3
  139. package/dist/modules/theme.d.ts.map +0 -1
  140. package/dist/utils/json.d.ts +0 -3
  141. package/dist/utils/json.d.ts.map +0 -1
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../src/hooks/use-required-context.ts","../../../src/hooks/use-store.ts","../../../src/utils/object.ts","../../../src/utils/report.ts","../../../src/utils/store.ts","../../../src/events.ts","../../../src/modules/media/constants.ts","../../../src/modules/media/utils.ts","../../../src/kernel/context-registry.ts","../../../src/modules/media/context.tsx","../../../src/modules/media/hooks.ts","../../../src/kernel/constants.ts","../../../src/kernel/store.ts","../../../src/kernel/provider.tsx","../../../src/kernel/installed.ts","../../../src/kernel/page-controller.tsx","../../../src/kernel/module.tsx","../../../src/modules/media/overlay.tsx","../../../src/modules/media/module.tsx"],"names":["useRef","useEffect","useCallback","useMemo","useSyncExternalStore"],"mappings":"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","file":"index.js","sourcesContent":["\"use client\";\n\nimport { use, type Context } from \"react\";\n\nexport function useRequiredContext<T>(\n context: Context<T | null>,\n hookName: string,\n providerName: string,\n): T {\n const value = use(context);\n if (value === null) {\n throw new Error(`${hookName} must be used within ${providerName}`);\n }\n return value;\n}\n","\"use client\";\n\nimport { useCallback, useRef, useSyncExternalStore } from \"react\";\nimport { type ExternalStore } from \"../utils\";\n\nexport function useStore<TState, TSlice = TState>(\n store: ExternalStore<TState>,\n selector: (state: TState) => TSlice = (state: TState) =>\n state as unknown as TSlice,\n isEqual: (a: TSlice, b: TSlice) => boolean = Object.is,\n): TSlice {\n const cacheRef = useRef<{\n isEqual: ((a: TSlice, b: TSlice) => boolean) | null;\n selected: TSlice | undefined;\n selector: ((state: TState) => TSlice) | null;\n snapshot: TState | null;\n }>({\n isEqual: null,\n selected: undefined,\n selector: null,\n snapshot: null,\n });\n\n const getSelectedSnapshot = useCallback(() => {\n const snapshot = store.getSnapshot();\n const cache = cacheRef.current;\n if (\n cache.snapshot === snapshot &&\n cache.selector === selector &&\n cache.isEqual === isEqual\n ) {\n return cache.selected as TSlice;\n }\n\n const selected = selector(snapshot);\n if (\n cache.snapshot !== null &&\n cache.isEqual === isEqual &&\n isEqual(cache.selected as TSlice, selected)\n ) {\n cache.snapshot = snapshot;\n cache.selector = selector;\n return cache.selected as TSlice;\n }\n\n cacheRef.current = {\n isEqual,\n selected,\n selector,\n snapshot,\n };\n return selected;\n }, [isEqual, selector, store]);\n\n return useSyncExternalStore(\n store.subscribe,\n getSelectedSnapshot,\n getSelectedSnapshot,\n );\n}\n","export function isObject(value: unknown): value is Record<string, unknown> {\n return Boolean(value) && typeof value === \"object\" && !Array.isArray(value);\n}\n\nexport function isPlainObject(\n value: unknown,\n): value is Record<string, unknown> {\n if (!isObject(value)) return false;\n const proto = Object.getPrototypeOf(value);\n return proto === Object.prototype || proto === null;\n}\n\nexport function shallowEqual(a: unknown, b: unknown): boolean {\n if (Object.is(a, b)) return true;\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 as object);\n const keysB = Object.keys(b as object);\n\n if (keysA.length !== keysB.length) return false;\n\n for (const key of keysA) {\n if (\n !Object.prototype.hasOwnProperty.call(b, key) ||\n !Object.is(\n (a as Record<string, unknown>)[key],\n (b as Record<string, unknown>)[key],\n )\n ) {\n return false;\n }\n }\n\n return true;\n}\n\nexport function toArray<T>(value: T | T[] | null | undefined): T[] {\n if (value === null || value === undefined) return [];\n return Array.isArray(value) ? value : [value];\n}\n","export type ReportLevel = \"error\" | \"warn\";\n\nexport type ReportSink = (\n scope: string,\n error: unknown,\n level: ReportLevel,\n) => void;\n\nlet sink: ReportSink | null = null;\n\nexport function report(\n scope: string,\n error: unknown,\n level: ReportLevel = \"error\",\n): void {\n if (sink) {\n try {\n sink(scope, error, level);\n return;\n } catch {}\n }\n\n if (process.env.NODE_ENV === \"production\" && typeof window !== \"undefined\") {\n return;\n }\n console[level](`[${scope}]`, error);\n}\n\nexport function setReportSink(next: ReportSink): () => void {\n sink = next;\n return () => {\n if (sink === next) sink = null;\n };\n}\n","import { report } from \"./report\";\nexport interface ExternalStore<TState = unknown> {\n readonly getSnapshot: () => TState;\n readonly publish: (\n nextState: TState | ((currentState: TState) => TState),\n ) => boolean;\n readonly setState: (\n updater: Partial<TState> | ((currentState: TState) => TState),\n ) => boolean;\n readonly subscribe: (listener: () => void) => () => void;\n}\n\nfunction freezeStoreSnapshot<TState>(state: TState): TState {\n if (\n process.env.NODE_ENV === \"production\" ||\n !state ||\n typeof state !== \"object\"\n ) {\n return state;\n }\n\n const seen = new WeakSet<object>();\n const freeze = (value: object): void => {\n if (seen.has(value) || Object.isFrozen(value)) return;\n seen.add(value);\n\n const prototype = Object.getPrototypeOf(value);\n if (\n Array.isArray(value) ||\n prototype === Object.prototype ||\n prototype === null\n ) {\n for (const key of Reflect.ownKeys(value)) {\n const descriptor = Object.getOwnPropertyDescriptor(value, key);\n if (descriptor && \"value\" in descriptor && descriptor.value !== null) {\n if (typeof descriptor.value === \"object\") freeze(descriptor.value);\n }\n }\n }\n\n Object.freeze(value);\n };\n\n freeze(state);\n return state;\n}\n\nexport interface CreateStoreOptions {\n freezeSnapshots?: boolean;\n}\n\nexport function createStore<TState = Record<string, unknown>>(\n initialState: TState,\n { freezeSnapshots = true }: CreateStoreOptions = {},\n): ExternalStore<TState> {\n const listeners = new Set<() => void>();\n const prepare = freezeSnapshots\n ? freezeStoreSnapshot\n : <T>(state: T): T => state;\n let snapshot = prepare(initialState);\n\n const publish = (\n nextStateOrUpdater: TState | ((currentState: TState) => TState),\n ): boolean => {\n const nextState =\n typeof nextStateOrUpdater === \"function\"\n ? (nextStateOrUpdater as (currentState: TState) => TState)(snapshot)\n : nextStateOrUpdater;\n if (Object.is(snapshot, nextState)) return false;\n snapshot = prepare(nextState);\n\n for (const listener of listeners) {\n try {\n listener();\n } catch (error) {\n report(\"CoreStore subscriber\", error, \"warn\");\n }\n }\n return true;\n };\n\n const setState = (\n updater: Partial<TState> | ((currentState: TState) => TState),\n ): boolean => {\n if (typeof updater === \"function\") {\n return publish(updater as (currentState: TState) => TState);\n }\n if (\n snapshot &&\n typeof snapshot === \"object\" &&\n updater &&\n typeof updater === \"object\"\n ) {\n return publish({ ...snapshot, ...updater });\n }\n return publish(updater as TState);\n };\n\n return Object.freeze({\n getSnapshot() {\n return snapshot;\n },\n publish,\n setState,\n subscribe(listener: () => void) {\n if (typeof listener !== \"function\") return () => {};\n listeners.add(listener);\n return () => listeners.delete(listener);\n },\n });\n}\n","import { report } from \"./utils/report\";\nexport type EventListener<T = unknown> = (payload: T) => void;\n\nexport const EVENT_TYPES = Object.freeze({\n API_UNAUTHORIZED: \"API_UNAUTHORIZED\",\n STATE_CHANGE: \"STATE_CHANGE\",\n API_ERROR: \"API_ERROR\",\n APP_ERROR: \"APP_ERROR\",\n} as const);\n\nexport interface FrameworkEventMap {\n [EVENT_TYPES.API_UNAUTHORIZED]: {\n error?: unknown;\n status?: number;\n [key: string]: unknown;\n };\n [EVENT_TYPES.API_ERROR]: {\n error: unknown;\n isCritical?: boolean;\n message?: string;\n retry?: () => void;\n status?: number;\n [key: string]: unknown;\n };\n [EVENT_TYPES.APP_ERROR]: {\n error?: unknown;\n message?: string;\n resetError?: () => void;\n source?: string;\n [key: string]: unknown;\n };\n [EVENT_TYPES.STATE_CHANGE]: {\n message?: string;\n status?: \"success\" | \"warning\" | \"info\" | \"error\" | string;\n [key: string]: unknown;\n };\n}\n\nexport class EventEmitter<TEvents extends object = FrameworkEventMap> {\n private events: Map<string, Set<EventListener<never>>> = new Map();\n private debounceTimers: Map<string, ReturnType<typeof setTimeout>> =\n new Map();\n\n subscribe<K extends keyof TEvents>(\n event: K,\n callback: EventListener<TEvents[K]>,\n ): () => void;\n subscribe<T = unknown>(event: string, callback: EventListener<T>): () => void;\n subscribe(event: string, callback: EventListener<never>): () => void {\n if (typeof event !== \"string\" || !event || typeof callback !== \"function\") {\n return () => {};\n }\n const listeners = this.events.get(event) || new Set<EventListener<never>>();\n listeners.add(callback);\n this.events.set(event, listeners);\n\n return () => {\n listeners.delete(callback);\n if (listeners.size === 0) this.events.delete(event);\n };\n }\n\n emit<K extends keyof TEvents>(\n event: K,\n ...args: TEvents[K] extends void | undefined\n ? [payload?: TEvents[K]]\n : [payload: TEvents[K]]\n ): void;\n emit<T = unknown>(event: string, payload?: T): void;\n emit(event: string, payload?: unknown): void {\n const listeners = this.events.get(event);\n if (!listeners || listeners.size === 0) return;\n const snapshot = Array.from(listeners);\n for (const callback of snapshot) {\n try {\n (callback as EventListener<unknown>)(payload);\n } catch (error) {\n report(`Event listener (${String(event)})`, error);\n }\n }\n }\n\n emitDebounced<K extends keyof TEvents>(\n event: K,\n payload: TEvents[K],\n waitMs?: number,\n ): void;\n emitDebounced<T = unknown>(event: string, payload?: T, waitMs?: number): void;\n emitDebounced(event: string, payload?: unknown, waitMs: number = 100): void {\n const existing = this.debounceTimers.get(event);\n if (existing) clearTimeout(existing);\n\n const timer = setTimeout(() => {\n this.debounceTimers.delete(event);\n this.emit(event, payload);\n }, waitMs);\n\n this.debounceTimers.set(event, timer);\n }\n\n cancelDebounced(event?: string): void {\n if (event) {\n const timer = this.debounceTimers.get(event);\n if (timer) {\n clearTimeout(timer);\n this.debounceTimers.delete(event);\n }\n } else {\n for (const timer of this.debounceTimers.values()) {\n clearTimeout(timer);\n }\n this.debounceTimers.clear();\n }\n }\n\n unsubscribeAll(event?: string): void {\n this.cancelDebounced(event);\n if (event) this.events.delete(event);\n else this.events.clear();\n }\n\n hasListeners(event: string): boolean {\n return Boolean(this.events.get(event)?.size);\n }\n\n getListenerCount(event: string): number {\n return this.events.get(event)?.size || 0;\n }\n\n getAllEvents(): string[] {\n return [...this.events.keys()];\n }\n}\n\nconst GLOBAL_EVENTS_KEY = Symbol.for(\"__base_framework_global_events__\");\ntype GlobalWithEvents = typeof globalThis & {\n [GLOBAL_EVENTS_KEY]?: EventEmitter<FrameworkEventMap>;\n};\n\nconst _global = globalThis as GlobalWithEvents;\nexport const globalEvents: EventEmitter<FrameworkEventMap> =\n _global[GLOBAL_EVENTS_KEY] ??\n (_global[GLOBAL_EVENTS_KEY] = new EventEmitter<FrameworkEventMap>());\n","import { type MediaState } from \"./types\";\n\nexport const DEFAULT_MEDIA_STATE: MediaState = Object.freeze({\n audibleElement: null,\n element: null,\n hasMedia: false,\n isPlaying: false,\n kind: null,\n loop: false,\n sourceId: null,\n});\n\nexport const MEDIA_SYNC_DRIFT_SECONDS = 0.3;\n\nexport const MEDIA_REGISTRY_KEY = \"page-media\";\n\n/** Id of the audio source registered through `usePage({ media })`. */\nexport const PAGE_MEDIA_ID = \"page\";\n","import { shallowEqual } from \"@/utils\";\nimport { DEFAULT_MEDIA_STATE, MEDIA_SYNC_DRIFT_SECONDS } from \"./constants\";\nimport {\n type MediaSession,\n type MediaEntry,\n type MediaEntryInput,\n type MediaPageConfig,\n type MediaPageOptions,\n type MediaState,\n} from \"./types\";\n\nconst noop = () => {};\n\nfunction newest(sources: readonly MediaEntry[]): MediaEntry {\n return sources.reduce((a, b) => (b.order > a.order ? b : a));\n}\n\nexport function resolveMediaSession(\n sources: readonly MediaEntry[],\n): MediaSession | null {\n if (sources.length === 0) return null;\n\n const ids = new Set(sources.map((source) => source.id));\n const wantsFollow = (source: MediaEntry) =>\n Boolean(source.follow) &&\n source.follow !== source.id &&\n ids.has(source.follow!);\n const rootIds = new Set(\n sources.filter((source) => !wantsFollow(source)).map((source) => source.id),\n );\n const isFollower = (source: MediaEntry) =>\n wantsFollow(source) && rootIds.has(source.follow!);\n\n const transport = newest(sources.filter((source) => !isFollower(source)));\n const followers = sources\n .filter((source) => isFollower(source) && source.follow === transport.id)\n .sort((a, b) => a.order - b.order);\n const audioFollowers = followers.filter((source) => source.kind === \"audio\");\n\n return {\n audible: audioFollowers.length > 0 ? newest(audioFollowers) : transport,\n followers,\n transport,\n };\n}\n\nexport function createMediaState(session: MediaSession | null): MediaState {\n if (!session) return DEFAULT_MEDIA_STATE;\n const { audible, transport } = session;\n return {\n audibleElement: audible.element,\n element: transport.element,\n hasMedia: true,\n isPlaying: transport.isPlaying,\n kind: transport.kind,\n loop: transport.loop,\n sourceId: transport.id,\n };\n}\n\nexport function mediaStatesEqual(a: MediaState, b: MediaState): boolean {\n return shallowEqual(a, b);\n}\n\nexport function mergeMediaSource(\n current: MediaEntry | undefined,\n input: MediaEntryInput,\n order: number,\n): MediaEntry {\n return {\n controls: undefined,\n element: null,\n follow: null,\n isPlaying: false,\n kind: \"audio\",\n loop: false,\n ...current,\n ...input,\n order: current?.order ?? order,\n };\n}\n\nexport function toggleElement(element: HTMLMediaElement | null): void {\n if (!element) return;\n if (element.paused || element.ended) {\n void Promise.resolve(element.play()).catch(noop);\n } else {\n element.pause();\n }\n}\n\nexport function safePlay(element: HTMLMediaElement): void {\n try {\n void Promise.resolve(element.play()).catch(noop);\n } catch {\n /* autoplay blocked or element detached */\n }\n}\n\nexport function bindFollowers(\n transport: HTMLMediaElement,\n followers: readonly HTMLMediaElement[],\n): () => void {\n const ownLoops = followers.map((follower) => follower.loop);\n\n const align = (hard: boolean) => {\n const time = Number(transport.currentTime) || 0;\n for (const follower of followers) {\n follower.loop = false;\n if (follower.playbackRate !== transport.playbackRate) {\n follower.playbackRate = transport.playbackRate;\n }\n const drift = Math.abs((Number(follower.currentTime) || 0) - time);\n if (hard || drift > MEDIA_SYNC_DRIFT_SECONDS) follower.currentTime = time;\n }\n };\n const play = () => {\n align(false);\n followers.forEach(safePlay);\n };\n const pause = () => followers.forEach((follower) => follower.pause());\n const hardAlign = () => align(true);\n const softAlign = () => align(false);\n\n const listeners: [string, () => void][] = [\n [\"play\", play],\n [\"playing\", play],\n [\"pause\", pause],\n [\"waiting\", pause],\n [\"ended\", pause],\n [\"seeking\", hardAlign],\n [\"seeked\", hardAlign],\n [\"ratechange\", softAlign],\n [\"timeupdate\", softAlign],\n ];\n for (const [type, listener] of listeners) {\n transport.addEventListener(type, listener);\n }\n\n hardAlign();\n if (!transport.paused && !transport.ended) play();\n\n return () => {\n for (const [type, listener] of listeners) {\n transport.removeEventListener(type, listener);\n }\n followers.forEach((follower, index) => {\n follower.loop = ownLoops[index];\n });\n };\n}\n\nexport function sameElements(\n a: readonly (HTMLMediaElement | null)[],\n b: readonly (HTMLMediaElement | null)[],\n): boolean {\n return (\n a.length === b.length && a.every((element, index) => element === b[index])\n );\n}\n\nexport function selectPageMedia(\n media: MediaPageConfig | null | undefined,\n): MediaPageOptions | null {\n if (!media) return null;\n if (typeof media === \"string\") return { src: media };\n return media.src ? media : null;\n}\n\n/**\n * Standalone audio that a newly registered source pushes out of the controls.\n * Two independent tracks would otherwise play over each other while the dock\n * only controls the newest.\n */\nexport function findDisplacedAudio(\n entries: readonly MediaEntry[],\n session: MediaSession | null,\n newId: string,\n): MediaEntry[] {\n if (!session || session.transport.id !== newId) return [];\n const followerIds = new Set(session.followers.map((entry) => entry.id));\n return entries.filter(\n (entry) =>\n entry.id !== newId &&\n !followerIds.has(entry.id) &&\n entry.kind === \"audio\" &&\n entry.element !== null &&\n !entry.element.paused,\n );\n}\n","import { createContext, type Context } from \"react\";\n\nexport function getOrCreateGlobalContext<T>(\n name: string,\n defaultValue: T,\n): Context<T> {\n const sym = Symbol.for(`@omerdlw/base-framework/context/${name}`);\n const store = globalThis as unknown as Record<symbol, Context<T>>;\n if (!store[sym]) {\n store[sym] = createContext<T>(defaultValue);\n }\n return store[sym];\n}\n","\"use client\";\n\nimport { createContext, useEffect, useMemo, useRef, useState } from \"react\";\nimport { useRequiredContext, useStore } from \"@/hooks\";\nimport { createStore } from \"@/utils\";\nimport { DEFAULT_MEDIA_STATE } from \"./constants\";\nimport {\n type MediaActions,\n type MediaContextValue,\n type MediaProviderProps,\n type MediaSession,\n type MediaEntry,\n type MediaState,\n} from \"./types\";\nimport {\n bindFollowers,\n createMediaState,\n findDisplacedAudio,\n mediaStatesEqual,\n mergeMediaSource,\n resolveMediaSession,\n sameElements,\n toggleElement,\n} from \"./utils\";\nimport { getOrCreateGlobalContext } from \"@/kernel/context-registry\";\n\nexport const MediaContext = getOrCreateGlobalContext<MediaContextValue | null>(\n \"MediaContext\",\n null,\n);\n\ninterface Binding {\n cleanup: () => void;\n followers: readonly (HTMLMediaElement | null)[];\n transport: HTMLMediaElement;\n}\n\nexport function MediaProvider({ children }: MediaProviderProps) {\n const [store] = useState(() =>\n createStore<MediaState>(DEFAULT_MEDIA_STATE, { freezeSnapshots: false }),\n );\n const sourcesRef = useRef(new Map<string, MediaEntry>());\n const sessionRef = useRef<MediaSession | null>(null);\n const orderRef = useRef(0);\n const bindingRef = useRef<Binding | null>(null);\n\n const actions = useMemo<MediaActions>(() => {\n const unbind = () => {\n bindingRef.current?.cleanup();\n bindingRef.current = null;\n };\n\n const rebind = (session: MediaSession | null) => {\n const transport = session?.transport.element ?? null;\n const followers = (session?.followers ?? []).map(\n (source) => source.element,\n );\n const current = bindingRef.current;\n if (\n current &&\n current.transport === transport &&\n sameElements(current.followers, followers)\n ) {\n return;\n }\n unbind();\n const live = followers.filter(\n (element): element is HTMLMediaElement => element !== null,\n );\n if (!transport || live.length === 0) return;\n bindingRef.current = {\n cleanup: bindFollowers(transport, live),\n followers,\n transport,\n };\n };\n\n const commit = () => {\n const session = resolveMediaSession([...sourcesRef.current.values()]);\n sessionRef.current = session;\n rebind(session);\n const next = createMediaState(session);\n store.publish((prev) => (mediaStatesEqual(prev, next) ? prev : next));\n };\n\n const patch = (id: string, changes: Partial<MediaEntry>) => {\n const current = sourcesRef.current.get(id);\n if (!current) return;\n sourcesRef.current.set(id, { ...current, ...changes });\n commit();\n };\n\n return {\n removeSource: (id) => {\n if (sourcesRef.current.delete(id)) commit();\n },\n setMuted: (muted) => {\n const audible = sessionRef.current?.audible;\n if (!audible) return;\n if (audible.controls?.setMuted) audible.controls.setMuted(muted);\n else if (audible.element) audible.element.muted = muted;\n },\n toggle: () => {\n const transport = sessionRef.current?.transport;\n if (!transport) return;\n if (transport.controls?.toggle) transport.controls.toggle();\n else toggleElement(transport.element);\n },\n toggleLoop: () => {\n const transport = sessionRef.current?.transport;\n if (!transport) return;\n if (transport.controls?.toggleLoop) {\n transport.controls.toggleLoop();\n return;\n }\n const loop = !transport.loop;\n if (transport.element) transport.element.loop = loop;\n patch(transport.id, { loop });\n },\n upsertSource: (input) => {\n const current = sourcesRef.current.get(input.id);\n if (!current) orderRef.current += 1;\n sourcesRef.current.set(\n input.id,\n mergeMediaSource(current, input, orderRef.current),\n );\n commit();\n if (!current) {\n findDisplacedAudio(\n [...sourcesRef.current.values()],\n sessionRef.current,\n input.id,\n ).forEach((entry) => entry.element?.pause());\n }\n },\n };\n }, [store]);\n\n useEffect(\n () => () => {\n bindingRef.current?.cleanup();\n bindingRef.current = null;\n },\n [],\n );\n\n const value = useMemo<MediaContextValue>(\n () => ({ actions, store }),\n [actions, store],\n );\n\n return <MediaContext value={value}>{children}</MediaContext>;\n}\n\nexport function useMediaState(): MediaState {\n const { store } = useRequiredContext(\n MediaContext,\n \"useMediaState\",\n \"MediaProvider\",\n );\n return useStore(store);\n}\n\nexport function useMediaActions(): MediaActions {\n return useRequiredContext(MediaContext, \"useMediaActions\", \"MediaProvider\")\n .actions;\n}\n","\"use client\";\n\nimport { useCallback, useEffect, useId, useMemo, useRef } from \"react\";\nimport { useMediaActions } from \"./context\";\nimport { toggleElement } from \"./utils\";\nimport { type MediaHandle, type MediaOptions } from \"./types\";\n\nexport function useMedia(options: MediaOptions): MediaHandle {\n const generatedId = useId();\n const id = options.id ?? `media-${generatedId}`;\n const { removeSource, upsertSource } = useMediaActions();\n const audioRef = useRef<HTMLAudioElement | null>(null);\n const optionsRef = useRef(options);\n const { src, enabled = true } = options;\n const isEnabled = enabled && Boolean(src);\n\n useEffect(() => {\n optionsRef.current = options;\n });\n\n useEffect(() => {\n if (!isEnabled || !src) return undefined;\n const audio = new Audio();\n audio.preload = \"auto\";\n audio.src = src;\n audioRef.current = audio;\n\n const initial = optionsRef.current;\n audio.loop = Boolean(initial.loop);\n audio.muted = Boolean(initial.muted);\n if (typeof initial.volume === \"number\") {\n audio.volume = Math.min(1, Math.max(0, initial.volume));\n }\n\n upsertSource({\n element: audio,\n follow: initial.follow ?? null,\n id,\n isPlaying: false,\n kind: \"audio\",\n loop: audio.loop,\n });\n\n const syncPlaying = () =>\n upsertSource({ id, isPlaying: !audio.paused && !audio.ended });\n const events = [\"play\", \"playing\", \"pause\", \"ended\"] as const;\n events.forEach((type) => audio.addEventListener(type, syncPlaying));\n\n if (!initial.follow && initial.autoplay !== false) {\n void Promise.resolve(audio.play()).catch(() => {});\n }\n\n return () => {\n events.forEach((type) => audio.removeEventListener(type, syncPlaying));\n audio.pause();\n audio.removeAttribute(\"src\");\n audio.load();\n audioRef.current = null;\n removeSource(id);\n };\n }, [id, isEnabled, removeSource, src, upsertSource]);\n\n const { follow = null, loop, muted, volume } = options;\n useEffect(() => {\n const audio = audioRef.current;\n if (!audio) return;\n if (loop !== undefined && !follow) audio.loop = loop;\n if (muted !== undefined) audio.muted = muted;\n if (volume !== undefined) audio.volume = Math.min(1, Math.max(0, volume));\n upsertSource({ follow, id, ...(follow ? {} : { loop: audio.loop }) });\n }, [follow, id, isEnabled, loop, muted, src, upsertSource, volume]);\n\n const play = useCallback(() => {\n const audio = audioRef.current;\n if (audio) void Promise.resolve(audio.play()).catch(() => {});\n }, []);\n const pause = useCallback(() => audioRef.current?.pause(), []);\n const toggle = useCallback(() => toggleElement(audioRef.current), []);\n\n return useMemo(\n () => ({ id, pause, play, toggle }),\n [id, pause, play, toggle],\n );\n}\n","import type {\n RegistryLifecycle,\n RegistryScopeKind,\n RegistrySource,\n RegistryValidationMode,\n} from \"./types\";\n\nexport const DEFAULT_SOURCE: RegistrySource = \"dynamic\";\n\nexport const REGISTRY_SOURCES: Readonly<Record<string, RegistrySource>> =\n Object.freeze({\n STATIC: \"static\",\n DYNAMIC: \"dynamic\",\n USER: \"user\",\n });\n\nexport const REGISTRY_LIFECYCLES: Readonly<Record<string, RegistryLifecycle>> =\n Object.freeze({\n IMMEDIATE: \"immediate\",\n GRACEFUL: \"graceful\",\n PERSISTENT: \"persistent\",\n ROUTE: \"route\",\n });\n\nexport const REGISTRY_VALIDATION_MODES: Readonly<\n Record<string, RegistryValidationMode>\n> = Object.freeze({\n WARN: \"warn\",\n STRICT: \"strict\",\n});\n\nexport const REGISTRY_METADATA_KEYS: readonly string[] = Object.freeze([\n \"cleanup\",\n \"cleanupDelayMs\",\n \"instanceId\",\n \"lifecycle\",\n \"priority\",\n \"source\",\n \"scope\",\n \"validation\",\n]);\n\nexport const REGISTRY_SOURCE_PRIORITY: Readonly<Record<string, number>> =\n Object.freeze({\n [REGISTRY_SOURCES.STATIC]: 100,\n [REGISTRY_SOURCES.DYNAMIC]: 200,\n [REGISTRY_SOURCES.USER]: 300,\n });\n\nexport const REGISTRY_SOURCE_RANK: Readonly<Record<string, number>> =\n Object.freeze({\n [REGISTRY_SOURCES.STATIC]: 10,\n [REGISTRY_SOURCES.DYNAMIC]: 20,\n [REGISTRY_SOURCES.USER]: 30,\n });\n\nexport const REGISTRY_LIFECYCLE_VALUES: ReadonlySet<string> = new Set(\n Object.values(REGISTRY_LIFECYCLES),\n);\n\nexport const REGISTRY_METADATA_KEY_SET: ReadonlySet<string> = new Set(\n REGISTRY_METADATA_KEYS,\n);\n\nconst REGISTRY_SCOPE_KINDS: Readonly<Record<string, RegistryScopeKind>> =\n Object.freeze({\n APP: \"app\",\n SESSION: \"session\",\n ROUTE: \"route\",\n INSTANCE: \"instance\",\n WORKSPACE: \"workspace\",\n });\n\nexport const DEFAULT_REGISTRY_SCOPE: RegistryScopeKind =\n REGISTRY_SCOPE_KINDS.APP;\n","import { isValidElement } from \"react\";\nimport {\n createRecordKey,\n createRegisterOperation,\n createRegistryOperations,\n createUnregisterOperation,\n type RegistryOperations,\n} from \"./operations\";\nimport {\n DEFAULT_SOURCE,\n REGISTRY_SOURCES,\n REGISTRY_VALIDATION_MODES,\n validateRegistryMetadata,\n validateRegistryValue,\n} from \"./schema\";\nimport { createRegistryTransaction } from \"./runtime\";\nimport type {\n AppRegistryEntry,\n RegisterOperation,\n RegistrationHandle,\n RegistryDefinitions,\n RegistryMetadata,\n RegistryOperation,\n RegistryQueue,\n RegistrySourceOrOptions,\n RegistryState,\n RegistryStore,\n RegistryTransactionQueue,\n} from \"./types\";\nimport { report } from \"@/utils\";\n\nexport type InitialRegistryEntries = readonly AppRegistryEntry[];\n\nconst NO_DEFINITIONS: RegistryDefinitions = new Map();\n\nfunction createNoopHandle(\n status: RegistrationHandle[\"status\"] = \"rejected\",\n reason = \"unknown\",\n): RegistrationHandle {\n const handle: RegistrationHandle = Object.assign(() => false, {\n active: false,\n dispose: () => false,\n instanceId: null,\n key: \"\",\n priority: 0,\n reason,\n source: \"\",\n status,\n type: \"\",\n update: (): RegistrationHandle => handle,\n updatedAt: 0,\n validation: \"warn\",\n });\n return handle;\n}\n\nconst NOOP_HANDLE: RegistrationHandle = createNoopHandle();\n\nfunction isNoopHandle(handle: RegistrationHandle | null | undefined): boolean {\n return (\n handle === NOOP_HANDLE ||\n handle?.status === \"rejected\" ||\n handle?.status === \"ignored\"\n );\n}\n\nfunction cloneRegistryValue<T>(\n value: T,\n seen = new WeakMap<object, unknown>(),\n): T {\n if (value === null || typeof value !== \"object\" || isValidElement(value)) {\n return value;\n }\n\n const prototype = Object.getPrototypeOf(value);\n const isPlainObject =\n !Array.isArray(value) &&\n (prototype === Object.prototype || prototype === null);\n\n if (!Array.isArray(value) && !isPlainObject) return value;\n if (seen.has(value)) return seen.get(value) as T;\n\n const source = value as Record<string, unknown>;\n const clone = (Array.isArray(value) ? [] : {}) as Record<string, unknown>;\n seen.set(value, clone);\n\n for (const key in source) {\n if (Object.prototype.hasOwnProperty.call(source, key)) {\n clone[key] = cloneRegistryValue(source[key], seen);\n }\n }\n\n return clone as T;\n}\n\nfunction normalizeInitialEntries(entries: unknown): AppRegistryEntry[] {\n return (Array.isArray(entries) ? entries : []).filter(\n (entry): entry is AppRegistryEntry =>\n entry?.type && entry?.items && typeof entry.items === \"object\",\n );\n}\n\nfunction createInitialState(\n ops: RegistryOperations,\n definitions: RegistryDefinitions,\n entries: unknown,\n): RegistryState {\n const normalizedEntries = normalizeInitialEntries(entries);\n if (normalizedEntries.length === 0) return ops.createInitialRegistries();\n\n const timestamp = Date.now();\n let sequence = 0;\n let state = ops.createInitialRegistries();\n\n normalizedEntries.forEach((entry) => {\n const source = entry.source || REGISTRY_SOURCES.STATIC;\n const options: RegistryMetadata = {\n ...(entry.options || {}),\n instanceId:\n entry.instanceId || entry.options?.instanceId || \"registry-initial\",\n };\n\n Object.entries(entry.items).forEach(([key, value]) => {\n const validation = validateRegistration(\n definitions,\n entry.type,\n key,\n value,\n source,\n options,\n );\n if (!validation.valid) return;\n\n const operation = createRegisterOperation(\n entry.type,\n key,\n cloneRegistryValue(value),\n source,\n options,\n timestamp,\n ++sequence,\n );\n if (ops.hasOperationEffect(state, operation)) {\n state = ops.applyOperation(state, operation);\n }\n });\n });\n return state;\n}\n\nfunction notifyListeners(listeners: Set<() => void> | undefined): void {\n if (!listeners) return;\n for (const listener of listeners) {\n try {\n listener();\n } catch (error) {\n report(\"Registry listener\", error);\n }\n }\n}\n\nfunction getOrCreateKeyListeners(\n listenersByType: Map<string, Map<string | null, Set<() => void>>>,\n type: string,\n key: string | null,\n): Set<() => void> {\n let listeners = listenersByType.get(type);\n if (!listeners) {\n listeners = new Map();\n listenersByType.set(type, listeners);\n }\n let keyListeners = listeners.get(key);\n if (!keyListeners) {\n keyListeners = new Set();\n listeners.set(key, keyListeners);\n }\n return keyListeners;\n}\n\nfunction resolveRegistrationOptions(\n sourceOrOptions: RegistrySourceOrOptions | undefined,\n optionsArg?: RegistryMetadata,\n): RegistryMetadata {\n if (sourceOrOptions && typeof sourceOrOptions === \"object\")\n return sourceOrOptions;\n return optionsArg && typeof optionsArg === \"object\" ? optionsArg : {};\n}\n\nfunction validateRegistration(\n definitions: RegistryDefinitions,\n type: string,\n key: string,\n value: unknown,\n sourceOrOptions: RegistrySourceOrOptions | undefined,\n optionsArg?: RegistryMetadata,\n): { issues?: string[]; reason?: string; valid: boolean } {\n const options = resolveRegistrationOptions(sourceOrOptions, optionsArg);\n const metadataValidation = validateRegistryMetadata(options);\n const isStrict = options.validation === REGISTRY_VALIDATION_MODES.STRICT;\n\n if (!metadataValidation.valid && isStrict) {\n return {\n issues: metadataValidation.issues,\n reason: \"invalid-metadata\",\n valid: false,\n };\n }\n\n const validation = validateRegistryValue(type, key, value, definitions);\n if (validation.valid) return { valid: true };\n\n if (!isStrict) {\n report(`Registry ${type} \"${key}\" is invalid`, validation.issues, \"warn\");\n }\n\n return {\n issues: validation.issues,\n reason: \"invalid-value\",\n valid: !isStrict,\n };\n}\n\nfunction createRegistrationHandle(\n store: RegistryStore,\n operation: RegisterOperation,\n): RegistrationHandle {\n let disposed = false;\n const dispose = (reason = \"manual\") => {\n if (disposed) return false;\n disposed = true;\n return store.dispose(operation, reason);\n };\n\n const handle = ((reason?: string) => dispose(reason)) as RegistrationHandle;\n handle.dispose = dispose;\n\n handle.update = (value: unknown, options: RegistryMetadata = {}) => {\n if (disposed || !store.isCurrent(operation)) return NOOP_HANDLE;\n const nextHandle = store.register(\n operation.type,\n operation.key,\n value,\n operation.source,\n {\n ...(typeof options === \"object\" ? options : {}),\n instanceId: operation.instanceId,\n priority: operation.record.priority,\n ...(operation.scope ? { scope: operation.scope } : {}),\n ...(operation.validation ? { validation: operation.validation } : {}),\n },\n );\n if (isNoopHandle(nextHandle)) return handle;\n disposed = true;\n return nextHandle;\n };\n\n Object.defineProperties(handle, {\n active: {\n enumerable: true,\n get: () => !disposed && store.isCurrent(operation),\n },\n instanceId: { enumerable: true, value: operation.instanceId },\n key: { enumerable: true, value: operation.key },\n priority: { enumerable: true, value: operation.record.priority },\n source: { enumerable: true, value: operation.source },\n status: {\n enumerable: true,\n get: () =>\n disposed\n ? \"disposed\"\n : store.isCurrent(operation)\n ? \"active\"\n : \"superseded\",\n },\n type: { enumerable: true, value: operation.type },\n updatedAt: { enumerable: true, value: operation.record.updatedAt },\n validation: { enumerable: true, value: operation.validation || \"warn\" },\n });\n\n return handle as RegistrationHandle;\n}\n\nfunction prepareRegisterOperation(\n ops: RegistryOperations,\n definitions: RegistryDefinitions,\n type: string,\n key: string,\n item: unknown,\n sourceOrOptions: RegistrySourceOrOptions,\n optionsArg: RegistryMetadata,\n timestamp: number,\n sequence: number,\n): { operation: RegisterOperation } | { rejected: RegistrationHandle } {\n if (!ops.isValidRegistryTarget(type, key)) {\n return { rejected: createNoopHandle(\"rejected\", \"invalid-target\") };\n }\n\n const validation = validateRegistration(\n definitions,\n type,\n key,\n item,\n sourceOrOptions,\n optionsArg,\n );\n if (!validation.valid) {\n return { rejected: createNoopHandle(\"rejected\", validation.reason) };\n }\n\n return {\n operation: createRegisterOperation(\n type,\n key,\n cloneRegistryValue(item),\n sourceOrOptions,\n optionsArg,\n timestamp,\n sequence,\n ),\n };\n}\n\nexport function createRegistryStore(\n initialEntries: InitialRegistryEntries = [],\n definitions: RegistryDefinitions = NO_DEFINITIONS,\n): RegistryStore {\n const ops = createRegistryOperations(definitions);\n let registries = createInitialState(ops, definitions, initialEntries);\n let sequence = normalizeInitialEntries(initialEntries).reduce(\n (count, entry) => count + Object.keys(entry.items).length,\n 0,\n );\n\n const listenersByType = new Map<\n string,\n Map<string | null, Set<() => void>>\n >();\n const entrySnapshots = new Map<\n string,\n {\n typeRegistry: RegistryState[string];\n value: Readonly<Record<string, unknown>>;\n }\n >();\n const valueSnapshots = new Map<\n string,\n Map<\n string,\n { entry: RegistryState[string][string] | undefined; value: unknown }\n >\n >();\n const resolveCachedValue = ops.createResolverCache();\n\n const subscribe = (\n type: string,\n key: string | null | undefined,\n listener: () => void,\n ) => {\n const keyListeners = getOrCreateKeyListeners(\n listenersByType,\n type,\n key ?? null,\n );\n keyListeners.add(listener);\n\n return () => {\n keyListeners.delete(listener);\n if (keyListeners.size > 0) return;\n\n const listeners = listenersByType.get(type);\n if (listeners) {\n listeners.delete(key ?? null);\n if (listeners.size === 0) listenersByType.delete(type);\n }\n };\n };\n\n const commit = (\n nextState: RegistryState,\n operations: RegistryOperation[] = [],\n ) => {\n if (registries === nextState) return;\n const previousState = registries;\n registries = nextState;\n\n const changedKeysByType = new Map<string, Set<string>>();\n for (const operation of operations) {\n if (!ops.isValidRegistryTarget(operation?.type, operation?.key)) continue;\n let keys = changedKeysByType.get(operation.type);\n if (!keys) {\n keys = new Set();\n changedKeysByType.set(operation.type, keys);\n }\n keys.add(operation.key);\n }\n\n for (const [type, changedKeys] of changedKeysByType) {\n const previousRegistry = previousState[type] || {};\n const nextRegistry = nextState[type] || {};\n const typeListeners = listenersByType.get(type);\n let typeChanged = false;\n\n if (!typeListeners) continue;\n\n for (const key of changedKeys) {\n if (previousRegistry[key] === nextRegistry[key]) continue;\n typeChanged = true;\n notifyListeners(typeListeners.get(key));\n }\n\n if (typeChanged) {\n notifyListeners(typeListeners.get(null));\n }\n }\n };\n\n const isCurrent = (operation: RegisterOperation) => {\n const entry = registries[operation.type]?.[operation.key];\n const recordKey = createRecordKey(\n operation.source,\n operation.instanceId,\n operation.scope,\n );\n return entry?.[recordKey] === operation.record;\n };\n\n const dispose = (\n operation: RegisterOperation,\n _reason = \"manual\",\n ): boolean => {\n if (!isCurrent(operation)) return false;\n const unregisterOperation = createUnregisterOperation(\n operation.type,\n operation.key,\n {\n source: operation.source,\n instanceId: operation.instanceId,\n scope: operation.scope,\n },\n );\n\n if (!ops.hasOperationEffect(registries, unregisterOperation)) return false;\n commit(ops.applyOperation(registries, unregisterOperation), [\n unregisterOperation,\n ]);\n return true;\n };\n\n const register = (\n type: string,\n key: string,\n item: unknown,\n sourceOrOptions: RegistrySourceOrOptions = DEFAULT_SOURCE,\n optionsArg: RegistryMetadata = {},\n ): RegistrationHandle => {\n const prepared = prepareRegisterOperation(\n ops,\n definitions,\n type,\n key,\n item,\n sourceOrOptions,\n optionsArg,\n Date.now(),\n ++sequence,\n );\n if (\"rejected\" in prepared) return prepared.rejected;\n\n const { operation } = prepared;\n if (!ops.hasOperationEffect(registries, operation)) {\n return createNoopHandle(\"ignored\", \"unchanged\");\n }\n\n commit(ops.applyOperation(registries, operation), [operation]);\n return createRegistrationHandle(store, operation);\n };\n\n const unregister = (\n type: string,\n key: string,\n sourceOrOptions: RegistrySourceOrOptions = DEFAULT_SOURCE,\n ): void => {\n if (!ops.isValidRegistryTarget(type, key)) return;\n const operation = createUnregisterOperation(type, key, sourceOrOptions);\n if (!ops.hasOperationEffect(registries, operation)) return;\n\n commit(ops.applyOperation(registries, operation), [operation]);\n };\n\n const batch = (executor: (queue: RegistryQueue) => void): number => {\n if (typeof executor !== \"function\") return 0;\n const timestamp = Date.now();\n const operations: RegistryOperation[] = [];\n\n const queue: RegistryQueue = {\n register: (\n type: string,\n key: string,\n item: unknown,\n sourceOrOptions: RegistrySourceOrOptions = DEFAULT_SOURCE,\n optionsArg: RegistryMetadata = {},\n ): RegistrationHandle => {\n const prepared = prepareRegisterOperation(\n ops,\n definitions,\n type,\n key,\n item,\n sourceOrOptions,\n optionsArg,\n timestamp,\n ++sequence,\n );\n if (\"rejected\" in prepared) return prepared.rejected;\n\n operations.push(prepared.operation);\n return createRegistrationHandle(store, prepared.operation);\n },\n unregister: (\n type: string,\n key: string,\n sourceOrOptions: RegistrySourceOrOptions = DEFAULT_SOURCE,\n ): void => {\n if (!ops.isValidRegistryTarget(type, key)) return;\n operations.push(createUnregisterOperation(type, key, sourceOrOptions));\n },\n };\n\n executor(queue);\n if (operations.length === 0) return 0;\n\n const { effectiveOperations, nextState } = ops.resolveEffectiveOperations(\n registries,\n operations,\n );\n if (effectiveOperations.length === 0) return 0;\n\n commit(nextState, effectiveOperations);\n return effectiveOperations.length;\n };\n\n const getSnapshot = (\n type: string,\n key: string,\n scope: string | null = null,\n ): unknown => {\n const entry = registries[type]?.[key];\n let snapshots = valueSnapshots.get(type);\n if (!snapshots) {\n snapshots = new Map();\n valueSnapshots.set(type, snapshots);\n }\n\n const cacheKey = scope === null ? key : `${scope}\\u0000${key}`;\n\n if (entry === undefined) {\n snapshots.delete(cacheKey);\n return undefined;\n }\n\n const cached = snapshots.get(cacheKey);\n if (cached && cached.entry === entry) return cached.value;\n\n const value = resolveCachedValue(type, entry, scope);\n snapshots.set(cacheKey, { entry, value });\n return value;\n };\n\n const getEntriesSnapshot = (\n type: string,\n scope: string | null = null,\n ): Readonly<Record<string, unknown>> => {\n const typeRegistry = registries[type] || {};\n\n const cacheKey = `${type}::${scope ?? \"null\"}`;\n const cached = entrySnapshots.get(cacheKey);\n\n if (cached?.typeRegistry === typeRegistry) return cached.value;\n\n const resolved: Record<string, unknown> = {};\n for (const key in typeRegistry) {\n if (Object.prototype.hasOwnProperty.call(typeRegistry, key)) {\n const value = resolveCachedValue(type, typeRegistry[key], scope);\n if (value !== undefined) resolved[key] = value;\n }\n }\n\n const finalValue = Object.freeze(resolved);\n entrySnapshots.set(cacheKey, { typeRegistry, value: finalValue });\n return finalValue;\n };\n\n const store = {\n batch,\n dispose,\n getEntriesSnapshot,\n getSnapshot,\n isCurrent,\n register,\n subscribe,\n transaction: (\n executor: (tx: RegistryTransactionQueue) => void,\n metadata: RegistryMetadata = {},\n ) => createRegistryTransaction(store, metadata).run(executor),\n unregister,\n } as RegistryStore;\n return store;\n}\n","\"use client\";\n\nimport {\n createContext,\n useCallback,\n useMemo,\n useState,\n useSyncExternalStore,\n type ReactNode,\n} from \"react\";\nimport { useRequiredContext } from \"@/hooks\";\nimport type {\n RegistryDefinitions,\n RegistrySchema,\n RegistryStore,\n} from \"./types\";\nimport { createRegistryStore, type InitialRegistryEntries } from \"./store\";\n\ntype RegistryValueOf<K extends string> = K extends keyof RegistrySchema\n ? RegistrySchema[K]\n : unknown;\n\ninterface RegistryContextValue {\n actions: Pick<\n RegistryStore,\n \"batch\" | \"register\" | \"transaction\" | \"unregister\"\n >;\n subscription: Pick<\n RegistryStore,\n \"getEntriesSnapshot\" | \"getSnapshot\" | \"subscribe\"\n >;\n}\nimport { getOrCreateGlobalContext } from \"./context-registry\";\n\nconst RegistryContext = getOrCreateGlobalContext<RegistryContextValue | null>(\n \"RegistryContext\",\n null,\n);\n\nexport function RegistryProvider({\n children,\n definitions,\n initialEntries = [],\n}: {\n children?: ReactNode;\n definitions?: RegistryDefinitions;\n initialEntries?: InitialRegistryEntries;\n}) {\n const [store] = useState(() =>\n createRegistryStore(initialEntries, definitions),\n );\n\n const contextValue = useMemo(\n () => ({\n actions: {\n batch: store.batch,\n register: store.register,\n transaction: store.transaction,\n unregister: store.unregister,\n },\n subscription: {\n getEntriesSnapshot: store.getEntriesSnapshot,\n getSnapshot: store.getSnapshot,\n subscribe: store.subscribe,\n },\n }),\n [store],\n );\n\n return <RegistryContext value={contextValue}>{children}</RegistryContext>;\n}\n\nexport function useRegistryActions(): RegistryContextValue[\"actions\"] {\n return useRequiredContext(\n RegistryContext,\n \"useRegistryActions\",\n \"RegistryProvider\",\n ).actions;\n}\n\nfunction useRegistrySubscription(): RegistryContextValue[\"subscription\"] {\n return useRequiredContext(\n RegistryContext,\n \"useRegistrySubscription\",\n \"RegistryProvider\",\n ).subscription;\n}\n\nexport function useRegistryValue<\n K extends string = string,\n T = RegistryValueOf<K>,\n>(type: K, key: string): T | undefined {\n const { getSnapshot, subscribe } = useRegistrySubscription();\n\n const subscribeToKey = useCallback(\n (listener: () => void) => subscribe(type, key, listener),\n [key, subscribe, type],\n );\n const getValue = useCallback(\n () => getSnapshot<K, T>(type, key),\n [getSnapshot, key, type],\n );\n\n return useSyncExternalStore(subscribeToKey, getValue, getValue);\n}\n\nexport function useRegistryEntries<\n K extends string = string,\n T = RegistryValueOf<K>,\n>(type: K): Record<string, T> {\n const { getEntriesSnapshot, subscribe } = useRegistrySubscription();\n\n const subscribeToType = useCallback(\n (listener: () => void) => subscribe(type, null, listener),\n [subscribe, type],\n );\n const getEntries = useCallback(\n () => getEntriesSnapshot<K, T>(type),\n [getEntriesSnapshot, type],\n );\n\n return useSyncExternalStore(subscribeToType, getEntries, getEntries);\n}\n","\"use client\";\n\nimport { createContext, use, type ComponentType, type ReactNode } from \"react\";\nimport { isObject } from \"@/utils\";\nimport type {\n AnyCoreModule,\n PageConfig,\n RegistryDefinition,\n RegistryDefinitions,\n RegistryMetadata,\n} from \"./types\";\n\nexport type BoundaryComponent = ComponentType<{\n children?: ReactNode;\n name?: string;\n}>;\n\nexport interface ModuleHostValue {\n Boundary: BoundaryComponent;\n byId: ReadonlyMap<string, AnyCoreModule>;\n definitions: RegistryDefinitions;\n modules: readonly AnyCoreModule[];\n}\n\nexport const EMPTY_MODULES: readonly AnyCoreModule[] = Object.freeze([]);\n\nexport const PassthroughBoundary: BoundaryComponent = ({ children }) =>\n children;\nimport { getOrCreateGlobalContext } from \"./context-registry\";\n\nexport const ModuleHostContext =\n getOrCreateGlobalContext<ModuleHostValue | null>(\"ModuleHostContext\", null);\n\nexport function selectModuleSlice(\n coreModule: AnyCoreModule,\n config: PageConfig,\n): unknown {\n const slice = coreModule.page?.select\n ? coreModule.page.select(config)\n : (config as Record<string, unknown>)[coreModule.id];\n return slice ?? null;\n}\n\nexport function createModulePayload(\n modules: readonly AnyCoreModule[],\n config: PageConfig,\n metadata: RegistryMetadata = {},\n): PageConfig | null {\n const payload: Record<string, unknown> = {};\n let hasSlices = false;\n for (const coreModule of modules) {\n if (!coreModule.page?.entries) continue;\n const slice = selectModuleSlice(coreModule, config);\n if (slice === null) continue;\n payload[coreModule.id] = slice;\n hasSlices = true;\n }\n if (!hasSlices) return null;\n return {\n ...payload,\n registry: {\n ...metadata,\n ...(isObject(config.registry) ? config.registry : {}),\n },\n } as PageConfig;\n}\n\nconst MODULE_ID_PATTERN = /^[a-z][a-zA-Z0-9]*$/;\n\nexport function sortModules(\n modules: readonly AnyCoreModule[],\n): AnyCoreModule[] {\n const byId = new Map<string, AnyCoreModule>();\n for (const coreModule of modules) {\n if (!MODULE_ID_PATTERN.test(coreModule.id)) {\n throw new Error(\n `[Core] Invalid module id \"${coreModule.id}\": use a camelCase name such as \"contextMenu\".`,\n );\n }\n if (byId.has(coreModule.id)) {\n throw new Error(`[Core] Module \"${coreModule.id}\" is installed twice.`);\n }\n byId.set(coreModule.id, coreModule);\n }\n\n const sorted: AnyCoreModule[] = [];\n const state = new Map<string, \"visiting\" | \"done\">();\n const visit = (coreModule: AnyCoreModule, path: string[]) => {\n const current = state.get(coreModule.id);\n if (current === \"done\") return;\n if (current === \"visiting\") {\n throw new Error(\n `[Core] Module dependency cycle: ${[...path, coreModule.id].join(\" -> \")}`,\n );\n }\n state.set(coreModule.id, \"visiting\");\n for (const id of coreModule.uses ?? []) {\n const dependency = byId.get(id);\n if (dependency) visit(dependency, [...path, coreModule.id]);\n }\n state.set(coreModule.id, \"done\");\n sorted.push(coreModule);\n };\n modules.forEach((coreModule) => visit(coreModule, []));\n return sorted;\n}\n\nexport function createModuleRegistryDefinitions(\n modules: readonly AnyCoreModule[],\n): RegistryDefinitions {\n const definitions = new Map<string, RegistryDefinition>();\n for (const coreModule of modules) {\n if (coreModule.registry)\n definitions.set(coreModule.id, coreModule.registry);\n }\n return definitions;\n}\n\nexport function useInstalledModules(): readonly AnyCoreModule[] {\n return use(ModuleHostContext)?.modules ?? EMPTY_MODULES;\n}\n","\"use client\";\n\nimport {\n createContext,\n use,\n useCallback,\n useEffect,\n useId,\n useMemo,\n useRef,\n useState,\n useSyncExternalStore,\n type ReactNode,\n} from \"react\";\nimport { useIsomorphicLayoutEffect } from \"@/hooks\";\nimport { useRegistry, useShallowStable } from \"./hooks\";\nimport { selectModuleSlice, useInstalledModules } from \"./installed\";\nimport { pickRegistryMetadata } from \"./schema\";\nimport { mergeModuleConfigs } from \"./utils\";\nimport type {\n PageConfig,\n PageController,\n PageControllerStore,\n PageModuleApi,\n PageModules,\n PageOptions,\n} from \"./types\";\nimport { report } from \"@/utils\";\n\nconst EMPTY_OBJECT: PageConfig = Object.freeze({});\n\nfunction createPageControllerStore(): PageControllerStore {\n const listeners = new Set<() => void>();\n let stack: {\n controllerRef: { current: PageController | null };\n id: string;\n }[] = [];\n\n const notify = (): void => {\n listeners.forEach((listener) => {\n try {\n listener();\n } catch (error) {\n report(\"Page controller listener\", error);\n }\n });\n };\n\n return {\n getSnapshot(): PageController | null {\n const top = stack[stack.length - 1];\n return top?.controllerRef?.current || null;\n },\n notify,\n register(\n id: string,\n controllerRef: { current: PageController | null },\n ): void {\n stack = stack.filter((item) => item.id !== id);\n stack.push({ controllerRef, id });\n notify();\n },\n subscribe(listener: () => void): () => void {\n listeners.add(listener);\n return () => {\n listeners.delete(listener);\n };\n },\n unregister(id: string): void {\n stack = stack.filter((item) => item.id !== id);\n notify();\n },\n };\n}\n\nfunction createControllerScope(): {\n Provider: PageController[\"Provider\"];\n publish: (controller: PageController) => void;\n} {\n const listeners = new Set<() => void>();\n let current: PageController | null = null;\n\n const subscribe = (listener: () => void) => {\n listeners.add(listener);\n return () => {\n listeners.delete(listener);\n };\n };\n const getSnapshot = () => current;\n\n function PageProvider({ children }: { children?: ReactNode }) {\n const controller = useSyncExternalStore(\n subscribe,\n getSnapshot,\n getSnapshot,\n );\n return (\n <PageControllerContext value={controller}>\n {children}\n </PageControllerContext>\n );\n }\n\n return {\n Provider: PageProvider,\n publish(controller) {\n if (current === controller) return;\n current = controller;\n listeners.forEach((listener) => listener());\n },\n };\n}\n\nconst fallbackStandaloneStore = createPageControllerStore();\n\nconst noopHook = () => {};\nconst PassthroughProvider = ({ children }: { children?: ReactNode }) =>\n children;\n\nimport { getOrCreateGlobalContext } from \"./context-registry\";\n\nconst PageControllerContext = getOrCreateGlobalContext<PageController | null>(\n \"PageControllerContext\",\n null,\n);\n\nconst PageControllerStoreContext =\n getOrCreateGlobalContext<PageControllerStore>(\n \"PageControllerStoreContext\",\n fallbackStandaloneStore,\n );\n\nexport function PageControllerProvider({ children }: { children?: ReactNode }) {\n const [store] = useState<PageControllerStore>(() =>\n createPageControllerStore(),\n );\n return (\n <PageControllerStoreContext value={store}>\n {children}\n </PageControllerStoreContext>\n );\n}\n\nconst emptySubscribe = () => () => {};\nconst getNullSnapshot = () => null;\n\nconst FALLBACK_PAGE_CONTROLLER: PageController = Object.freeze({\n Provider: PassthroughProvider,\n config: EMPTY_OBJECT,\n modules: Object.freeze({}),\n reset: noopHook,\n set: noopHook,\n});\n\nexport function usePageController(): PageController {\n const scopedContext = use(PageControllerContext);\n const controllerStore = use(PageControllerStoreContext);\n\n const storeSubscribe = scopedContext\n ? emptySubscribe\n : controllerStore.subscribe;\n const storeSnapshot = scopedContext\n ? getNullSnapshot\n : controllerStore.getSnapshot;\n\n const storeController = useSyncExternalStore(\n storeSubscribe,\n storeSnapshot,\n getNullSnapshot,\n );\n\n return scopedContext ?? storeController ?? FALLBACK_PAGE_CONTROLLER;\n}\n\nexport function usePage(\n pageConfig: PageConfig = EMPTY_OBJECT,\n options?: PageOptions,\n): PageController {\n const instanceId = useId();\n const controllerStore = use(PageControllerStoreContext);\n const modules = useInstalledModules();\n\n const [overrides, setOverrides] = useState<Partial<PageConfig>>(EMPTY_OBJECT);\n\n const set = useCallback((partial: Partial<PageConfig>) => {\n if (!partial || typeof partial !== \"object\") return;\n setOverrides((prev) => mergeModuleConfigs(prev, partial));\n }, []);\n\n const reset = useCallback(() => {\n setOverrides(EMPTY_OBJECT);\n }, []);\n\n const effectiveConfig = useMemo<PageConfig>(() => {\n const base = pageConfig || EMPTY_OBJECT;\n if (Object.keys(overrides).length === 0) return base;\n return mergeModuleConfigs(base, overrides);\n }, [pageConfig, overrides]);\n\n const moduleSlices = useMemo(\n () =>\n modules.map((coreModule) =>\n selectModuleSlice(coreModule, effectiveConfig),\n ),\n [effectiveConfig, modules],\n );\n\n const registryMetadata = useMemo(\n () => pickRegistryMetadata(options),\n [options],\n );\n useRegistry(effectiveConfig, registryMetadata);\n\n const pageApi = useMemo<PageModuleApi>(() => ({ set }), [set]);\n const moduleControllers: Record<string, unknown> = {};\n for (let index = 0; index < modules.length; index += 1) {\n const coreModule = modules[index];\n if (coreModule.page?.use) {\n moduleControllers[coreModule.id] = coreModule.page.use(\n moduleSlices[index],\n pageApi,\n );\n }\n }\n const pageModules = useShallowStable(moduleControllers) as PageModules;\n\n const [scope] = useState(createControllerScope);\n\n const controller = useMemo<PageController>(\n () => ({\n Provider: scope.Provider,\n config: effectiveConfig,\n modules: pageModules,\n reset,\n set,\n }),\n [effectiveConfig, pageModules, reset, scope, set],\n );\n\n const controllerRef = useRef<PageController | null>(controller);\n\n useIsomorphicLayoutEffect(() => {\n controllerRef.current = controller;\n scope.publish(controller);\n controllerStore.notify();\n }, [controller, controllerStore, scope]);\n\n useEffect(() => {\n controllerStore.register(instanceId, controllerRef);\n return () => {\n controllerStore.unregister(instanceId);\n };\n }, [controllerStore, instanceId]);\n\n return controller;\n}\n","\"use client\";\n\nimport { createElement, use, useState, type ReactNode } from \"react\";\nimport { useStore } from \"@/hooks\";\nimport { createStore, type ExternalStore } from \"@/utils\";\nimport {\n EMPTY_MODULES,\n ModuleHostContext,\n PassthroughBoundary,\n createModuleRegistryDefinitions,\n sortModules,\n type BoundaryComponent,\n type ModuleHostValue,\n} from \"./installed\";\nimport { PageControllerProvider } from \"./page-controller\";\nimport { RegistryProvider } from \"./provider\";\nimport type {\n AnyCoreModule,\n AppRegistryEntry,\n CoreModule,\n CoreModules,\n ModuleId,\n ModuleRuntimeOf,\n ModuleStateOf,\n} from \"./types\";\nimport { report } from \"@/utils\";\n\nexport function defineModule<\n TId extends string,\n TRuntime = never,\n TSlice = never,\n TController = never,\n>(\n coreModule: CoreModule<TId, TRuntime, TSlice, TController>,\n): CoreModule<TId, TRuntime, TSlice, TController> {\n return Object.freeze({ ...coreModule });\n}\n\nfunction warnMissingPeers(modules: readonly AnyCoreModule[]): void {\n const installed = new Set(modules.map((coreModule) => coreModule.id));\n for (const { id, uses } of modules) {\n const missing = (uses ?? []).filter((peer) => !installed.has(peer));\n if (missing.length > 0) {\n report(\n `Module \"${id}\" runs without its optional peers`,\n missing.join(\", \"),\n \"warn\",\n );\n }\n }\n}\n\nfunction createModuleHost(\n modules: readonly AnyCoreModule[],\n Boundary: BoundaryComponent,\n): ModuleHostValue {\n const sorted = sortModules(modules);\n if (process.env.NODE_ENV !== \"production\") warnMissingPeers(sorted);\n return {\n Boundary,\n byId: new Map(sorted.map((coreModule) => [coreModule.id, coreModule])),\n definitions: createModuleRegistryDefinitions(sorted),\n modules: Object.freeze(sorted),\n };\n}\n\nexport interface ModuleHostProps {\n boundary?: BoundaryComponent;\n children?: ReactNode;\n modules?: readonly AnyCoreModule[];\n registryEntries?: readonly AppRegistryEntry[];\n}\n\nexport function ModuleHost({\n boundary = PassthroughBoundary,\n children,\n modules = EMPTY_MODULES,\n registryEntries,\n}: ModuleHostProps) {\n const [host] = useState(() => createModuleHost(modules, boundary));\n const { Boundary } = host;\n\n const content = (\n <>\n {host.modules.map(({ Backdrop, id }) =>\n Backdrop ? (\n <Boundary key={id} name={id}>\n <Backdrop />\n </Boundary>\n ) : null,\n )}\n {children}\n {host.modules.map(({ Overlay, id }) =>\n Overlay ? (\n <Boundary key={id} name={id}>\n <Overlay />\n </Boundary>\n ) : null,\n )}\n </>\n );\n\n const tree = host.modules.reduceRight<ReactNode>(\n (inner, { Provider }) => (Provider ? <Provider>{inner}</Provider> : inner),\n content,\n );\n\n return (\n <RegistryProvider\n definitions={host.definitions}\n initialEntries={registryEntries}\n >\n <ModuleHostContext value={host}>\n <PageControllerProvider>{tree}</PageControllerProvider>\n </ModuleHostContext>\n </RegistryProvider>\n );\n}\n\nexport function useModule<K extends ModuleId>(\n id: K,\n): ModuleRuntimeOf<CoreModules[K]> | null {\n const coreModule = use(ModuleHostContext)?.byId.get(id);\n return coreModule?.context ? (use(coreModule.context) ?? null) : null;\n}\n\ntype ModuleActionsOf<K extends ModuleId> =\n ModuleRuntimeOf<CoreModules[K]> extends { actions: infer TActions }\n ? TActions\n : never;\n\nexport interface ModulePeer<K extends ModuleId> {\n useActions(): ModuleActionsOf<K>;\n useRuntime(): ModuleRuntimeOf<CoreModules[K]>;\n useState<T>(\n selector: (state: ModuleStateOf<K>) => T,\n isEqual?: (a: T, b: T) => boolean,\n ): T;\n}\n\nexport function definePeer<K extends ModuleId>(\n id: K,\n inert: ModuleRuntimeOf<CoreModules[K]>,\n): ModulePeer<K> {\n const useRuntime = (): ModuleRuntimeOf<CoreModules[K]> =>\n useModule(id) ?? inert;\n return {\n useRuntime,\n useActions: () => useRuntime().actions as ModuleActionsOf<K>,\n useState: <T,>(\n selector: (state: ModuleStateOf<K>) => T,\n isEqual?: (a: T, b: T) => boolean,\n ) =>\n useStore<ModuleStateOf<K>, T>(\n (useRuntime() as { store: ExternalStore<ModuleStateOf<K>> }).store,\n selector,\n isEqual,\n ),\n };\n}\n\nconst NO_MODULE_STORE: ExternalStore<unknown> = createStore<unknown>(undefined);\n\nexport function useModuleState<K extends ModuleId, T>(\n id: K,\n selector: (state: ModuleStateOf<K>) => T,\n fallback: T,\n isEqual: (a: T, b: T) => boolean = Object.is,\n): T {\n const runtime = useModule(id) as { store: ExternalStore<unknown> } | null;\n return useStore<unknown, T>(\n runtime?.store ?? NO_MODULE_STORE,\n (state) => (runtime ? selector(state as ModuleStateOf<K>) : fallback),\n isEqual,\n );\n}\n\nexport function ModuleBoundary({\n children,\n name,\n}: {\n children?: ReactNode;\n name?: string;\n}) {\n const Boundary = use(ModuleHostContext)?.Boundary ?? PassthroughBoundary;\n return createElement(Boundary, { name }, children);\n}\n\nexport function useIsModuleInstalled(id: ModuleId): boolean {\n return use(ModuleHostContext)?.byId.has(id) ?? false;\n}\n","\"use client\";\n\nimport { useRegistryValue } from \"@/kernel\";\nimport { MEDIA_REGISTRY_KEY, PAGE_MEDIA_ID } from \"./constants\";\nimport { useMedia } from \"./hooks\";\nimport { type MediaPageOptions, type MediaSourceProps } from \"./types\";\n\n/** Declarative form of `useMedia`: mount it anywhere to register an audio source. */\nexport function MediaSource(props: MediaSourceProps) {\n useMedia(props);\n return null;\n}\n\n/**\n * Plays whatever the current page declared with `usePage({ media })`. The\n * registry drops the value when the page goes away, which stops the audio.\n */\nexport function MediaOverlay() {\n const page = useRegistryValue<\"media\", MediaPageOptions>(\n \"media\",\n MEDIA_REGISTRY_KEY,\n );\n useMedia({ ...page, id: PAGE_MEDIA_ID, src: page?.src });\n return null;\n}\n","\"use client\";\n\nimport { useMemo } from \"react\";\nimport { defineModule, type PageModuleApi } from \"@/kernel\";\nimport { MEDIA_REGISTRY_KEY } from \"./constants\";\nimport { MediaContext, MediaProvider, useMediaActions } from \"./context\";\nimport { MediaOverlay } from \"./overlay\";\nimport { selectPageMedia } from \"./utils\";\nimport {\n type MediaPageApi,\n type MediaPageConfig,\n type MediaPageOptions,\n} from \"./types\";\n\nfunction useMediaPage(\n _slice: MediaPageOptions | null,\n page: PageModuleApi,\n): MediaPageApi {\n const actions = useMediaActions();\n return useMemo(\n () => ({\n ...actions,\n set: (media: MediaPageConfig) => page.set({ media }),\n }),\n [actions, page],\n );\n}\n\nexport const mediaModule = defineModule({\n id: \"media\",\n context: MediaContext,\n Provider: MediaProvider,\n Overlay: MediaOverlay,\n registry: {\n cleanupDelayMs: 600,\n keyPolicy: \"singleton\",\n lifecycle: \"immediate\",\n singletonKey: MEDIA_REGISTRY_KEY,\n },\n page: {\n select: (config) => selectPageMedia(config.media),\n entries: (slice: MediaPageOptions) => [\n { key: MEDIA_REGISTRY_KEY, value: slice },\n ],\n use: useMediaPage,\n },\n});\n\ndeclare module \"@omerdlw/base-framework/kernel\" {\n interface CoreModules {\n media: typeof mediaModule;\n }\n interface PageConfig {\n media?: MediaPageConfig;\n }\n}\n"]}
1
+ {"version":3,"sources":["../../../src/hooks/use-required-context.ts","../../../src/hooks/use-store.ts","../../../src/utils/object.ts","../../../src/utils/report.ts","../../../src/utils/store.ts","../../../src/kernel/context-registry.ts","../../../src/kernel/provider.tsx","../../../src/kernel/module.tsx","../../../src/modules/media/constants.ts","../../../src/modules/media/utils.ts","../../../src/modules/media/context.tsx","../../../src/modules/media/hooks.ts","../../../src/modules/media/overlay.tsx","../../../src/modules/media/module.tsx"],"names":["useCallback","useSyncExternalStore","useState","useRef","useMemo","jsx","useEffect"],"mappings":"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","file":"index.js","sourcesContent":["\"use client\";\n\nimport { use, type Context } from \"react\";\n\nexport function useRequiredContext<T>(\n context: Context<T | null>,\n hookName: string,\n providerName: string,\n): T {\n const value = use(context);\n if (value === null) {\n throw new Error(`${hookName} must be used within ${providerName}`);\n }\n return value;\n}\n","\"use client\";\n\nimport { useCallback, useRef, useSyncExternalStore } from \"react\";\nimport { type ExternalStore } from \"../utils\";\n\nexport function useStore<TState, TSlice = TState>(\n store: ExternalStore<TState>,\n selector: (state: TState) => TSlice = (state: TState) =>\n state as unknown as TSlice,\n isEqual: (a: TSlice, b: TSlice) => boolean = Object.is,\n): TSlice {\n const cacheRef = useRef<{\n isEqual: ((a: TSlice, b: TSlice) => boolean) | null;\n selected: TSlice | undefined;\n selector: ((state: TState) => TSlice) | null;\n snapshot: TState | null;\n }>({\n isEqual: null,\n selected: undefined,\n selector: null,\n snapshot: null,\n });\n\n const getSelectedSnapshot = useCallback(() => {\n const snapshot = store.getSnapshot();\n const cache = cacheRef.current;\n if (\n cache.snapshot === snapshot &&\n cache.selector === selector &&\n cache.isEqual === isEqual\n ) {\n return cache.selected as TSlice;\n }\n\n const selected = selector(snapshot);\n if (\n cache.snapshot !== null &&\n cache.isEqual === isEqual &&\n isEqual(cache.selected as TSlice, selected)\n ) {\n cache.snapshot = snapshot;\n cache.selector = selector;\n return cache.selected as TSlice;\n }\n\n cacheRef.current = {\n isEqual,\n selected,\n selector,\n snapshot,\n };\n return selected;\n }, [isEqual, selector, store]);\n\n return useSyncExternalStore(\n store.subscribe,\n getSelectedSnapshot,\n getSelectedSnapshot,\n );\n}\n","export function isObject(value: unknown): value is Record<string, unknown> {\n return Boolean(value) && typeof value === \"object\" && !Array.isArray(value);\n}\n\nexport function isPlainObject(\n value: unknown,\n): value is Record<string, unknown> {\n if (!isObject(value)) return false;\n const proto = Object.getPrototypeOf(value);\n return proto === Object.prototype || proto === null;\n}\n\nexport function shallowEqual(a: unknown, b: unknown): boolean {\n if (Object.is(a, b)) return true;\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 as object);\n const keysB = Object.keys(b as object);\n\n if (keysA.length !== keysB.length) return false;\n\n for (const key of keysA) {\n if (\n !Object.prototype.hasOwnProperty.call(b, key) ||\n !Object.is(\n (a as Record<string, unknown>)[key],\n (b as Record<string, unknown>)[key],\n )\n ) {\n return false;\n }\n }\n\n return true;\n}\n\nexport function toArray<T>(value: T | T[] | null | undefined): T[] {\n if (value === null || value === undefined) return [];\n return Array.isArray(value) ? value : [value];\n}\n","export type ReportLevel = \"error\" | \"warn\";\n\nexport type ReportSink = (\n scope: string,\n error: unknown,\n level: ReportLevel,\n) => void;\n\nlet sink: ReportSink | null = null;\n\nexport function report(\n scope: string,\n error: unknown,\n level: ReportLevel = \"error\",\n): void {\n if (sink) {\n try {\n sink(scope, error, level);\n return;\n } catch {}\n }\n\n if (process.env.NODE_ENV === \"production\" && typeof window !== \"undefined\") {\n return;\n }\n console[level](`[${scope}]`, error);\n}\n\nexport function setReportSink(next: ReportSink): () => void {\n sink = next;\n return () => {\n if (sink === next) sink = null;\n };\n}\n","import { report } from \"./report\";\nexport interface ExternalStore<TState = unknown> {\n readonly getSnapshot: () => TState;\n readonly publish: (\n nextState: TState | ((currentState: TState) => TState),\n ) => boolean;\n readonly setState: (\n updater: Partial<TState> | ((currentState: TState) => TState),\n ) => boolean;\n readonly subscribe: (listener: () => void) => () => void;\n}\n\nfunction freezeStoreSnapshot<TState>(state: TState): TState {\n if (\n process.env.NODE_ENV === \"production\" ||\n !state ||\n typeof state !== \"object\"\n ) {\n return state;\n }\n\n const seen = new WeakSet<object>();\n const freeze = (value: object): void => {\n if (seen.has(value) || Object.isFrozen(value)) return;\n seen.add(value);\n\n const prototype = Object.getPrototypeOf(value);\n if (\n Array.isArray(value) ||\n prototype === Object.prototype ||\n prototype === null\n ) {\n for (const key of Reflect.ownKeys(value)) {\n const descriptor = Object.getOwnPropertyDescriptor(value, key);\n if (descriptor && \"value\" in descriptor && descriptor.value !== null) {\n if (typeof descriptor.value === \"object\") freeze(descriptor.value);\n }\n }\n }\n\n Object.freeze(value);\n };\n\n freeze(state);\n return state;\n}\n\nexport interface CreateStoreOptions {\n freezeSnapshots?: boolean;\n}\n\nexport function createStore<TState = Record<string, unknown>>(\n initialState: TState,\n { freezeSnapshots = true }: CreateStoreOptions = {},\n): ExternalStore<TState> {\n const listeners = new Set<() => void>();\n const prepare = freezeSnapshots\n ? freezeStoreSnapshot\n : <T>(state: T): T => state;\n let snapshot = prepare(initialState);\n\n const publish = (\n nextStateOrUpdater: TState | ((currentState: TState) => TState),\n ): boolean => {\n const nextState =\n typeof nextStateOrUpdater === \"function\"\n ? (nextStateOrUpdater as (currentState: TState) => TState)(snapshot)\n : nextStateOrUpdater;\n if (Object.is(snapshot, nextState)) return false;\n snapshot = prepare(nextState);\n\n for (const listener of listeners) {\n try {\n listener();\n } catch (error) {\n report(\"CoreStore subscriber\", error, \"warn\");\n }\n }\n return true;\n };\n\n const setState = (\n updater: Partial<TState> | ((currentState: TState) => TState),\n ): boolean => {\n if (typeof updater === \"function\") {\n return publish(updater as (currentState: TState) => TState);\n }\n if (\n snapshot &&\n typeof snapshot === \"object\" &&\n updater &&\n typeof updater === \"object\"\n ) {\n return publish({ ...snapshot, ...updater });\n }\n return publish(updater as TState);\n };\n\n return Object.freeze({\n getSnapshot() {\n return snapshot;\n },\n publish,\n setState,\n subscribe(listener: () => void) {\n if (typeof listener !== \"function\") return () => {};\n listeners.add(listener);\n return () => listeners.delete(listener);\n },\n });\n}\n","import { createContext, type Context } from \"react\";\n\nexport function getOrCreateGlobalContext<T>(\n name: string,\n defaultValue: T,\n): Context<T> {\n const sym = Symbol.for(`@omerdlw/base-framework/context/${name}`);\n const store = globalThis as unknown as Record<symbol, Context<T>>;\n if (!store[sym]) {\n store[sym] = createContext<T>(defaultValue);\n }\n return store[sym];\n}\n","\"use client\";\n\nimport {\n useCallback,\n useMemo,\n useState,\n useSyncExternalStore,\n type ReactNode,\n} from \"react\";\nimport { useRequiredContext } from \"@/hooks\";\nimport { getOrCreateGlobalContext } from \"./context-registry\";\n\nimport type {\n RegistryDefinitions,\n RegistrySchema,\n RegistryStore,\n} from \"./types\";\nimport { createRegistryStore, type InitialRegistryEntries } from \"./store\";\n\ntype RegistryValueOf<K extends string> = K extends keyof RegistrySchema\n ? RegistrySchema[K]\n : unknown;\n\ninterface RegistryContextValue {\n actions: Pick<\n RegistryStore,\n \"batch\" | \"register\" | \"transaction\" | \"unregister\"\n >;\n subscription: Pick<\n RegistryStore,\n \"getEntriesSnapshot\" | \"getSnapshot\" | \"subscribe\"\n >;\n}\n\nconst RegistryContext = getOrCreateGlobalContext<RegistryContextValue | null>(\n\n \"RegistryContext\",\n null,\n);\n\nexport function RegistryProvider({\n children,\n definitions,\n initialEntries = [],\n}: {\n children?: ReactNode;\n definitions?: RegistryDefinitions;\n initialEntries?: InitialRegistryEntries;\n}) {\n const [store] = useState(() =>\n createRegistryStore(initialEntries, definitions),\n );\n\n const contextValue = useMemo(\n () => ({\n actions: {\n batch: store.batch,\n register: store.register,\n transaction: store.transaction,\n unregister: store.unregister,\n },\n subscription: {\n getEntriesSnapshot: store.getEntriesSnapshot,\n getSnapshot: store.getSnapshot,\n subscribe: store.subscribe,\n },\n }),\n [store],\n );\n\n return <RegistryContext value={contextValue}>{children}</RegistryContext>;\n}\n\nexport function useRegistryActions(): RegistryContextValue[\"actions\"] {\n return useRequiredContext(\n RegistryContext,\n \"useRegistryActions\",\n \"RegistryProvider\",\n ).actions;\n}\n\nfunction useRegistrySubscription(): RegistryContextValue[\"subscription\"] {\n return useRequiredContext(\n RegistryContext,\n \"useRegistrySubscription\",\n \"RegistryProvider\",\n ).subscription;\n}\n\nexport function useRegistryValue<\n K extends string = string,\n T = RegistryValueOf<K>,\n>(type: K, key: string): T | undefined {\n const { getSnapshot, subscribe } = useRegistrySubscription();\n\n const subscribeToKey = useCallback(\n (listener: () => void) => subscribe(type, key, listener),\n [key, subscribe, type],\n );\n const getValue = useCallback(\n () => getSnapshot<K, T>(type, key),\n [getSnapshot, key, type],\n );\n\n return useSyncExternalStore(subscribeToKey, getValue, getValue);\n}\n\nexport function useRegistryEntries<\n K extends string = string,\n T = RegistryValueOf<K>,\n>(type: K): Record<string, T> {\n const { getEntriesSnapshot, subscribe } = useRegistrySubscription();\n\n const subscribeToType = useCallback(\n (listener: () => void) => subscribe(type, null, listener),\n [subscribe, type],\n );\n const getEntries = useCallback(\n () => getEntriesSnapshot<K, T>(type),\n [getEntriesSnapshot, type],\n );\n\n return useSyncExternalStore(subscribeToType, getEntries, getEntries);\n}\n","\"use client\";\n\nimport { createElement, use, useState, type ReactNode } from \"react\";\nimport { useStore } from \"@/hooks\";\nimport { createStore, type ExternalStore } from \"@/utils\";\nimport {\n EMPTY_MODULES,\n ModuleHostContext,\n PassthroughBoundary,\n createModuleRegistryDefinitions,\n sortModules,\n type BoundaryComponent,\n type ModuleHostValue,\n} from \"./installed\";\nimport { PageControllerProvider } from \"./page-controller\";\nimport { RegistryProvider } from \"./provider\";\nimport type {\n AnyCoreModule,\n AppRegistryEntry,\n CoreModule,\n CoreModules,\n ModuleId,\n ModuleRuntimeOf,\n ModuleStateOf,\n} from \"./types\";\nimport { report } from \"@/utils\";\n\nexport function defineModule<\n TId extends string,\n TRuntime = never,\n TSlice = never,\n TController = never,\n>(\n coreModule: CoreModule<TId, TRuntime, TSlice, TController>,\n): CoreModule<TId, TRuntime, TSlice, TController> {\n return Object.freeze({ ...coreModule });\n}\n\nfunction warnMissingPeers(modules: readonly AnyCoreModule[]): void {\n const installed = new Set(modules.map((coreModule) => coreModule.id));\n for (const { id, uses } of modules) {\n const missing = (uses ?? []).filter((peer) => !installed.has(peer));\n if (missing.length > 0) {\n report(\n `Module \"${id}\" runs without its optional peers`,\n missing.join(\", \"),\n \"warn\",\n );\n }\n }\n}\n\nfunction createModuleHost(\n modules: readonly AnyCoreModule[],\n Boundary: BoundaryComponent,\n): ModuleHostValue {\n const sorted = sortModules(modules);\n if (process.env.NODE_ENV !== \"production\") warnMissingPeers(sorted);\n return {\n Boundary,\n byId: new Map(sorted.map((coreModule) => [coreModule.id, coreModule])),\n definitions: createModuleRegistryDefinitions(sorted),\n modules: Object.freeze(sorted),\n };\n}\n\nexport interface ModuleHostProps {\n boundary?: BoundaryComponent;\n children?: ReactNode;\n modules?: readonly AnyCoreModule[];\n registryEntries?: readonly AppRegistryEntry[];\n}\n\nexport function ModuleHost({\n boundary = PassthroughBoundary,\n children,\n modules = EMPTY_MODULES,\n registryEntries,\n}: ModuleHostProps) {\n const [host] = useState(() => createModuleHost(modules, boundary));\n const { Boundary } = host;\n\n const content = (\n <>\n {host.modules.map(({ Backdrop, id }) =>\n Backdrop ? (\n <Boundary key={id} name={id}>\n <Backdrop />\n </Boundary>\n ) : null,\n )}\n {children}\n {host.modules.map(({ Overlay, id }) =>\n Overlay ? (\n <Boundary key={id} name={id}>\n <Overlay />\n </Boundary>\n ) : null,\n )}\n </>\n );\n\n const tree = host.modules.reduceRight<ReactNode>(\n (inner, { Provider }) => (Provider ? <Provider>{inner}</Provider> : inner),\n content,\n );\n\n return (\n <RegistryProvider\n definitions={host.definitions}\n initialEntries={registryEntries}\n >\n <ModuleHostContext value={host}>\n <PageControllerProvider>{tree}</PageControllerProvider>\n </ModuleHostContext>\n </RegistryProvider>\n );\n}\n\nexport function useModule<K extends ModuleId>(\n id: K,\n): ModuleRuntimeOf<CoreModules[K]> | null {\n const coreModule = use(ModuleHostContext)?.byId.get(id);\n return coreModule?.context ? (use(coreModule.context) ?? null) : null;\n}\n\ntype ModuleActionsOf<K extends ModuleId> =\n ModuleRuntimeOf<CoreModules[K]> extends { actions: infer TActions }\n ? TActions\n : never;\n\nexport interface ModulePeer<K extends ModuleId> {\n useActions(): ModuleActionsOf<K>;\n useRuntime(): ModuleRuntimeOf<CoreModules[K]>;\n useState<T>(\n selector: (state: ModuleStateOf<K>) => T,\n isEqual?: (a: T, b: T) => boolean,\n ): T;\n}\n\nexport function definePeer<K extends ModuleId>(\n id: K,\n inert: ModuleRuntimeOf<CoreModules[K]>,\n): ModulePeer<K> {\n const useRuntime = (): ModuleRuntimeOf<CoreModules[K]> =>\n useModule(id) ?? inert;\n return {\n useRuntime,\n useActions: () => useRuntime().actions as ModuleActionsOf<K>,\n useState: <T,>(\n selector: (state: ModuleStateOf<K>) => T,\n isEqual?: (a: T, b: T) => boolean,\n ) =>\n useStore<ModuleStateOf<K>, T>(\n (useRuntime() as { store: ExternalStore<ModuleStateOf<K>> }).store,\n selector,\n isEqual,\n ),\n };\n}\n\nconst NO_MODULE_STORE: ExternalStore<unknown> = createStore<unknown>(undefined);\n\nexport function useModuleState<K extends ModuleId, T>(\n id: K,\n selector: (state: ModuleStateOf<K>) => T,\n fallback: T,\n isEqual: (a: T, b: T) => boolean = Object.is,\n): T {\n const runtime = useModule(id) as { store: ExternalStore<unknown> } | null;\n return useStore<unknown, T>(\n runtime?.store ?? NO_MODULE_STORE,\n (state) => (runtime ? selector(state as ModuleStateOf<K>) : fallback),\n isEqual,\n );\n}\n\nexport function ModuleBoundary({\n children,\n name,\n}: {\n children?: ReactNode;\n name?: string;\n}) {\n const Boundary = use(ModuleHostContext)?.Boundary ?? PassthroughBoundary;\n return createElement(Boundary, { name }, children);\n}\n\nexport function useIsModuleInstalled(id: ModuleId): boolean {\n return use(ModuleHostContext)?.byId.has(id) ?? false;\n}\n","import { type MediaActions, type MediaState } from \"./types\";\n\nexport const DEFAULT_MEDIA_STATE: MediaState = Object.freeze({\n audibleElement: null,\n element: null,\n hasMedia: false,\n isPlaying: false,\n kind: null,\n loop: false,\n sourceId: null,\n});\n\nexport const INERT_MEDIA_ACTIONS: MediaActions = Object.freeze({\n removeSource: () => {},\n setMuted: () => {},\n toggle: () => {},\n toggleLoop: () => {},\n upsertSource: () => {},\n});\n\n\nexport const MEDIA_SYNC_DRIFT_SECONDS = 0.3;\n\nexport const MEDIA_REGISTRY_KEY = \"page-media\";\n\n/** Id of the audio source registered through `usePage({ media })`. */\nexport const PAGE_MEDIA_ID = \"page\";\n","import { shallowEqual } from \"@/utils\";\nimport { DEFAULT_MEDIA_STATE, MEDIA_SYNC_DRIFT_SECONDS } from \"./constants\";\nimport {\n type MediaSession,\n type MediaEntry,\n type MediaEntryInput,\n type MediaPageConfig,\n type MediaPageOptions,\n type MediaState,\n} from \"./types\";\n\nconst noop = () => {};\n\nfunction newest(sources: readonly MediaEntry[]): MediaEntry {\n return sources.reduce((a, b) => (b.order > a.order ? b : a));\n}\n\nexport function resolveMediaSession(\n sources: readonly MediaEntry[],\n): MediaSession | null {\n if (sources.length === 0) return null;\n\n const ids = new Set(sources.map((source) => source.id));\n const wantsFollow = (source: MediaEntry) =>\n Boolean(source.follow) &&\n source.follow !== source.id &&\n ids.has(source.follow!);\n const rootIds = new Set(\n sources.filter((source) => !wantsFollow(source)).map((source) => source.id),\n );\n const isFollower = (source: MediaEntry) =>\n wantsFollow(source) && rootIds.has(source.follow!);\n\n const transport = newest(sources.filter((source) => !isFollower(source)));\n const followers = sources\n .filter((source) => isFollower(source) && source.follow === transport.id)\n .sort((a, b) => a.order - b.order);\n const audioFollowers = followers.filter((source) => source.kind === \"audio\");\n\n return {\n audible: audioFollowers.length > 0 ? newest(audioFollowers) : transport,\n followers,\n transport,\n };\n}\n\nexport function createMediaState(session: MediaSession | null): MediaState {\n if (!session) return DEFAULT_MEDIA_STATE;\n const { audible, transport } = session;\n return {\n audibleElement: audible.element,\n element: transport.element,\n hasMedia: true,\n isPlaying: transport.isPlaying,\n kind: transport.kind,\n loop: transport.loop,\n sourceId: transport.id,\n };\n}\n\nexport function mediaStatesEqual(a: MediaState, b: MediaState): boolean {\n return shallowEqual(a, b);\n}\n\nexport function mergeMediaSource(\n current: MediaEntry | undefined,\n input: MediaEntryInput,\n order: number,\n): MediaEntry {\n return {\n controls: undefined,\n element: null,\n follow: null,\n isPlaying: false,\n kind: \"audio\",\n loop: false,\n ...current,\n ...input,\n order: current?.order ?? order,\n };\n}\n\nexport function toggleElement(element: HTMLMediaElement | null): void {\n if (!element) return;\n if (element.paused || element.ended) {\n void Promise.resolve(element.play()).catch(noop);\n } else {\n element.pause();\n }\n}\n\nexport function safePlay(element: HTMLMediaElement): void {\n try {\n void Promise.resolve(element.play()).catch(noop);\n } catch {\n /* autoplay blocked or element detached */\n }\n}\n\nexport function bindFollowers(\n transport: HTMLMediaElement,\n followers: readonly HTMLMediaElement[],\n): () => void {\n const ownLoops = followers.map((follower) => follower.loop);\n\n const align = (hard: boolean) => {\n const time = Number(transport.currentTime) || 0;\n for (const follower of followers) {\n follower.loop = false;\n if (follower.playbackRate !== transport.playbackRate) {\n follower.playbackRate = transport.playbackRate;\n }\n const drift = Math.abs((Number(follower.currentTime) || 0) - time);\n if (hard || drift > MEDIA_SYNC_DRIFT_SECONDS) follower.currentTime = time;\n }\n };\n const play = () => {\n align(false);\n followers.forEach(safePlay);\n };\n const pause = () => followers.forEach((follower) => follower.pause());\n const hardAlign = () => align(true);\n const softAlign = () => align(false);\n\n const listeners: [string, () => void][] = [\n [\"play\", play],\n [\"playing\", play],\n [\"pause\", pause],\n [\"waiting\", pause],\n [\"ended\", pause],\n [\"seeking\", hardAlign],\n [\"seeked\", hardAlign],\n [\"ratechange\", softAlign],\n [\"timeupdate\", softAlign],\n ];\n for (const [type, listener] of listeners) {\n transport.addEventListener(type, listener);\n }\n\n hardAlign();\n if (!transport.paused && !transport.ended) play();\n\n return () => {\n for (const [type, listener] of listeners) {\n transport.removeEventListener(type, listener);\n }\n followers.forEach((follower, index) => {\n follower.loop = ownLoops[index];\n });\n };\n}\n\nexport function sameElements(\n a: readonly (HTMLMediaElement | null)[],\n b: readonly (HTMLMediaElement | null)[],\n): boolean {\n return (\n a.length === b.length && a.every((element, index) => element === b[index])\n );\n}\n\nexport function selectPageMedia(\n media: MediaPageConfig | null | undefined,\n): MediaPageOptions | null {\n if (!media) return null;\n if (typeof media === \"string\") return { src: media };\n return media.src ? media : null;\n}\n\n/**\n * Standalone audio that a newly registered source pushes out of the controls.\n * Two independent tracks would otherwise play over each other while the dock\n * only controls the newest.\n */\nexport function findDisplacedAudio(\n entries: readonly MediaEntry[],\n session: MediaSession | null,\n newId: string,\n): MediaEntry[] {\n if (!session || session.transport.id !== newId) return [];\n const followerIds = new Set(session.followers.map((entry) => entry.id));\n return entries.filter(\n (entry) =>\n entry.id !== newId &&\n !followerIds.has(entry.id) &&\n entry.kind === \"audio\" &&\n entry.element !== null &&\n !entry.element.paused,\n );\n}\n","\"use client\";\n\nimport { useContext, useEffect, useMemo, useRef, useState } from \"react\";\nimport { useRequiredContext, useStore } from \"@/hooks\";\nimport { getOrCreateGlobalContext } from \"@/kernel\";\nimport { createStore } from \"@/utils\";\n\nimport { DEFAULT_MEDIA_STATE, INERT_MEDIA_ACTIONS } from \"./constants\";\n\nimport {\n type MediaActions,\n type MediaContextValue,\n type MediaProviderProps,\n type MediaSession,\n type MediaEntry,\n type MediaState,\n} from \"./types\";\nimport {\n bindFollowers,\n createMediaState,\n findDisplacedAudio,\n mediaStatesEqual,\n mergeMediaSource,\n resolveMediaSession,\n sameElements,\n toggleElement,\n} from \"./utils\";\n\nexport const MediaContext = getOrCreateGlobalContext<MediaContextValue | null>(\n\n \"MediaContext\",\n null,\n);\n\ninterface Binding {\n cleanup: () => void;\n followers: readonly (HTMLMediaElement | null)[];\n transport: HTMLMediaElement;\n}\n\nexport function MediaProvider({ children }: MediaProviderProps) {\n const [store] = useState(() =>\n createStore<MediaState>(DEFAULT_MEDIA_STATE, { freezeSnapshots: false }),\n );\n const sourcesRef = useRef(new Map<string, MediaEntry>());\n const sessionRef = useRef<MediaSession | null>(null);\n const orderRef = useRef(0);\n const bindingRef = useRef<Binding | null>(null);\n\n const actions = useMemo<MediaActions>(() => {\n const unbind = () => {\n bindingRef.current?.cleanup();\n bindingRef.current = null;\n };\n\n const rebind = (session: MediaSession | null) => {\n const transport = session?.transport.element ?? null;\n const followers = (session?.followers ?? []).map(\n (source) => source.element,\n );\n const current = bindingRef.current;\n if (\n current &&\n current.transport === transport &&\n sameElements(current.followers, followers)\n ) {\n return;\n }\n unbind();\n const live = followers.filter(\n (element): element is HTMLMediaElement => element !== null,\n );\n if (!transport || live.length === 0) return;\n bindingRef.current = {\n cleanup: bindFollowers(transport, live),\n followers,\n transport,\n };\n };\n\n const commit = () => {\n const session = resolveMediaSession([...sourcesRef.current.values()]);\n sessionRef.current = session;\n rebind(session);\n const next = createMediaState(session);\n store.publish((prev) => (mediaStatesEqual(prev, next) ? prev : next));\n };\n\n const patch = (id: string, changes: Partial<MediaEntry>) => {\n const current = sourcesRef.current.get(id);\n if (!current) return;\n sourcesRef.current.set(id, { ...current, ...changes });\n commit();\n };\n\n return {\n removeSource: (id) => {\n if (sourcesRef.current.delete(id)) commit();\n },\n setMuted: (muted) => {\n const audible = sessionRef.current?.audible;\n if (!audible) return;\n if (audible.controls?.setMuted) audible.controls.setMuted(muted);\n else if (audible.element) audible.element.muted = muted;\n },\n toggle: () => {\n const transport = sessionRef.current?.transport;\n if (!transport) return;\n if (transport.controls?.toggle) transport.controls.toggle();\n else toggleElement(transport.element);\n },\n toggleLoop: () => {\n const transport = sessionRef.current?.transport;\n if (!transport) return;\n if (transport.controls?.toggleLoop) {\n transport.controls.toggleLoop();\n return;\n }\n const loop = !transport.loop;\n if (transport.element) transport.element.loop = loop;\n patch(transport.id, { loop });\n },\n upsertSource: (input) => {\n const current = sourcesRef.current.get(input.id);\n if (!current) orderRef.current += 1;\n sourcesRef.current.set(\n input.id,\n mergeMediaSource(current, input, orderRef.current),\n );\n commit();\n if (!current) {\n findDisplacedAudio(\n [...sourcesRef.current.values()],\n sessionRef.current,\n input.id,\n ).forEach((entry) => entry.element?.pause());\n }\n },\n };\n }, [store]);\n\n useEffect(\n () => () => {\n bindingRef.current?.cleanup();\n bindingRef.current = null;\n },\n [],\n );\n\n const value = useMemo<MediaContextValue>(\n () => ({ actions, store }),\n [actions, store],\n );\n\n return <MediaContext value={value}>{children}</MediaContext>;\n}\n\nexport function useMediaState(): MediaState {\n const { store } = useRequiredContext(\n MediaContext,\n \"useMediaState\",\n \"MediaProvider\",\n );\n return useStore(store);\n}\n\nexport function useMediaActions(): MediaActions {\n return useRequiredContext(MediaContext, \"useMediaActions\", \"MediaProvider\")\n .actions;\n}\n\nconst NOOP_MEDIA_STORE = createStore<MediaState>(DEFAULT_MEDIA_STATE);\n\nexport function useOptionalMediaState(): MediaState;\nexport function useOptionalMediaState<T>(\n selector: (state: MediaState) => T,\n isEqual?: (a: T, b: T) => boolean,\n): T;\nexport function useOptionalMediaState<T = MediaState>(\n selector?: (state: MediaState) => T,\n isEqual?: (a: T, b: T) => boolean,\n): T {\n const ctx = useContext(MediaContext);\n return useStore(\n ctx?.store ?? NOOP_MEDIA_STORE,\n selector as (state: MediaState) => T,\n isEqual,\n );\n}\n\nexport function useOptionalMediaActions(): MediaActions {\n const ctx = useContext(MediaContext);\n return ctx?.actions ?? INERT_MEDIA_ACTIONS;\n}\n\n\n","\"use client\";\n\nimport { useCallback, useEffect, useId, useMemo, useRef } from \"react\";\nimport { useMediaActions } from \"./context\";\nimport { toggleElement } from \"./utils\";\nimport { type MediaHandle, type MediaOptions } from \"./types\";\n\nexport function useMedia(options: MediaOptions): MediaHandle {\n const generatedId = useId();\n const id = options.id ?? `media-${generatedId}`;\n const { removeSource, upsertSource } = useMediaActions();\n const audioRef = useRef<HTMLAudioElement | null>(null);\n const optionsRef = useRef(options);\n const { src, enabled = true } = options;\n const isEnabled = enabled && Boolean(src);\n\n useEffect(() => {\n optionsRef.current = options;\n });\n\n useEffect(() => {\n if (!isEnabled || !src) return undefined;\n const audio = new Audio();\n audio.preload = \"auto\";\n audio.src = src;\n audioRef.current = audio;\n\n const initial = optionsRef.current;\n audio.loop = Boolean(initial.loop);\n audio.muted = Boolean(initial.muted);\n if (typeof initial.volume === \"number\") {\n audio.volume = Math.min(1, Math.max(0, initial.volume));\n }\n\n upsertSource({\n element: audio,\n follow: initial.follow ?? null,\n id,\n isPlaying: false,\n kind: \"audio\",\n loop: audio.loop,\n });\n\n const syncPlaying = () =>\n upsertSource({ id, isPlaying: !audio.paused && !audio.ended });\n const events = [\"play\", \"playing\", \"pause\", \"ended\"] as const;\n events.forEach((type) => audio.addEventListener(type, syncPlaying));\n\n if (!initial.follow && initial.autoplay !== false) {\n void Promise.resolve(audio.play()).catch(() => {});\n }\n\n return () => {\n events.forEach((type) => audio.removeEventListener(type, syncPlaying));\n audio.pause();\n audio.removeAttribute(\"src\");\n audio.load();\n audioRef.current = null;\n removeSource(id);\n };\n }, [id, isEnabled, removeSource, src, upsertSource]);\n\n const { follow = null, loop, muted, volume } = options;\n useEffect(() => {\n const audio = audioRef.current;\n if (!audio) return;\n if (loop !== undefined && !follow) audio.loop = loop;\n if (muted !== undefined) audio.muted = muted;\n if (volume !== undefined) audio.volume = Math.min(1, Math.max(0, volume));\n upsertSource({ follow, id, ...(follow ? {} : { loop: audio.loop }) });\n }, [follow, id, isEnabled, loop, muted, src, upsertSource, volume]);\n\n const play = useCallback(() => {\n const audio = audioRef.current;\n if (audio) void Promise.resolve(audio.play()).catch(() => {});\n }, []);\n const pause = useCallback(() => audioRef.current?.pause(), []);\n const toggle = useCallback(() => toggleElement(audioRef.current), []);\n\n return useMemo(\n () => ({ id, pause, play, toggle }),\n [id, pause, play, toggle],\n );\n}\n","\"use client\";\n\nimport { useRegistryValue } from \"@/kernel\";\nimport { MEDIA_REGISTRY_KEY, PAGE_MEDIA_ID } from \"./constants\";\nimport { useMedia } from \"./hooks\";\nimport { type MediaPageOptions, type MediaSourceProps } from \"./types\";\n\n/** Declarative form of `useMedia`: mount it anywhere to register an audio source. */\nexport function MediaSource(props: MediaSourceProps) {\n useMedia(props);\n return null;\n}\n\n/**\n * Plays whatever the current page declared with `usePage({ media })`. The\n * registry drops the value when the page goes away, which stops the audio.\n */\nexport function MediaOverlay() {\n const page = useRegistryValue<\"media\", MediaPageOptions>(\n \"media\",\n MEDIA_REGISTRY_KEY,\n );\n useMedia({ ...page, id: PAGE_MEDIA_ID, src: page?.src });\n return null;\n}\n","\"use client\";\n\nimport { useMemo } from \"react\";\nimport { defineModule, type PageModuleApi } from \"@/kernel\";\nimport { MEDIA_REGISTRY_KEY } from \"./constants\";\nimport { MediaContext, MediaProvider, useMediaActions } from \"./context\";\nimport { MediaOverlay } from \"./overlay\";\nimport { selectPageMedia } from \"./utils\";\nimport {\n type MediaPageApi,\n type MediaPageConfig,\n type MediaPageOptions,\n} from \"./types\";\n\nfunction useMediaPage(\n _slice: MediaPageOptions | null,\n page: PageModuleApi,\n): MediaPageApi {\n const actions = useMediaActions();\n return useMemo(\n () => ({\n ...actions,\n set: (media: MediaPageConfig) => page.set({ media }),\n }),\n [actions, page],\n );\n}\n\nexport const mediaModule = defineModule({\n id: \"media\",\n context: MediaContext,\n Provider: MediaProvider,\n Overlay: MediaOverlay,\n registry: {\n cleanupDelayMs: 600,\n keyPolicy: \"singleton\",\n lifecycle: \"immediate\",\n singletonKey: MEDIA_REGISTRY_KEY,\n },\n page: {\n select: (config) => selectPageMedia(config.media),\n entries: (slice: MediaPageOptions) => [\n { key: MEDIA_REGISTRY_KEY, value: slice },\n ],\n use: useMediaPage,\n },\n});\n\ndeclare module \"@omerdlw/base-framework/kernel\" {\n interface CoreModules {\n media: typeof mediaModule;\n }\n interface PageConfig {\n media?: MediaPageConfig;\n }\n}\n"]}
@@ -16,5 +16,5 @@ export declare const MODAL_BREAKPOINTS: Readonly<{
16
16
  export declare const SMOOTH_SCROLL_LOCK_EVENT = "modal:smooth-scroll-lock";
17
17
  export declare const FOCUSABLE_SELECTOR = "button:not([disabled]), [href], input:not([disabled]), select:not([disabled]), textarea:not([disabled]), [contenteditable=\"true\"], [tabindex]:not([tabindex=\"-1\"])";
18
18
  export declare const HEIGHT_CONSTRAINT_PATTERN: RegExp;
19
- export declare const modalTheme: import("../theme").ThemeSpec<ModalThemeSlot>;
19
+ export declare const modalTheme: import("@/theme").ThemeSpec<ModalThemeSlot>;
20
20
  //# sourceMappingURL=constants.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../../../src/modules/modal/constants.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,KAAK,cAAc,EAAE,MAAM,SAAS,CAAC;AAE9C,eAAO,MAAM,eAAe;;;;;;EAMjB,CAAC;AAEZ,eAAO,MAAM,YAAY;;;EAGd,CAAC;AAEZ,eAAO,MAAM,iBAAiB;;EAEnB,CAAC;AAEZ,eAAO,MAAM,wBAAwB,6BAA6B,CAAC;AAEnE,eAAO,MAAM,kBAAkB,2KACuI,CAAC;AAEvK,eAAO,MAAM,yBAAyB,QAAmC,CAAC;AAE1E,eAAO,MAAM,UAAU,8CAA2C,CAAC"}
1
+ {"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../../../src/modules/modal/constants.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,KAAK,cAAc,EAAE,MAAM,SAAS,CAAC;AAE9C,eAAO,MAAM,eAAe;;;;;;EAMjB,CAAC;AAEZ,eAAO,MAAM,YAAY;;;EAGd,CAAC;AAEZ,eAAO,MAAM,iBAAiB;;EAEnB,CAAC;AAEZ,eAAO,MAAM,wBAAwB,6BAA6B,CAAC;AAEnE,eAAO,MAAM,kBAAkB,2KACuI,CAAC;AAEvK,eAAO,MAAM,yBAAyB,QAAmC,CAAC;AAE1E,eAAO,MAAM,UAAU,6CAA2C,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../../../src/modules/modal/context.tsx"],"names":[],"mappings":"AAIA,OAAO,EAGL,KAAK,gBAAgB,EACtB,MAAM,UAAU,CAAC;AAClB,OAAO,EAAe,KAAK,aAAa,EAAE,MAAM,SAAS,CAAC;AAE1D,OAAO,EACL,KAAK,YAAY,EACjB,KAAK,cAAc,EAEnB,KAAK,gBAAgB,EAErB,KAAK,UAAU,EAGf,KAAK,eAAe,EACpB,KAAK,kBAAkB,EACvB,KAAK,UAAU,EAChB,MAAM,SAAS,CAAC;AAKjB,MAAM,WAAW,iBAAiB;IAChC,OAAO,EAAE,YAAY,CAAC;IACtB,KAAK,EAAE,aAAa,CAAC,UAAU,CAAC,CAAC;CAClC;AAGD,eAAO,MAAM,YAAY,mDAGxB,CAAC;AAEF,wBAAgB,oBAAoB,CAClC,MAAM,EAAE,eAAe,GAAG,IAAI,GAAG,SAAS,EAC1C,OAAO,CAAC,EAAE,gBAAgB,GAAG;IAAE,OAAO,CAAC,EAAE,OAAO,CAAA;CAAE,GACjD,IAAI,CAEN;AAED,wBAAgB,uBAAuB,IAAI;IACzC,GAAG,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,cAAc,GAAG,SAAS,CAAC;CACnD,CAGA;AAOD,wBAAgB,aAAa,CAAC,EAC5B,QAAQ,EACR,aAAa,EAAE,aAAoB,GACpC,EAAE,kBAAkB,+BAuHpB;AAED,wBAAgB,eAAe,IAAI,YAAY,CAG9C;AAED,wBAAgB,aAAa,IAAI,UAAU,CAO1C;AAED,wBAAgB,QAAQ,IAAI,UAAU,GAAG,YAAY,CAAC;AACtD,wBAAgB,QAAQ,CAAC,UAAU,EAAE,UAAU,GAAG,gBAAgB,CAAC"}
1
+ {"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../../../src/modules/modal/context.tsx"],"names":[],"mappings":"AAIA,OAAO,EAIL,KAAK,gBAAgB,EACtB,MAAM,UAAU,CAAC;AAElB,OAAO,EAAe,KAAK,aAAa,EAAE,MAAM,SAAS,CAAC;AAE1D,OAAO,EACL,KAAK,YAAY,EACjB,KAAK,cAAc,EAEnB,KAAK,gBAAgB,EAErB,KAAK,UAAU,EAGf,KAAK,eAAe,EACpB,KAAK,kBAAkB,EACvB,KAAK,UAAU,EAChB,MAAM,SAAS,CAAC;AAKjB,MAAM,WAAW,iBAAiB;IAChC,OAAO,EAAE,YAAY,CAAC;IACtB,KAAK,EAAE,aAAa,CAAC,UAAU,CAAC,CAAC;CAClC;AAED,eAAO,MAAM,YAAY,mDAIxB,CAAC;AAEF,wBAAgB,oBAAoB,CAClC,MAAM,EAAE,eAAe,GAAG,IAAI,GAAG,SAAS,EAC1C,OAAO,CAAC,EAAE,gBAAgB,GAAG;IAAE,OAAO,CAAC,EAAE,OAAO,CAAA;CAAE,GACjD,IAAI,CAEN;AAED,wBAAgB,uBAAuB,IAAI;IACzC,GAAG,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,cAAc,GAAG,SAAS,CAAC;CACnD,CAGA;AAOD,wBAAgB,aAAa,CAAC,EAC5B,QAAQ,EACR,aAAa,EAAE,aAAoB,GACpC,EAAE,kBAAkB,+BAuHpB;AAED,wBAAgB,eAAe,IAAI,YAAY,CAG9C;AAED,wBAAgB,aAAa,IAAI,UAAU,CAO1C;AAED,wBAAgB,QAAQ,IAAI,UAAU,GAAG,YAAY,CAAC;AACtD,wBAAgB,QAAQ,CAAC,UAAU,EAAE,UAAU,GAAG,gBAAgB,CAAC"}
@@ -21,7 +21,7 @@ export declare function useModalLayerModel({ closeModal, entry, isMobileViewport
21
21
  baseZIndex: 140;
22
22
  };
23
23
  export declare function useModalContainerModel(): {
24
- theme: import("../theme").ResolvedTheme<import("./types").ModalThemeSlot>;
24
+ theme: import("@/theme").ResolvedTheme<import("./types").ModalThemeSlot>;
25
25
  };
26
26
  export declare function useModalModel(): {
27
27
  modalStack: ModalEntry[];
@@ -36,6 +36,6 @@ export declare function useModalModel(): {
36
36
  isMobileViewport: boolean;
37
37
  isTopExitSettling: boolean;
38
38
  setIsTopExitSettling: import("react").Dispatch<import("react").SetStateAction<boolean>>;
39
- theme: import("../theme").ResolvedTheme<import("./types").ModalThemeSlot>;
39
+ theme: import("@/theme").ResolvedTheme<import("./types").ModalThemeSlot>;
40
40
  };
41
41
  //# sourceMappingURL=hooks.d.ts.map