-
Notifications
You must be signed in to change notification settings - Fork 0
Core API
Complete API for modern-cmdk — the framework-agnostic core engine.
Creates a new command palette state machine instance. Returns a Disposable object (use with using keyword).
using machine = createCommandMachine({ search: customSearchEngine, // optional: pluggable SearchEngine frecency: frecencyEngine, // optional: FrecencyEngine instance loop: true, // optional: wrap navigation (default: false) initialSearch: '', // optional: initial search query });
| Method | Signature | Description |
|---|---|---|
send |
(event: CommandEvent) => void |
Dispatch an event to the state machine |
getState |
() => CommandState |
Get current immutable state snapshot |
subscribe |
(listener: (state: CommandState) => void) => () => void |
Subscribe to state changes; returns unsubscribe function |
[Symbol.dispose] |
() => void |
Clean up resources |
interface CommandState { search: string; activeItemId: ItemId | null; items: ReadonlyMap<ItemId, CommandItem>; filteredIds: readonly ItemId[]; groupedIds: ReadonlyMap<GroupId, readonly ItemId[]>; pages: readonly string[]; open: boolean; lastUpdated: Temporal.Instant; }
| Event Type | Payload | Description |
|---|---|---|
SEARCH_CHANGE |
{ search: string } |
Update search query |
REGISTER_ITEM |
{ item: CommandItem } |
Register a new item |
DEREGISTER_ITEM |
{ id: ItemId } |
Remove an item |
NAVIGATE |
{ direction: 'next' | 'prev' | 'first' | 'last' } |
Move active item |
ITEM_SELECT |
{ id: ItemId } |
Select the active item |
ITEM_ACTIVATE |
{ id: ItemId } |
Set a specific active item |
OPEN |
{} |
Open dialog |
CLOSE |
{} |
Close dialog |
TOGGLE |
{} |
Toggle open/close |
PAGE_PUSH |
{ page: string } |
Push a sub-page |
PAGE_POP |
{} |
Pop current page |
interface CommandItem { id: ItemId; value: string; label?: string; groupId?: GroupId; keywords?: readonly string[]; disabled?: boolean; onSelect?: () => void; }
Creates a branded ItemId from a plain string. Ensures type safety across the API.
const id = itemId('my-item');
Creates a branded GroupId from a plain string.
const gid = groupId('settings');
Creates the default TypeScript fuzzy search engine with substring + boundary matching.
interface SearchEngine { index(items: readonly CommandItem[]): void; search(query: string, items: readonly CommandItem[]): IteratorObject<SearchResult>; remove(ids: ReadonlySet<ItemId>): void; clear(): void; }
interface SearchResult { id: ItemId; score: number; matches: readonly { start: number; end: number }[]; }
Frequency x recency ranking engine using Temporal.Duration decay buckets.
using engine = new FrecencyEngine({ storage: new MemoryFrecencyStorage(), // or IdbFrecencyStorage namespace: 'my-app', // optional: storage namespace weights: { // optional: custom decay weights recent: 100, // < 1 hour day: 80, // < 1 day week: 60, // < 1 week month: 40, // < 1 month old: 20, // > 1 month }, });
| Method | Signature | Description |
|---|---|---|
recordSelection |
(id: ItemId) => void |
Record an item selection |
getBonus |
(id: ItemId) => number |
Get frecency bonus for an item |
getAllBonuses |
(now?: Temporal.Instant) => Map<ItemId, number> |
Get all bonuses |
[Symbol.dispose] |
() => void |
Save data and clean up |
Pure function for calculating a frecency bonus from a FrecencyRecord:
const bonus = computeFrecencyBonus(record, Temporal.Now.instant());
In-memory storage, no persistence. Default if none provided.
IndexedDB persistence via idb-keyval. Data survives page reloads.
import { IdbFrecencyStorage } from 'modern-cmdk'; using storage = new IdbFrecencyStorage(); using engine = new FrecencyEngine({ storage, namespace: 'app' });
Creates a keyboard shortcut registry with RegExp.escape-based parser and Object.groupBy conflict detection.
const registry = createKeyboardShortcutRegistry(); registry.register({ key: 'ctrl+k', handler: () => machine.send({ type: 'TOGGLE' }), description: 'Toggle command palette', }); // Detect conflicts const conflicts = registry.detectConflicts();
All major objects implement Disposable:
// Automatic cleanup with 'using' using machine = createCommandMachine(); using engine = new FrecencyEngine({ storage: new MemoryFrecencyStorage() }); // Resources are cleaned up when scope exits