test(dashboard): add autocomplete trigger/filter tests

This commit is contained in:
teernisse
2026-02-26 16:59:34 -05:00
parent 7059dea3f8
commit 48c3ddce90
3 changed files with 214 additions and 39 deletions

View File

@@ -1,5 +1,6 @@
import { html, useState, useRef, useCallback, useMemo, useEffect } from '../lib/preact.js';
import { getStatusMeta } from '../utils/status.js';
import { getTriggerInfo as _getTriggerInfo, filteredSkills as _filteredSkills } from '../utils/autocomplete.js';
export function SimpleInput({ sessionId, status, onRespond, autocompleteConfig = null }) {
const [text, setText] = useState('');
@@ -13,48 +14,12 @@ export function SimpleInput({ sessionId, status, onRespond, autocompleteConfig =
const autocompleteRef = useRef(null);
const meta = getStatusMeta(status);
// Detect if cursor is at a trigger position for autocomplete
const getTriggerInfo = useCallback((value, cursorPos) => {
// No config means no autocomplete
if (!autocompleteConfig) return null;
const { trigger } = autocompleteConfig;
// Find the start of the current "word" (after last whitespace before cursor)
let wordStart = cursorPos;
while (wordStart > 0 && !/\s/.test(value[wordStart - 1])) {
wordStart--;
}
// Check if word starts with this agent's trigger character
if (value[wordStart] === trigger) {
return {
trigger,
filterText: value.slice(wordStart + 1, cursorPos).toLowerCase(),
replaceStart: wordStart,
replaceEnd: cursorPos,
};
}
return null;
return _getTriggerInfo(value, cursorPos, autocompleteConfig);
}, [autocompleteConfig]);
// Filter skills based on user input after trigger
const filteredSkills = useMemo(() => {
if (!autocompleteConfig || !triggerInfo) return [];
const { skills } = autocompleteConfig;
const { filterText } = triggerInfo;
let filtered = skills;
if (filterText) {
filtered = skills.filter(s =>
s.name.toLowerCase().includes(filterText)
);
}
// Server pre-sorts, but re-sort after filtering for stability
return filtered.sort((a, b) => a.name.localeCompare(b.name));
return _filteredSkills(autocompleteConfig, triggerInfo);
}, [autocompleteConfig, triggerInfo]);
// Show/hide autocomplete based on trigger detection
@@ -229,7 +194,7 @@ export function SimpleInput({ sessionId, status, onRespond, autocompleteConfig =
<div class="px-3 py-2 text-sm text-dim">No matching skills</div>
` : filteredSkills.map((skill, i) => html`
<div
key=${i}
key=${skill.name}
class="px-3 py-2 cursor-pointer text-sm transition-colors ${
i === selectedIndex
? 'bg-selection/50 text-bright'