Restructure src/ modules with consistent internal organization
Reorganize major src/ directories to follow a consistent pattern with
core/, menu/, submenu/, inputs/, logs/, layout/, feedback/ subdirectories.
Changes by module:
- stores/: Move 5 store files to stores/core/
- utils/: Create core/ (terminal, tools, etc.) and menu/ (progress-bar)
- api/: Create copilot/core/, copilot/auth/, ollama/core/
- providers/: Create core/, copilot/core/, copilot/auth/, ollama/core/, login/core/
- ui/: Create core/, banner/core/, banner/menu/, spinner/core/,
input-editor/core/, components/core/, components/menu/
- tools/: Create core/ for registry.ts and types.ts
- tui-solid/: Reorganize components/ into menu/, submenu/, inputs/,
logs/, modals/, panels/, layout/, feedback/
- commands/: Create core/ for runner.ts and handlers.ts
- services/: Create core/ for agent.ts, permissions.ts, session.ts,
executor.ts, config.ts
All imports updated to use new paths. TypeScript compilation verified.
This commit is contained in:
@@ -21,7 +21,7 @@ import type {
|
||||
PatchRollback,
|
||||
ParsedFilePatch,
|
||||
} from "@/types/apply-patch";
|
||||
import type { ToolContext, ToolResult } from "@tools/types";
|
||||
import type { ToolContext, ToolResult } from "@tools/core/types";
|
||||
|
||||
// Rollback storage (in-memory for session)
|
||||
const rollbackStore: Map<string, PatchRollback> = new Map();
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
* Applies unified diff patches to files with fuzzy matching support.
|
||||
*/
|
||||
|
||||
import type { ToolDefinition } from "@tools/types";
|
||||
import type { ToolDefinition } from "@tools/core/types";
|
||||
import { applyPatchParams } from "@tools/apply-patch/params";
|
||||
import { executeApplyPatch } from "@tools/apply-patch/execute";
|
||||
|
||||
|
||||
@@ -9,7 +9,7 @@ import {
|
||||
BASH_MESSAGES,
|
||||
BASH_DESCRIPTION,
|
||||
} from "@constants/bash";
|
||||
import { promptPermission } from "@services/permissions";
|
||||
import { promptPermission } from "@services/core/permissions";
|
||||
import { bashParams } from "@tools/bash/params";
|
||||
import {
|
||||
truncateOutput,
|
||||
|
||||
6
src/tools/core/index.ts
Normal file
6
src/tools/core/index.ts
Normal file
@@ -0,0 +1,6 @@
|
||||
/**
|
||||
* Tools Core - Registry and Types
|
||||
*/
|
||||
|
||||
export * from "./registry";
|
||||
export * from "./types";
|
||||
219
src/tools/core/registry.ts
Normal file
219
src/tools/core/registry.ts
Normal file
@@ -0,0 +1,219 @@
|
||||
/**
|
||||
* Tool Registry
|
||||
*
|
||||
* Central registry for all available tools with support for
|
||||
* built-in tools, MCP tools, and plugin tools.
|
||||
*/
|
||||
|
||||
import type { ToolDefinition, FunctionDefinition } from "@tools/core/types";
|
||||
import { toolToFunction } from "@tools/core/types";
|
||||
import { bashTool } from "@/tools/bash";
|
||||
import { readTool } from "@/tools/read";
|
||||
import { writeTool } from "@/tools/write";
|
||||
import { editTool } from "@/tools/edit";
|
||||
import { todoWriteTool } from "@/tools/todo-write";
|
||||
import { todoReadTool } from "@/tools/todo-read";
|
||||
import { globToolDefinition } from "@/tools/glob/definition";
|
||||
import { grepToolDefinition } from "@/tools/grep/definition";
|
||||
import { webSearchTool } from "@/tools/web-search";
|
||||
import { webFetchTool } from "@/tools/web-fetch";
|
||||
import { multiEditTool } from "@/tools/multi-edit";
|
||||
import { lspTool } from "@/tools/lsp";
|
||||
import { applyPatchTool } from "@/tools/apply-patch";
|
||||
import {
|
||||
isMCPTool,
|
||||
executeMCPTool,
|
||||
getMCPToolsForApi,
|
||||
} from "@/services/mcp/tools";
|
||||
import {
|
||||
isPluginTool,
|
||||
getPluginTool,
|
||||
getPluginToolsForApi,
|
||||
} from "@/services/plugin-service";
|
||||
import { z } from "zod";
|
||||
|
||||
/**
|
||||
* All built-in tools
|
||||
*/
|
||||
export const tools: ToolDefinition[] = [
|
||||
bashTool,
|
||||
readTool,
|
||||
writeTool,
|
||||
editTool,
|
||||
multiEditTool,
|
||||
globToolDefinition,
|
||||
grepToolDefinition,
|
||||
todoWriteTool,
|
||||
todoReadTool,
|
||||
webSearchTool,
|
||||
webFetchTool,
|
||||
lspTool,
|
||||
applyPatchTool,
|
||||
];
|
||||
|
||||
/**
|
||||
* Tools that are read-only (allowed in chat mode)
|
||||
*/
|
||||
const READ_ONLY_TOOLS = new Set([
|
||||
"read",
|
||||
"glob",
|
||||
"grep",
|
||||
"todo_read",
|
||||
"web_search",
|
||||
"web_fetch",
|
||||
"lsp",
|
||||
]);
|
||||
|
||||
/**
|
||||
* Map of tools by name for fast lookup
|
||||
*/
|
||||
export const toolMap: Map<string, ToolDefinition> = new Map(
|
||||
tools.map((t) => [t.name, t]),
|
||||
);
|
||||
|
||||
/**
|
||||
* Cached MCP tools
|
||||
*/
|
||||
let mcpToolsCache: Awaited<ReturnType<typeof getMCPToolsForApi>> | null = null;
|
||||
|
||||
/**
|
||||
* Get tool by name (including MCP tools and plugin tools)
|
||||
*/
|
||||
export const getTool = (name: string): ToolDefinition | undefined => {
|
||||
const builtInTool = toolMap.get(name);
|
||||
if (builtInTool) {
|
||||
return builtInTool;
|
||||
}
|
||||
|
||||
if (isPluginTool(name)) {
|
||||
return getPluginTool(name);
|
||||
}
|
||||
|
||||
if (isMCPTool(name)) {
|
||||
return {
|
||||
name,
|
||||
description: `MCP tool: ${name}`,
|
||||
parameters: z.object({}).passthrough(),
|
||||
execute: async (args) => {
|
||||
const result = await executeMCPTool(
|
||||
name,
|
||||
args as Record<string, unknown>,
|
||||
);
|
||||
return {
|
||||
success: result.success,
|
||||
title: name,
|
||||
output: result.output,
|
||||
error: result.error,
|
||||
};
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
return undefined;
|
||||
};
|
||||
|
||||
/**
|
||||
* Get all tools as OpenAI function definitions
|
||||
*/
|
||||
export const getToolFunctions = (): FunctionDefinition[] => {
|
||||
return tools.map(toolToFunction);
|
||||
};
|
||||
|
||||
/**
|
||||
* Filter tools based on chat mode (read-only vs full access)
|
||||
*/
|
||||
const filterToolsForMode = (
|
||||
toolList: ToolDefinition[],
|
||||
chatMode: boolean,
|
||||
): ToolDefinition[] => {
|
||||
if (!chatMode) return toolList;
|
||||
return toolList.filter((t) => READ_ONLY_TOOLS.has(t.name));
|
||||
};
|
||||
|
||||
/**
|
||||
* Get tools as format expected by Copilot/OpenAI API
|
||||
* This includes both built-in tools and MCP tools
|
||||
* @param chatMode - If true, only return read-only tools (no file modifications)
|
||||
*/
|
||||
export const getToolsForApiAsync = async (
|
||||
chatMode = false,
|
||||
): Promise<
|
||||
{
|
||||
type: "function";
|
||||
function: FunctionDefinition;
|
||||
}[]
|
||||
> => {
|
||||
const filteredTools = filterToolsForMode(tools, chatMode);
|
||||
const builtInTools = filteredTools.map((t) => ({
|
||||
type: "function" as const,
|
||||
function: toolToFunction(t),
|
||||
}));
|
||||
|
||||
if (chatMode) {
|
||||
return builtInTools;
|
||||
}
|
||||
|
||||
try {
|
||||
mcpToolsCache = await getMCPToolsForApi();
|
||||
const pluginTools = getPluginToolsForApi();
|
||||
return [...builtInTools, ...pluginTools, ...mcpToolsCache];
|
||||
} catch {
|
||||
const pluginTools = getPluginToolsForApi();
|
||||
return [...builtInTools, ...pluginTools];
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Get tools synchronously (uses cached MCP tools if available)
|
||||
* @param chatMode - If true, only return read-only tools (no file modifications)
|
||||
*/
|
||||
export const getToolsForApi = (
|
||||
chatMode = false,
|
||||
): {
|
||||
type: "function";
|
||||
function: FunctionDefinition;
|
||||
}[] => {
|
||||
const filteredTools = filterToolsForMode(tools, chatMode);
|
||||
const builtInTools = filteredTools.map((t) => ({
|
||||
type: "function" as const,
|
||||
function: toolToFunction(t),
|
||||
}));
|
||||
|
||||
if (chatMode) {
|
||||
return builtInTools;
|
||||
}
|
||||
|
||||
const pluginTools = getPluginToolsForApi();
|
||||
|
||||
if (mcpToolsCache) {
|
||||
return [...builtInTools, ...pluginTools, ...mcpToolsCache];
|
||||
}
|
||||
|
||||
return [...builtInTools, ...pluginTools];
|
||||
};
|
||||
|
||||
/**
|
||||
* Refresh MCP tools cache
|
||||
* Returns information about the refresh result for logging
|
||||
*/
|
||||
export const refreshMCPTools = async (): Promise<{
|
||||
success: boolean;
|
||||
toolCount: number;
|
||||
error?: string;
|
||||
}> => {
|
||||
try {
|
||||
mcpToolsCache = await getMCPToolsForApi();
|
||||
return {
|
||||
success: true,
|
||||
toolCount: mcpToolsCache.length,
|
||||
};
|
||||
} catch (err) {
|
||||
mcpToolsCache = null;
|
||||
const errorMessage = err instanceof Error ? err.message : String(err);
|
||||
return {
|
||||
success: false,
|
||||
toolCount: 0,
|
||||
error: errorMessage,
|
||||
};
|
||||
}
|
||||
};
|
||||
@@ -6,7 +6,7 @@ import fs from "fs/promises";
|
||||
import path from "path";
|
||||
|
||||
import { EDIT_MESSAGES, EDIT_TITLES, EDIT_DESCRIPTION } from "@constants/edit";
|
||||
import { isFileOpAllowed, promptFilePermission } from "@services/permissions";
|
||||
import { isFileOpAllowed, promptFilePermission } from "@services/core/permissions";
|
||||
import { formatDiff } from "@utils/diff/format";
|
||||
import { generateDiff } from "@utils/diff/generate";
|
||||
import { editParams } from "@tools/edit/params";
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
* Tool registry - exports all available tools
|
||||
*/
|
||||
|
||||
export * from "@tools/types";
|
||||
export * from "@tools/core/types";
|
||||
export { bashTool } from "@tools/bash";
|
||||
export { readTool } from "@tools/read";
|
||||
export { writeTool } from "@tools/write";
|
||||
@@ -17,8 +17,8 @@ export { multiEditTool } from "@tools/multi-edit";
|
||||
export { lspTool } from "@tools/lsp";
|
||||
export { applyPatchTool } from "@tools/apply-patch";
|
||||
|
||||
import type { ToolDefinition, FunctionDefinition } from "@tools/types";
|
||||
import { toolToFunction } from "@tools/types";
|
||||
import type { ToolDefinition, FunctionDefinition } from "@tools/core/types";
|
||||
import { toolToFunction } from "@tools/core/types";
|
||||
import { bashTool } from "@tools/bash";
|
||||
import { readTool } from "@tools/read";
|
||||
import { writeTool } from "@tools/write";
|
||||
|
||||
@@ -17,7 +17,7 @@ import {
|
||||
type DocumentSymbol,
|
||||
type Hover,
|
||||
} from "@services/lsp/index";
|
||||
import type { ToolDefinition } from "@tools/types";
|
||||
import type { ToolDefinition } from "@tools/core/types";
|
||||
import fs from "fs/promises";
|
||||
|
||||
const PositionSchema = z.object({
|
||||
|
||||
@@ -13,7 +13,7 @@ import {
|
||||
MULTI_EDIT_TITLES,
|
||||
MULTI_EDIT_DESCRIPTION,
|
||||
} from "@constants/multi-edit";
|
||||
import { isFileOpAllowed, promptFilePermission } from "@services/permissions";
|
||||
import { isFileOpAllowed, promptFilePermission } from "@services/core/permissions";
|
||||
import { formatDiff } from "@utils/diff/format";
|
||||
import { generateDiff } from "@utils/diff/generate";
|
||||
import { multiEditParams } from "@tools/multi-edit/params";
|
||||
|
||||
@@ -11,7 +11,7 @@ import {
|
||||
READ_TITLES,
|
||||
READ_DESCRIPTION,
|
||||
} from "@constants/read";
|
||||
import { isFileOpAllowed, promptFilePermission } from "@services/permissions";
|
||||
import { isFileOpAllowed, promptFilePermission } from "@services/core/permissions";
|
||||
import { readParams } from "@tools/read/params";
|
||||
import { processLines } from "@tools/read/format";
|
||||
import type {
|
||||
|
||||
@@ -5,8 +5,8 @@
|
||||
*/
|
||||
|
||||
import { z } from "zod";
|
||||
import { todoStore } from "@stores/todo-store";
|
||||
import type { ToolDefinition } from "@tools/types";
|
||||
import { todoStore } from "@stores/core/todo-store";
|
||||
import type { ToolDefinition } from "@tools/core/types";
|
||||
|
||||
const parametersSchema = z.object({});
|
||||
|
||||
|
||||
@@ -5,8 +5,8 @@
|
||||
*/
|
||||
|
||||
import { z } from "zod";
|
||||
import { todoStore } from "@stores/todo-store";
|
||||
import type { ToolDefinition } from "@tools/types";
|
||||
import { todoStore } from "@stores/core/todo-store";
|
||||
import type { ToolDefinition } from "@tools/core/types";
|
||||
import type { TodoStatus } from "@/types/todo";
|
||||
|
||||
const TodoItemSchema = z.object({
|
||||
|
||||
@@ -10,7 +10,7 @@ import {
|
||||
WRITE_TITLES,
|
||||
WRITE_DESCRIPTION,
|
||||
} from "@constants/write";
|
||||
import { isFileOpAllowed, promptFilePermission } from "@services/permissions";
|
||||
import { isFileOpAllowed, promptFilePermission } from "@services/core/permissions";
|
||||
import { formatDiff } from "@utils/diff/format";
|
||||
import { generateDiff } from "@utils/diff/generate";
|
||||
import { writeParams } from "@tools/write/params";
|
||||
|
||||
Reference in New Issue
Block a user