* Refactor GSD command/bootstrap modules * fix: resolve TypeScript build errors in refactored db-tools and catalog - db-tools.ts: add missing execute callback params (signal, onUpdate, ctx), remove isError from return objects (not in AgentToolResult type), cast details as any to avoid union type mismatch across error/success paths - catalog.ts: use Object.entries() on TemplateRegistry.templates Record instead of treating it as an array, use Record key as template id Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: update source-contract tests to reference refactored file locations The god-file refactor moved code from index.ts and commands.ts into bootstrap/agent-end-recovery.ts, bootstrap/register-hooks.ts, and commands/handlers/core.ts. Update three test files to read from the correct paths and adjust pattern assertions to match the new code structure. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
71 lines
2 KiB
TypeScript
71 lines
2 KiB
TypeScript
import type { Model } from "@gsd/pi-ai";
|
|
|
|
export async function handleModelCommand(host: any, searchTerm?: string): Promise<void> {
|
|
if (!searchTerm) {
|
|
host.showModelSelector();
|
|
return;
|
|
}
|
|
|
|
const model = await findExactModelMatch(host, searchTerm);
|
|
if (model) {
|
|
try {
|
|
await host.session.setModel(model);
|
|
host.footer.invalidate();
|
|
host.updateEditorBorderColor();
|
|
host.showStatus(`Model: ${model.id}`);
|
|
host.checkDaxnutsEasterEgg(model);
|
|
} catch (error) {
|
|
host.showError(error instanceof Error ? error.message : String(error));
|
|
}
|
|
return;
|
|
}
|
|
|
|
host.showModelSelector(searchTerm);
|
|
}
|
|
|
|
export async function findExactModelMatch(host: any, searchTerm: string): Promise<Model<any> | undefined> {
|
|
const term = searchTerm.trim();
|
|
if (!term) return undefined;
|
|
|
|
let targetProvider: string | undefined;
|
|
let targetModelId = "";
|
|
|
|
if (term.includes("/")) {
|
|
const parts = term.split("/", 2);
|
|
targetProvider = parts[0]?.trim().toLowerCase();
|
|
targetModelId = parts[1]?.trim().toLowerCase() ?? "";
|
|
} else {
|
|
targetModelId = term.toLowerCase();
|
|
}
|
|
|
|
if (!targetModelId) return undefined;
|
|
|
|
const models = await getModelCandidates(host);
|
|
const exactMatches = models.filter((item) => {
|
|
const idMatch = item.id.toLowerCase() === targetModelId;
|
|
const providerMatch = !targetProvider || item.provider.toLowerCase() === targetProvider;
|
|
return idMatch && providerMatch;
|
|
});
|
|
|
|
return exactMatches.length === 1 ? exactMatches[0] : undefined;
|
|
}
|
|
|
|
export async function getModelCandidates(host: any): Promise<Model<any>[]> {
|
|
if (host.session.scopedModels.length > 0) {
|
|
return host.session.scopedModels.map((scoped: any) => scoped.model);
|
|
}
|
|
|
|
host.session.modelRegistry.refresh();
|
|
try {
|
|
return await host.session.modelRegistry.getAvailable();
|
|
} catch {
|
|
return [];
|
|
}
|
|
}
|
|
|
|
export async function updateAvailableProviderCount(host: any): Promise<void> {
|
|
const models = await getModelCandidates(host);
|
|
const uniqueProviders = new Set(models.map((m) => m.provider));
|
|
host.footerDataProvider.setAvailableProviderCount(uniqueProviders.size);
|
|
}
|
|
|