{"version":3,"sources":["../../src/core/utils.ts","../../src/core/registry.ts","../../src/core/search.ts","../../src/core/keywords.ts","../../src/core/access-control.ts","../../src/core/frecency.ts","../../src/core/grouping.ts","../../src/core/context.ts","../../src/core/i18n.ts","../../src/core/search-history.ts","../../src/react/context.tsx","../../src/react/use-command-palette.ts","../../src/react/use-command-register.ts","../../src/react/use-frecency.ts","../../src/react/use-command-context.ts","../../src/react/use-search-history.ts"],"names":["items","createContext","useRef","useMemo","jsx","useContext","useState","useSyncExternalStore","useCallback","useEffect"],"mappings":"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","file":"index.cjs","sourcesContent":["/**\n * Schedule a microtask-batched callback. Multiple calls within the same\n * microtask only execute the callback once.\n */\nexport function createBatchScheduler(): (fn: () => void) => void {\n  let scheduled = false\n\n  return (fn: () => void) => {\n    if (scheduled) return\n    scheduled = true\n    queueMicrotask(() => {\n      scheduled = false\n      fn()\n    })\n  }\n}\n\n/**\n * Convert a path segment to a readable label.\n * Handles kebab-case, snake_case, camelCase, PascalCase.\n *\n * Examples:\n *  \"user-settings\" -> \"User Settings\"\n *  \"phone_numbers\" -> \"Phone Numbers\"\n *  \"phoneNumbers\"  -> \"Phone Numbers\"\n *  \"BillingOverview\" -> \"Billing Overview\"\n */\nexport function pathSegmentToLabel(segment: string): string {\n  return (\n    segment\n      // Insert space before uppercase letters in camelCase/PascalCase\n      .replace(/([a-z0-9])([A-Z])/g, '$1 $2')\n      // Replace hyphens and underscores with spaces\n      .replace(/[-_]/g, ' ')\n      // Capitalize first letter of each word\n      .replace(/\\b\\w/g, (c) => c.toUpperCase())\n      .trim()\n  )\n}\n\n/**\n * Convert a full path to a readable label.\n * Uses the last meaningful segment.\n *\n * \"/billing/overview\" -> \"Billing Overview\"\n * \"/settings\" -> \"Settings\"\n * \"/\" -> \"Home\"\n */\nexport function pathToLabel(path: string): string {\n  if (path === '/' || path === '') return 'Home'\n\n  const segments = path.split('/').filter(Boolean)\n  // Filter out dynamic segments like :id, [id], etc.\n  const meaningful = segments.filter((s) => !s.startsWith(':') && !s.startsWith('['))\n  const last = meaningful[meaningful.length - 1]\n\n  return last ? pathSegmentToLabel(last) : 'Home'\n}\n\n/**\n * Convert a full path to a group name.\n * Uses the first meaningful segment.\n *\n * \"/billing/overview\" -> \"Billing\"\n * \"/settings/team\" -> \"Settings\"\n */\nexport function pathToGroup(path: string): string | undefined {\n  const segments = path.split('/').filter(Boolean)\n  const first = segments[0]\n\n  if (!first || segments.length <= 1) return undefined\n  return pathSegmentToLabel(first)\n}\n\n/**\n * Generate a stable ID from a route path.\n * \"/billing/overview\" -> \"billing-overview\"\n */\nexport function pathToId(path: string): string {\n  return path\n    .replace(/^\\//, '')\n    .replace(/\\/$/, '')\n    .replace(/\\//g, '--')\n    .replace(/[^a-zA-Z0-9-]/g, '')\n    .toLowerCase() || 'home'\n}\n","import type { CommandItem, CommandRegistry } from './types'\nimport { createBatchScheduler } from './utils'\n\n/**\n * Create a new command registry — the central store for all commands.\n *\n * The registry implements a pub/sub pattern compatible with React's\n * useSyncExternalStore. Commands can be registered, updated, and removed,\n * and subscribers are notified of changes via batched microtask updates.\n */\nexport function createRegistry(): CommandRegistry {\n  const commands = new Map<string, CommandItem>()\n  const listeners = new Set<() => void>()\n  const schedule = createBatchScheduler()\n\n  // Cached snapshot — only recalculated when commands change\n  let snapshot: CommandItem[] = []\n  let snapshotDirty = true\n\n  function notify(): void {\n    schedule(() => {\n      for (const listener of listeners) {\n        listener()\n      }\n    })\n  }\n\n  function invalidateSnapshot(): void {\n    snapshotDirty = true\n    notify()\n  }\n\n  function register(command: CommandItem): () => void {\n    commands.set(command.id, { ...command })\n    invalidateSnapshot()\n    return () => unregister(command.id)\n  }\n\n  function registerMany(items: CommandItem[]): () => void {\n    for (const item of items) {\n      commands.set(item.id, { ...item })\n    }\n    invalidateSnapshot()\n    return () => {\n      for (const item of items) {\n        commands.delete(item.id)\n      }\n      invalidateSnapshot()\n    }\n  }\n\n  function update(id: string, partial: Partial<CommandItem>): void {\n    const existing = commands.get(id)\n    if (!existing) return\n    commands.set(id, { ...existing, ...partial })\n    invalidateSnapshot()\n  }\n\n  function unregister(id: string): void {\n    if (commands.delete(id)) {\n      invalidateSnapshot()\n    }\n  }\n\n  function getAll(): CommandItem[] {\n    return Array.from(commands.values())\n  }\n\n  function getById(id: string): CommandItem | undefined {\n    return commands.get(id)\n  }\n\n  function getByGroup(groupId: string): CommandItem[] {\n    return getAll().filter((cmd) => cmd.group === groupId)\n  }\n\n  function subscribe(listener: () => void): () => void {\n    listeners.add(listener)\n    return () => {\n      listeners.delete(listener)\n    }\n  }\n\n  function getSnapshot(): CommandItem[] {\n    if (snapshotDirty) {\n      snapshot = Array.from(commands.values())\n      snapshotDirty = false\n    }\n    return snapshot\n  }\n\n  return {\n    register,\n    registerMany,\n    update,\n    unregister,\n    getAll,\n    getById,\n    getByGroup,\n    subscribe,\n    getSnapshot,\n  }\n}\n","import type { CommandItem, SearchEngine, ScoredItem } from './types'\n\n/**\n * Built-in lightweight fuzzy search engine.\n * Searches label, description, and keywords fields.\n * No external dependencies. Target: < 1KB gzipped.\n *\n * Scoring bonuses:\n * - Exact prefix match (highest)\n * - Word boundary match\n * - Consecutive character matches\n * - Case-sensitive exact match\n */\nexport function createFuzzySearch(): SearchEngine {\n  return {\n    search(query: string, items: CommandItem[]): ScoredItem[] {\n      if (!query || query.trim() === '') {\n        // Empty query returns all items with max score, sorted by priority\n        return items\n          .filter((item) => !item.hidden)\n          .map((item) => ({ item, score: 1 }))\n          .sort((a, b) => (b.item.priority ?? 0) - (a.item.priority ?? 0))\n      }\n\n      const normalizedQuery = query.toLowerCase().trim()\n      const results: ScoredItem[] = []\n\n      for (const item of items) {\n        if (item.hidden) continue\n\n        const score = scoreItem(normalizedQuery, item)\n        if (score > 0) {\n          results.push({ item, score })\n        }\n      }\n\n      // Sort by score descending, then by priority descending\n      results.sort((a, b) => {\n        const scoreDiff = b.score - a.score\n        if (Math.abs(scoreDiff) > 0.001) return scoreDiff\n        return (b.item.priority ?? 0) - (a.item.priority ?? 0)\n      })\n\n      return results\n    },\n  }\n}\n\n/**\n * Score a single item against a query.\n * Returns 0 if no match, up to 1 for perfect match.\n *\n * Scoring weights:\n * - Label:            1.0x  (exact label match is highest signal)\n * - Original keywords: 0.85x (user explicitly tagged these)\n * - Description:      0.7x\n * - Synonym keywords:  0.55x (injected by keyword engine, lower confidence)\n */\nfunction scoreItem(query: string, item: CommandItem): number {\n  let bestScore = 0\n\n  // Score against label (highest weight)\n  bestScore = Math.max(bestScore, fuzzyScore(query, item.label.toLowerCase()) * 1.0)\n\n  // Score against description (medium weight)\n  if (item.description) {\n    bestScore = Math.max(bestScore, fuzzyScore(query, item.description.toLowerCase()) * 0.7)\n  }\n\n  // Score against original keywords (medium-high weight)\n  if (item.keywords) {\n    for (const kw of item.keywords) {\n      bestScore = Math.max(bestScore, fuzzyScore(query, kw.toLowerCase()) * 0.85)\n    }\n  }\n\n  // Score against synonym-expanded keywords (lower weight)\n  const synonymKeywords = (item.meta?._synonymKeywords as string[] | undefined)\n  if (synonymKeywords) {\n    for (const kw of synonymKeywords) {\n      bestScore = Math.max(bestScore, fuzzyScore(query, kw.toLowerCase()) * 0.55)\n    }\n  }\n\n  const finalScore = Math.min(bestScore, 1)\n\n  // Reject very low-confidence matches\n  if (finalScore < 0.15) return 0\n\n  return finalScore\n}\n\n/**\n * Fuzzy match a query against a target string.\n * Returns a score between 0 and 1.\n *\n * Scoring tiers:\n * - Exact match: 1.0\n * - Prefix match: 0.95\n * - Substring match: 0.8\n * - Word initials: 0.7\n * - Fuzzy (consecutive chars): up to 0.6\n * - Fuzzy (scattered chars): heavily penalized, often rejected\n */\nfunction fuzzyScore(query: string, target: string): number {\n  if (query === target) return 1 // Exact match\n  if (target.startsWith(query)) return 0.95 // Prefix match\n  if (target.includes(query)) return 0.8 // Substring match\n\n  // Check word boundary matches\n  const words = target.split(/[\\s\\-_]+/)\n  const wordInitials = words.map((w) => w[0]).join('')\n  if (wordInitials.includes(query)) return 0.7 // Initials match (e.g., \"bs\" matches \"Billing Settings\")\n\n  // Fuzzy character-by-character matching\n  let queryIdx = 0\n  let currentConsecutive = 0\n  let maxConsecutive = 0\n  let totalBonus = 0\n  let matchCount = 0\n  let totalGaps = 0\n  let lastMatchIdx = -1\n\n  for (let i = 0; i < target.length && queryIdx < query.length; i++) {\n    if (target[i] === query[queryIdx]) {\n      matchCount++\n      queryIdx++\n\n      // Track gaps between matches\n      if (lastMatchIdx >= 0) {\n        totalGaps += i - lastMatchIdx - 1\n      }\n      lastMatchIdx = i\n\n      // Track consecutive matches\n      currentConsecutive++\n      if (currentConsecutive > maxConsecutive) {\n        maxConsecutive = currentConsecutive\n      }\n      totalBonus += currentConsecutive * 0.1\n\n      // Bonus for word boundary match\n      if (i === 0 || /[\\s\\-_]/.test(target[i - 1])) {\n        totalBonus += 0.15\n      }\n    } else {\n      currentConsecutive = 0\n    }\n  }\n\n  // All query characters must match\n  if (queryIdx < query.length) return 0\n\n  // Contiguity ratio: how consecutive are the matches?\n  const contiguityRatio = matchCount > 0 ? maxConsecutive / matchCount : 0\n\n  // Aggressive penalty for scattered matches (contiguity < 50%)\n  // If most chars are scattered, the match is likely a false positive\n  const contiguityMultiplier =\n    contiguityRatio < 0.5\n      ? contiguityRatio * 0.5 // Very scattered: 0 to 0.25x\n      : 0.4 + 0.6 * contiguityRatio // Mostly consecutive: 0.7 to 1.0x\n\n  // Average gap penalty\n  const avgGap = matchCount > 1 ? totalGaps / (matchCount - 1) : 0\n  const gapPenalty = avgGap > 3 ? 0.15 : 0\n\n  // Base score from match ratio + bonuses\n  const matchRatio = matchCount / target.length\n  const rawScore = 0.2 + matchRatio * 0.3 + Math.min(totalBonus, 0.4)\n  const score = (rawScore - gapPenalty) * contiguityMultiplier\n\n  return Math.min(Math.max(score, 0), 0.6) // Cap fuzzy matches well below substring matches\n}\n","import type { CommandItem, SynonymMap } from './types'\n\n/**\n * Create a keyword engine for synonym expansion and user alias management.\n *\n * The engine enriches command items with additional searchable keywords\n * based on a synonym dictionary and optional user-defined aliases.\n */\nexport function createKeywordEngine(\n  synonyms: SynonymMap = {},\n  userAliases: Map<string, string[]> = new Map(),\n) {\n  return {\n    /**\n     * Expand a search query using the synonym dictionary.\n     * Returns the original query plus any synonym matches.\n     *\n     * e.g., query \"money\" with synonyms { billing: [\"money\", \"payment\"] }\n     * returns [\"money\", \"billing\"]\n     */\n    expandQuery(query: string): string[] {\n      const q = query.toLowerCase().trim()\n      if (!q) return []\n\n      const expanded = new Set<string>([q])\n\n      for (const [key, values] of Object.entries(synonyms)) {\n        const lowerValues = values.map((v) => v.toLowerCase())\n        // If query matches a synonym value, add the key\n        if (lowerValues.includes(q)) {\n          expanded.add(key.toLowerCase())\n        }\n        // If query matches a key, add all synonym values\n        if (key.toLowerCase() === q) {\n          for (const v of lowerValues) {\n            expanded.add(v)\n          }\n        }\n      }\n\n      return Array.from(expanded)\n    },\n\n    /**\n     * Enrich a command item's keywords with synonyms and user aliases.\n     * Returns a new CommandItem with original keywords preserved and\n     * synonym-expanded keywords stored separately in meta._synonymKeywords.\n     * This lets the search engine score original keywords higher.\n     */\n    enrichItem(item: CommandItem): CommandItem {\n      const originalKeywords = new Set<string>(item.keywords ?? [])\n      const synonymKeywords = new Set<string>()\n\n      // Add synonyms for existing keywords\n      for (const kw of item.keywords ?? []) {\n        const kwLower = kw.toLowerCase()\n        if (synonyms[kwLower]) {\n          for (const syn of synonyms[kwLower]) {\n            if (!originalKeywords.has(syn)) synonymKeywords.add(syn)\n          }\n        }\n        for (const [key, values] of Object.entries(synonyms)) {\n          if (values.map((v) => v.toLowerCase()).includes(kwLower)) {\n            if (!originalKeywords.has(key)) synonymKeywords.add(key)\n          }\n        }\n      }\n\n      // Add synonyms for the label\n      const labelLower = item.label.toLowerCase()\n      for (const [key, values] of Object.entries(synonyms)) {\n        if (key.toLowerCase() === labelLower) {\n          for (const v of values) {\n            if (!originalKeywords.has(v)) synonymKeywords.add(v)\n          }\n        }\n        if (values.map((v) => v.toLowerCase()).includes(labelLower)) {\n          if (!originalKeywords.has(key)) synonymKeywords.add(key)\n        }\n      }\n\n      // Add user aliases as original keywords (user explicitly added these)\n      const aliases = userAliases.get(item.id)\n      if (aliases) {\n        for (const alias of aliases) {\n          originalKeywords.add(alias)\n        }\n      }\n\n      return {\n        ...item,\n        keywords: Array.from(originalKeywords),\n        meta: {\n          ...item.meta,\n          ...(synonymKeywords.size > 0\n            ? { _synonymKeywords: Array.from(synonymKeywords) }\n            : {}),\n        },\n      }\n    },\n\n    /**\n     * Enrich all items in a list.\n     */\n    enrichAll(items: CommandItem[]): CommandItem[] {\n      return items.map((item) => this.enrichItem(item))\n    },\n\n    /**\n     * Add a user alias for a command.\n     */\n    addAlias(commandId: string, alias: string): void {\n      const existing = userAliases.get(commandId) ?? []\n      if (!existing.includes(alias)) {\n        userAliases.set(commandId, [...existing, alias])\n      }\n    },\n\n    /**\n     * Remove a user alias for a command.\n     */\n    removeAlias(commandId: string, alias: string): void {\n      const existing = userAliases.get(commandId) ?? []\n      userAliases.set(\n        commandId,\n        existing.filter((a) => a !== alias),\n      )\n    },\n\n    /**\n     * Get all user aliases.\n     */\n    getAliases(): Map<string, string[]> {\n      return new Map(userAliases)\n    },\n\n    /**\n     * Set the synonym dictionary.\n     */\n    setSynonyms(newSynonyms: SynonymMap): void {\n      Object.keys(synonyms).forEach((k) => delete synonyms[k])\n      Object.assign(synonyms, newSynonyms)\n    },\n  }\n}\n","import type { AccessCheckMode, AccessControlProvider, CommandItem } from './types'\n\n/**\n * Create an access control filter that removes commands the user\n * doesn't have permission to see.\n *\n * This is a UI filter, not a security boundary. Always enforce\n * permissions server-side.\n *\n * @param provider - The permission checking backend\n * @param mode - 'any' = user needs any listed permission, 'all' = needs all (default: 'any')\n */\nexport function createAccessFilter(\n  provider: AccessControlProvider,\n  mode: AccessCheckMode = 'any',\n): (items: CommandItem[]) => CommandItem[] {\n  return (items: CommandItem[]) => {\n    return items.filter((item) => {\n      // No permissions required = open to all\n      if (!item.permissions || item.permissions.length === 0) {\n        return true\n      }\n\n      if (mode === 'all') {\n        return provider.hasAllPermissions(item.permissions)\n      }\n\n      return provider.hasAnyPermission(item.permissions)\n    })\n  }\n}\n\n/**\n * Create a simple access control provider from a set of permissions.\n * Useful for static permission sets.\n */\nexport function createSimpleAccessProvider(\n  userPermissions: string[] | Set<string>,\n): AccessControlProvider {\n  const perms = userPermissions instanceof Set ? userPermissions : new Set(userPermissions)\n\n  return {\n    hasPermission(permission: string): boolean {\n      return perms.has(permission)\n    },\n\n    hasAnyPermission(permissions: string[]): boolean {\n      return permissions.some((p) => perms.has(p))\n    },\n\n    hasAllPermissions(permissions: string[]): boolean {\n      return permissions.every((p) => perms.has(p))\n    },\n  }\n}\n","import type { FrecencyEntry, FrecencyOptions, FrecencyStorage, ScoredItem } from './types'\n\nconst DEFAULT_HALF_LIFE = 7 // days\nconst DEFAULT_MAX_AGE = 30 // days\nconst MS_PER_DAY = 86_400_000\n\n/**\n * Create a frecency engine that tracks usage patterns and\n * ranks items by frequency + recency using exponential decay.\n *\n * Algorithm:\n *   score = count * 2^(-timeSinceLastUse / halfLife)\n *\n * This means:\n * - An item used 10 times yesterday ranks higher than one used 100 times a month ago\n * - The half-life (default 7 days) controls how quickly old usage decays\n */\nexport function createFrecencyEngine(options: FrecencyOptions = {}) {\n  const halfLife = options.halfLife ?? DEFAULT_HALF_LIFE\n  const maxAge = options.maxAge ?? DEFAULT_MAX_AGE\n  const storage = options.storage ?? createInMemoryStorage()\n\n  /**\n   * Record that a command was used.\n   */\n  function recordUsage(commandId: string): void {\n    const now = Date.now()\n    const existing = storage.get(commandId)\n\n    const entry: FrecencyEntry = {\n      id: commandId,\n      count: (existing?.count ?? 0) + 1,\n      lastUsed: now,\n      halfLifeScore: 0, // Will be calculated\n    }\n\n    entry.halfLifeScore = calculateScore(entry, now)\n    storage.set(commandId, entry)\n  }\n\n  /**\n   * Calculate the decayed score for an entry at a given time.\n   */\n  function calculateScore(entry: FrecencyEntry, now: number): number {\n    const daysSinceUse = (now - entry.lastUsed) / MS_PER_DAY\n    return entry.count * Math.pow(2, -daysSinceUse / halfLife)\n  }\n\n  /**\n   * Get the frecency score for a command.\n   * Returns 0 if never used.\n   */\n  function getScore(commandId: string): number {\n    const entry = storage.get(commandId)\n    if (!entry) return 0\n    return calculateScore(entry, Date.now())\n  }\n\n  /**\n   * Rank scored search results by blending search score with frecency.\n   *\n   * @param items - Search results with scores\n   * @param frecencyWeight - How much frecency affects ranking (0-1, default 0.3)\n   * @returns Re-ranked items\n   */\n  function rank(items: ScoredItem[], frecencyWeight = 0.3): ScoredItem[] {\n    const now = Date.now()\n\n    // Get max frecency score for normalization\n    let maxFrecency = 0\n    const frecencyScores = new Map<string, number>()\n\n    for (const { item } of items) {\n      const entry = storage.get(item.id)\n      if (entry) {\n        const score = calculateScore(entry, now)\n        frecencyScores.set(item.id, score)\n        maxFrecency = Math.max(maxFrecency, score)\n      }\n    }\n\n    // Blend search score with normalized frecency\n    return items\n      .map(({ item, score }) => {\n        const rawFrecency = frecencyScores.get(item.id) ?? 0\n        const normalizedFrecency = maxFrecency > 0 ? rawFrecency / maxFrecency : 0\n\n        const blendedScore =\n          score * (1 - frecencyWeight) + normalizedFrecency * frecencyWeight\n\n        return { item, score: blendedScore }\n      })\n      .sort((a, b) => b.score - a.score)\n  }\n\n  /**\n   * Get the most recently used command IDs, sorted by last use (newest first).\n   */\n  function getRecent(count = 5): string[] {\n    return storage\n      .getAll()\n      .filter((e) => e.count > 0)\n      .sort((a, b) => b.lastUsed - a.lastUsed)\n      .slice(0, count)\n      .map((e) => e.id)\n  }\n\n  /**\n   * Clean up entries older than maxAge.\n   */\n  function cleanup(): void {\n    const now = Date.now()\n    const cutoff = now - maxAge * MS_PER_DAY\n\n    for (const entry of storage.getAll()) {\n      if (entry.lastUsed < cutoff) {\n        storage.set(entry.id, { ...entry, count: 0, halfLifeScore: 0 })\n      }\n    }\n  }\n\n  /**\n   * Clear all frecency data.\n   */\n  function clear(): void {\n    storage.clear()\n  }\n\n  return {\n    recordUsage,\n    getScore,\n    getRecent,\n    rank,\n    cleanup,\n    clear,\n  }\n}\n\n/**\n * In-memory frecency storage (for testing or SSR).\n */\nexport function createInMemoryStorage(): FrecencyStorage {\n  const store = new Map<string, FrecencyEntry>()\n\n  return {\n    get(key: string): FrecencyEntry | null {\n      return store.get(key) ?? null\n    },\n    set(key: string, entry: FrecencyEntry): void {\n      store.set(key, entry)\n    },\n    getAll(): FrecencyEntry[] {\n      return Array.from(store.values())\n    },\n    clear(): void {\n      store.clear()\n    },\n  }\n}\n","import type { CommandGroup, CommandItem, ScoredItem } from './types'\n\n/**\n * Create a group manager that tracks command groups and their ordering.\n */\nexport function createGroupManager(initialGroups: CommandGroup[] = []) {\n  const groups = new Map<string, CommandGroup>()\n\n  for (const group of initialGroups) {\n    groups.set(group.id, group)\n  }\n\n  return {\n    /** Add or update a group definition */\n    addGroup(group: CommandGroup): void {\n      groups.set(group.id, group)\n    },\n\n    /** Remove a group */\n    removeGroup(id: string): void {\n      groups.delete(id)\n    },\n\n    /** Get a group by ID */\n    getGroup(id: string): CommandGroup | undefined {\n      return groups.get(id)\n    },\n\n    /** Get all defined groups sorted by priority (higher first) */\n    getAllGroups(): CommandGroup[] {\n      return Array.from(groups.values()).sort(\n        (a, b) => (b.priority ?? 0) - (a.priority ?? 0),\n      )\n    },\n\n    /**\n     * Group scored items by their group field.\n     * When query is empty: groups ordered by priority (higher first).\n     * When query is non-empty: groups ordered by best item score (relevance).\n     * Items without a group go into an \"Other\" bucket at the end.\n     */\n    groupResults(items: ScoredItem[], query?: string): GroupedResults {\n      const grouped = new Map<string, ScoredItem[]>()\n\n      for (const scored of items) {\n        const groupId = scored.item.group ?? '__ungrouped__'\n        if (!grouped.has(groupId)) {\n          grouped.set(groupId, [])\n        }\n        grouped.get(groupId)!.push(scored)\n      }\n\n      // Sort items within each group by score descending\n      for (const items of grouped.values()) {\n        items.sort((a, b) => b.score - a.score)\n      }\n\n      const isSearching = query !== undefined && query.trim() !== ''\n\n      // Collect all group entries\n      const allEntries: GroupedResult[] = []\n      const definedGroups = this.getAllGroups()\n      const usedGroupIds = new Set<string>()\n\n      for (const group of definedGroups) {\n        const groupItems = grouped.get(group.id)\n        if (groupItems && groupItems.length > 0) {\n          allEntries.push({ group, items: groupItems })\n          usedGroupIds.add(group.id)\n        }\n      }\n\n      // Add any groups that weren't pre-defined (auto-discovered from items)\n      for (const [groupId, groupItems] of grouped) {\n        if (groupId === '__ungrouped__' || usedGroupIds.has(groupId)) continue\n        allEntries.push({\n          group: { id: groupId, label: groupId },\n          items: groupItems,\n        })\n      }\n\n      // When searching, sort groups by best item score (relevance-first)\n      if (isSearching) {\n        allEntries.sort((a, b) => b.items[0].score - a.items[0].score)\n      }\n\n      // Add ungrouped items last\n      const ungrouped = grouped.get('__ungrouped__')\n      if (ungrouped && ungrouped.length > 0) {\n        allEntries.push({\n          group: { id: '__ungrouped__', label: 'Other' },\n          items: ungrouped,\n        })\n      }\n\n      return allEntries\n    },\n\n    /**\n     * Extract unique groups from a list of commands.\n     * Returns only groups that have at least one command.\n     */\n    extractGroups(commands: CommandItem[]): CommandGroup[] {\n      const seen = new Set<string>()\n      const result: CommandGroup[] = []\n\n      for (const cmd of commands) {\n        if (cmd.group && !seen.has(cmd.group)) {\n          seen.add(cmd.group)\n          const defined = groups.get(cmd.group)\n          result.push(defined ?? { id: cmd.group, label: cmd.group })\n        }\n      }\n\n      return result.sort((a, b) => (b.priority ?? 0) - (a.priority ?? 0))\n    },\n  }\n}\n\n/** A group with its scored items */\nexport interface GroupedResult {\n  group: CommandGroup\n  items: ScoredItem[]\n}\n\n/** Array of grouped results */\nexport type GroupedResults = GroupedResult[]\n","import type { CommandContext, ScoredItem } from './types'\n\n/**\n * Create a context engine that boosts commands matching the current app context.\n *\n * Commands with a `scope` field (e.g., ['/billing', '/billing/*']) get a score\n * boost when the current context path matches.\n *\n * @param boostWeight - How much to boost in-scope commands (0-1, default: 0.2)\n */\nexport function createContextEngine(boostWeight = 0.2) {\n  return {\n    /**\n     * Boost scores for items whose scope matches the current context.\n     * Items without a scope are unaffected.\n     */\n    boost(items: ScoredItem[], context: CommandContext): ScoredItem[] {\n      if (!context.path && (!context.tags || context.tags.length === 0)) {\n        return items\n      }\n\n      return items.map(({ item, score }) => {\n        if (!item.scope || item.scope.length === 0) {\n          return { item, score }\n        }\n\n        const matches = matchesContext(item.scope, context)\n        const boostedScore = matches\n          ? Math.min(score + boostWeight, 1)\n          : score\n\n        return { item, score: boostedScore }\n      })\n    },\n  }\n}\n\n/**\n * Check if any scope pattern matches the given context.\n */\nfunction matchesContext(scope: string[], context: CommandContext): boolean {\n  if (context.path) {\n    for (const pattern of scope) {\n      if (matchPath(pattern, context.path)) return true\n    }\n  }\n\n  if (context.tags && context.tags.length > 0) {\n    for (const pattern of scope) {\n      if (context.tags.includes(pattern)) return true\n    }\n  }\n\n  return false\n}\n\n/**\n * Match a scope pattern against a path.\n * Supports:\n * - Exact match: '/billing' matches '/billing'\n * - Prefix match: '/billing' matches '/billing/overview'\n * - Glob: '/billing/*' matches '/billing/overview' but not '/billing'\n */\nfunction matchPath(pattern: string, path: string): boolean {\n  // Glob pattern\n  if (pattern.endsWith('/*')) {\n    const prefix = pattern.slice(0, -2)\n    return path.startsWith(prefix + '/') && path !== prefix\n  }\n\n  // Exact or prefix match\n  return path === pattern || path.startsWith(pattern + '/')\n}\n","import type { TranslationFn } from './types'\n\n/** Default English UI strings */\nconst DEFAULT_STRINGS: Record<string, string> = {\n  'palette.placeholder': 'Type a command or search...',\n  'palette.empty': 'No results found.',\n  'palette.loading': 'Loading...',\n  'group.recent': 'Recent',\n  'group.other': 'Other',\n  'search.history': 'Recent Searches',\n}\n\n/**\n * Create the default English translation function.\n * Returns the English string for known keys, or the key itself as fallback.\n */\nexport function createDefaultTranslation(): TranslationFn {\n  return (key: string) => DEFAULT_STRINGS[key] ?? key\n}\n\n/**\n * Get the list of all known translation keys.\n * Useful for consumers building custom translation dictionaries.\n */\nexport function getTranslationKeys(): string[] {\n  return Object.keys(DEFAULT_STRINGS)\n}\n","import type { SearchHistoryConfig, SearchHistoryEntry } from './types'\n\nconst DEFAULT_MAX_ENTRIES = 20\nconst DEFAULT_STORAGE_KEY = 'cmdk-search-history'\nconst DEFAULT_MIN_QUERY_LENGTH = 2\n\n/**\n * Create a search history tracker that records search queries.\n * Separate from frecency (which tracks command usage).\n *\n * Uses localStorage for persistence (same pattern as frecency-storage.ts).\n */\nexport function createSearchHistory(config: SearchHistoryConfig = {}) {\n  const maxEntries = config.maxEntries ?? DEFAULT_MAX_ENTRIES\n  const storageKey = config.storageKey ?? DEFAULT_STORAGE_KEY\n  const minQueryLength = config.minQueryLength ?? DEFAULT_MIN_QUERY_LENGTH\n\n  function load(): SearchHistoryEntry[] {\n    try {\n      const raw = localStorage.getItem(storageKey)\n      return raw ? JSON.parse(raw) : []\n    } catch {\n      return []\n    }\n  }\n\n  function save(entries: SearchHistoryEntry[]): void {\n    try {\n      localStorage.setItem(storageKey, JSON.stringify(entries))\n    } catch {\n      // Silently fail (quota exceeded, SSR, etc.)\n    }\n  }\n\n  return {\n    /** Record a search query. Deduplicates by query string (updates timestamp). */\n    record(query: string, resultCount: number): void {\n      const trimmed = query.trim()\n      if (trimmed.length < minQueryLength) return\n\n      const entries = load()\n      // Remove existing entry for this query (will re-add at front)\n      const filtered = entries.filter((e) => e.query !== trimmed)\n      filtered.unshift({ query: trimmed, timestamp: Date.now(), resultCount })\n\n      // Trim to max entries\n      save(filtered.slice(0, maxEntries))\n    },\n\n    /** Get recent search queries, sorted by timestamp descending. */\n    getRecent(count?: number): SearchHistoryEntry[] {\n      const entries = load()\n      return count ? entries.slice(0, count) : entries\n    },\n\n    /** Remove a specific search query from history. */\n    remove(query: string): void {\n      const entries = load()\n      save(entries.filter((e) => e.query !== query))\n    },\n\n    /** Clear all search history. */\n    clear(): void {\n      try {\n        localStorage.removeItem(storageKey)\n      } catch {\n        // Silently fail\n      }\n    },\n  }\n}\n\n/**\n * In-memory search history (for testing or SSR).\n */\nexport function createInMemorySearchHistory(config: SearchHistoryConfig = {}) {\n  const maxEntries = config.maxEntries ?? DEFAULT_MAX_ENTRIES\n  const minQueryLength = config.minQueryLength ?? DEFAULT_MIN_QUERY_LENGTH\n  let entries: SearchHistoryEntry[] = []\n\n  return {\n    record(query: string, resultCount: number): void {\n      const trimmed = query.trim()\n      if (trimmed.length < minQueryLength) return\n      entries = entries.filter((e) => e.query !== trimmed)\n      entries.unshift({ query: trimmed, timestamp: Date.now(), resultCount })\n      entries = entries.slice(0, maxEntries)\n    },\n\n    getRecent(count?: number): SearchHistoryEntry[] {\n      return count ? entries.slice(0, count) : [...entries]\n    },\n\n    remove(query: string): void {\n      entries = entries.filter((e) => e.query !== query)\n    },\n\n    clear(): void {\n      entries = []\n    },\n  }\n}\n","import React, { createContext, useContext, useRef, useMemo } from 'react'\nimport type { CommandEngineConfig, CommandItem, CommandRegistry, TranslationFn } from '../core/types'\nimport { createRegistry } from '../core/registry'\nimport { createFuzzySearch } from '../core/search'\nimport { createKeywordEngine } from '../core/keywords'\nimport { createAccessFilter } from '../core/access-control'\nimport { createFrecencyEngine } from '../core/frecency'\nimport { createGroupManager } from '../core/grouping'\nimport { createContextEngine } from '../core/context'\nimport { createDefaultTranslation } from '../core/i18n'\nimport { createInMemorySearchHistory } from '../core/search-history'\nimport type { SearchEngine } from '../core/types'\n\n/** Internal engine context shape */\nexport interface EngineContextValue {\n  registry: CommandRegistry\n  search: SearchEngine\n  keywords: ReturnType<typeof createKeywordEngine>\n  accessFilter: ((items: CommandItem[]) => CommandItem[]) | null\n  frecency: ReturnType<typeof createFrecencyEngine>\n  groupManager: ReturnType<typeof createGroupManager>\n  contextEngine: ReturnType<typeof createContextEngine>\n  searchHistory: ReturnType<typeof createInMemorySearchHistory>\n  t: TranslationFn\n  config: CommandEngineConfig\n}\n\nconst EngineContext = createContext<EngineContextValue | null>(null)\n\nexport interface CommandEngineProviderProps {\n  children: React.ReactNode\n  config?: CommandEngineConfig\n}\n\n/**\n * Provider that initializes the command engine and makes it available\n * to all child hooks (useCommandPalette, useCommandRegister).\n */\nexport function CommandEngineProvider({ children, config = {} }: CommandEngineProviderProps) {\n  const registryRef = useRef<CommandRegistry | null>(null)\n  if (!registryRef.current) {\n    registryRef.current = createRegistry()\n  }\n\n  const value = useMemo<EngineContextValue>(() => {\n    const search = config.searchEngine ?? createFuzzySearch()\n    const keywords = createKeywordEngine(config.synonyms ?? {})\n    const accessFilter = config.accessControl\n      ? createAccessFilter(config.accessControl, config.accessCheckMode)\n      : null\n    const frecency = createFrecencyEngine(config.frecency)\n    const groupManager = createGroupManager(config.groups)\n    const contextEngine = createContextEngine(config.contextBoostWeight)\n    const t = config.t ?? createDefaultTranslation()\n    const searchHistory = createInMemorySearchHistory(config.searchHistory)\n\n    return {\n      registry: registryRef.current!,\n      search,\n      keywords,\n      accessFilter,\n      frecency,\n      groupManager,\n      contextEngine,\n      searchHistory,\n      t,\n      config,\n    }\n  }, [config])\n\n  return <EngineContext.Provider value={value}>{children}</EngineContext.Provider>\n}\n\n/**\n * Hook to access the engine context. Throws if used outside provider.\n */\nexport function useEngineContext(): EngineContextValue {\n  const ctx = useContext(EngineContext)\n  if (!ctx) {\n    throw new Error('useEngineContext must be used within a <CommandEngineProvider>')\n  }\n  return ctx\n}\n","import { useState, useCallback, useMemo, useSyncExternalStore } from 'react'\nimport type { CommandItem, CommandGroup, CommandPaletteState, ScoredItem } from '../core/types'\nimport type { GroupedResult } from '../core/grouping'\nimport { useEngineContext } from './context'\n\nexport interface UseCommandPaletteReturn extends CommandPaletteState {\n  /** Set the search query */\n  setSearch: (query: string) => void\n  /** Open the palette */\n  open: () => void\n  /** Close the palette */\n  close: () => void\n  /** Toggle the palette */\n  toggle: () => void\n  /** Record that a command was selected (for frecency) */\n  recordUsage: (commandId: string) => void\n  /** Select a command — records frecency, runs onSelect/action/href, closes palette */\n  select: (itemOrId: CommandItem | string) => void\n  /** Flat list of all result items (ungrouped) */\n  flatResults: ScoredItem[]\n  /** Results grouped by group, sorted by group priority (or relevance during search) */\n  groupedResults: GroupedResult[]\n  /** Navigate into a command's children (nested commands) */\n  drillDown: (item: CommandItem) => void\n  /** Go back one level in nested navigation */\n  drillUp: () => void\n  /** Reset to root level */\n  resetPath: () => void\n}\n\n/**\n * Main hook for the command palette.\n * Returns filtered, ranked, and grouped results based on the current search query.\n *\n * Subscribes to the registry via useSyncExternalStore for efficient updates.\n */\nexport function useCommandPalette(): UseCommandPaletteReturn {\n  const {\n    registry, search, keywords, accessFilter, frecency,\n    groupManager, contextEngine, searchHistory, t, config,\n  } = useEngineContext()\n\n  const [searchQuery, setSearchQuery] = useState('')\n  const [isOpen, setIsOpen] = useState(false)\n  const [activePath, setActivePath] = useState<CommandItem[]>([])\n\n  // Subscribe to registry changes\n  const commands = useSyncExternalStore(registry.subscribe, registry.getSnapshot, registry.getSnapshot)\n\n  // Determine which commands to search: root or nested children\n  const activeCommands = useMemo(() => {\n    if (activePath.length === 0) return commands\n    const parent = activePath[activePath.length - 1]\n    return parent.children ?? []\n  }, [commands, activePath])\n\n  // Pipeline: enrich → filter access → search → rank by frecency → context boost\n  const results = useMemo<ScoredItem[]>(() => {\n    // 1. Enrich with synonyms\n    const enriched = keywords.enrichAll(activeCommands)\n\n    // 2. Filter by access control\n    const accessible = accessFilter ? accessFilter(enriched) : enriched\n\n    // 3. Search\n    const searched = search.search(searchQuery, accessible)\n\n    // 4. Rank by frecency (only if there's a search query)\n    let ranked = searched\n    if (searchQuery.trim()) {\n      ranked = frecency.rank(searched, 0.3)\n\n      // 4b. Context boost (only during search, not empty state)\n      if (config.context) {\n        ranked = contextEngine.boost(ranked, config.context)\n        // Re-sort after boosting\n        ranked.sort((a, b) => b.score - a.score)\n      }\n\n      return ranked\n    }\n\n    // 5. Inject \"Recent\" group when search is empty\n    const frecencyConfig = config.frecency\n    if (!searchQuery.trim() && frecencyConfig?.showRecent) {\n      const recentCount = frecencyConfig.recentCount ?? 5\n      const recentLabel = frecencyConfig.recentLabel ?? t('group.recent')\n      const recentIds = frecency.getRecent(recentCount)\n\n      if (recentIds.length > 0) {\n        const recentItems: ScoredItem[] = []\n        const restItems: ScoredItem[] = []\n\n        for (const s of searched) {\n          if (recentIds.includes(s.item.id)) {\n            recentItems.push({\n              item: { ...s.item, group: recentLabel },\n              score: s.score,\n            })\n          } else {\n            restItems.push(s)\n          }\n        }\n\n        // Sort recent items by recency order\n        recentItems.sort(\n          (a, b) => recentIds.indexOf(a.item.id) - recentIds.indexOf(b.item.id),\n        )\n\n        return [...recentItems, ...restItems]\n      }\n    }\n\n    return searched\n  }, [activeCommands, searchQuery, search, keywords, accessFilter, frecency, contextEngine, t, config])\n\n  // Limit results\n  const limitedResults = useMemo(() => {\n    const max = config.maxResults ?? 50\n    return results.slice(0, max)\n  }, [results, config.maxResults])\n\n  // Group results by group field (for consumers building custom UIs)\n  const groupedResults = useMemo<GroupedResult[]>(() => {\n    return groupManager.groupResults(limitedResults, searchQuery)\n  }, [limitedResults, groupManager, searchQuery])\n\n  // Extract active groups\n  const groups = useMemo<CommandGroup[]>(() => {\n    return groupedResults.map((g) => g.group)\n  }, [groupedResults])\n\n  const open = useCallback(() => setIsOpen(true), [])\n  const close = useCallback(() => {\n    setIsOpen(false)\n    setSearchQuery('')\n    setActivePath([])\n  }, [])\n  const toggle = useCallback(() => {\n    setIsOpen((prev) => {\n      if (prev) {\n        setSearchQuery('')\n        setActivePath([])\n      }\n      return !prev\n    })\n  }, [])\n\n  // Nested navigation\n  const drillDown = useCallback((item: CommandItem) => {\n    if (!item.children?.length) return\n    setActivePath((prev) => [...prev, item])\n    setSearchQuery('')\n  }, [])\n\n  const drillUp = useCallback(() => {\n    setActivePath((prev) => prev.slice(0, -1))\n    setSearchQuery('')\n  }, [])\n\n  const resetPath = useCallback(() => {\n    setActivePath([])\n    setSearchQuery('')\n  }, [])\n\n  const recordUsage = useCallback(\n    (commandId: string) => {\n      frecency.recordUsage(commandId)\n    },\n    [frecency],\n  )\n\n  const select = useCallback(\n    (itemOrId: CommandItem | string) => {\n      const item =\n        typeof itemOrId === 'string'\n          ? limitedResults.find((r) => r.item.id === itemOrId)?.item\n          : itemOrId\n      if (!item) return\n\n      // If item has children, drill down instead of executing\n      if (item.children && item.children.length > 0) {\n        drillDown(item)\n        return\n      }\n\n      frecency.recordUsage(item.id)\n\n      // Record search history if enabled\n      if (config.searchHistory?.enabled && searchQuery.trim()) {\n        searchHistory.record(searchQuery, limitedResults.length)\n      }\n\n      if (config.onSelect) {\n        config.onSelect(item)\n      } else if (item.action) {\n        item.action(item)\n      } else if (item.href) {\n        window.location.href = item.href\n      }\n\n      close()\n    },\n    [limitedResults, frecency, searchHistory, config, searchQuery, close, drillDown],\n  )\n\n  return {\n    search: searchQuery,\n    setSearch: setSearchQuery,\n    results: limitedResults,\n    flatResults: limitedResults,\n    groupedResults,\n    groups,\n    isOpen,\n    isLoading: false,\n    breadcrumbs: activePath,\n    depth: activePath.length,\n    open,\n    close,\n    toggle,\n    recordUsage,\n    select,\n    drillDown,\n    drillUp,\n    resetPath,\n  }\n}\n","import { useEffect, useRef } from 'react'\nimport type { CommandItem } from '../core/types'\nimport { useEngineContext } from './context'\n\n/**\n * Register commands from within a component.\n * Commands are automatically unregistered when the component unmounts.\n *\n * @param commands - Commands to register\n * @param deps - Dependency array (re-registers when deps change)\n *\n * @example\n * ```tsx\n * function BillingPage() {\n *   useCommandRegister([\n *     { id: 'buy-credits', label: 'Buy Credits', action: () => openModal() },\n *   ])\n *   return <div>...</div>\n * }\n * ```\n */\nexport function useCommandRegister(\n  commands: CommandItem[],\n  deps: unknown[] = [],\n): void {\n  const { registry } = useEngineContext()\n  const cleanupRef = useRef<(() => void) | null>(null)\n\n  useEffect(() => {\n    // Clean up previous registration\n    cleanupRef.current?.()\n\n    // Register new commands\n    cleanupRef.current = registry.registerMany(commands)\n\n    // Cleanup on unmount or dep change\n    return () => {\n      cleanupRef.current?.()\n      cleanupRef.current = null\n    }\n  }, deps) // deps intentionally passed through from caller\n}\n","import { useCallback } from 'react'\nimport { useEngineContext } from './context'\n\n/**\n * Hook to interact with the frecency engine directly.\n *\n * @returns Object with recordUsage, getScore, and clear functions\n */\nexport function useFrecency() {\n  const { frecency } = useEngineContext()\n\n  const recordUsage = useCallback(\n    (commandId: string) => frecency.recordUsage(commandId),\n    [frecency],\n  )\n\n  const getScore = useCallback(\n    (commandId: string) => frecency.getScore(commandId),\n    [frecency],\n  )\n\n  const getRecent = useCallback(\n    (count?: number) => frecency.getRecent(count),\n    [frecency],\n  )\n\n  const clear = useCallback(() => frecency.clear(), [frecency])\n\n  return { recordUsage, getScore, getRecent, clear }\n}\n","import { useEngineContext } from './context'\nimport type { CommandContext } from '../core/types'\n\n/**\n * Hook to access context-related engine features.\n * Returns the current context config and the context engine for custom boosting.\n *\n * Note: To update context, pass it via the `config.context` prop on\n * `<CommandEngineProvider>`. This hook provides read access.\n */\nexport function useCommandContext(): {\n  context: CommandContext | undefined\n  boostWeight: number | undefined\n} {\n  const { config } = useEngineContext()\n\n  return {\n    context: config.context,\n    boostWeight: config.contextBoostWeight,\n  }\n}\n","import { useEngineContext } from './context'\nimport type { SearchHistoryEntry } from '../core/types'\n\n/**\n * Hook for direct access to search history.\n * Use this to build custom \"recent searches\" UI or manage history.\n */\nexport function useSearchHistory(): {\n  /** Get recent search queries */\n  getRecent: (count?: number) => SearchHistoryEntry[]\n  /** Clear all search history */\n  clear: () => void\n  /** Remove a specific query from history */\n  remove: (query: string) => void\n} {\n  const { searchHistory } = useEngineContext()\n\n  return {\n    getRecent: (count?: number) => searchHistory.getRecent(count),\n    clear: () => searchHistory.clear(),\n    remove: (query: string) => searchHistory.remove(query),\n  }\n}\n"]}