S3-01: Update Planner Prompt - Remove Old Tools

- Remove read_file and write_file from available tools list
- Update tool list to show: shell, http_get, http_search (3 tools)
- Update DO NOT invent tool names warning to reflect new tool list
- Update file operations guidance to use shell tool with cat/echo commands
- Update all references throughout the prompt
- Remove examples using read_file/write_file

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
larchanka
2026-02-17 17:48:10 +01:00
committed by Mikhail Larchanka
parent 028ff0b5bd
commit aaed8e4a19
3 changed files with 39 additions and 40 deletions

View File

@@ -2,15 +2,6 @@
## To Do
### S3-01 Update Planner Prompt - Remove Old Tools
- tags: [todo]
- defaultExpanded: false
```md
Remove read_file and write_file from planner prompt tool list and update references to use shell tool.
Source: S3-01_REMOVE_OLD_TOOLS_FROM_PLANNER.md
```
### S3-02 Update Planner Prompt - Document Shell Tool
- tags: [todo]
- defaultExpanded: false
@@ -94,8 +85,19 @@
## In Progress
### S2-02 Add Generator Service Tests
### S3-01 Update Planner Prompt - Remove Old Tools
- tags: [in-progress]
- defaultExpanded: false
```md
Remove read_file and write_file from planner prompt tool list and update references to use shell tool.
Source: S3-01_REMOVE_OLD_TOOLS_FROM_PLANNER.md
```
## Done
### S2-02 Add Generator Service Tests
- tags: [done]
- defaultExpanded: false
```md
Test that generator service correctly handles shell tool responses and extracts content for prompts.
@@ -103,8 +105,6 @@
Source: S2-02_GENERATOR_SERVICE_TESTS.md
```
## Done
### S2-01 Update Generator Service Content Extraction
- tags: [done]
- defaultExpanded: false

View File

@@ -59,9 +59,9 @@ You must respond with exactly one JSON object matching this structure. No markdo
### tool-host service
- **type**: \`tool\`
- **Available tools ONLY**: \`read_file\`, \`write_file\`, \`http_get\`, \`http_search\`
- **input**: \`{ "tool": "read_file" | "write_file" | "http_get" | "http_search", "arguments": {...} }\`
- **DO NOT** invent tool names that don't exist. Only use the four tools listed above.
- **Available tools ONLY**: \`shell\`, \`http_get\`, \`http_search\`
- **input**: \`{ "tool": "shell" | "http_get" | "http_search", "arguments": {...} }\`
- **DO NOT** invent tool names that don't exist. Only use the three tools listed above.
#### http_get tool
- **Purpose**: Fetch content from URLs with smart fallback to browser automation
@@ -98,7 +98,7 @@ You must respond with exactly one JSON object matching this structure. No markdo
- **Do NOT use** when:
- User provides a specific URL (use \`http_get\` instead)
- Information is already available in conversation context or stored memory
- User asks to read/write files (use \`read_file\`/\`write_file\` instead)
- User asks to read/write files (use \`shell\` tool with cat/echo commands instead)
- **Use \`semantic_search\` instead** when:
- User asks to search stored knowledge/memory without mentioning "web" or "online"
- User wants to search archived conversations or stored documents
@@ -139,12 +139,12 @@ You must respond with exactly one JSON object matching this structure. No markdo
## Important Guidelines
- **For mathematical calculations**: Use \`generate_text\` with \`model-router\` service. DO NOT create tools like "calculate_average", "math", or "calculator".
- **For code generation**: Use \`generate_text\` with \`model-router\` service. DO NOT create tools like "generate_javascript", "write_code", or "code_generator".
- **For file operations**: Use \`tool\` type with \`tool-host\` service and tool name \`read_file\` or \`write_file\`.
- **For file operations**: Use \`tool\` type with \`tool-host\` service and tool name \`shell\` with commands like \`cat file.txt\` (read) or \`echo "content" > file.txt\` (write).
- **For HTTP requests**: Use \`tool\` type with \`tool-host\` service and tool name \`http_get\`. Use \`useBrowser: true\` when fetching SPAs or sites with bot detection. HTML responses are automatically converted to Markdown for better readability.
- **For URL summarization**: When user asks to summarize a URL or web page, create a two-step plan: (1) fetch the URL content using \`http_get\` tool (use \`useBrowser: true\` if it's a SPA or protected site), (2) summarize the fetched content using \`generate_text\` with model-router. The summarize node should depend on the fetch node. The fetched content will be in Markdown format by default, making it easier to summarize.
- **For reminders**: When user requests a reminder, create a two-step plan: (1) parse time expression to cron using \`generate_text\` with a prompt that extracts the time part and converts it to cron format, (2) schedule reminder using \`schedule_reminder\` with cron-manager, including the extracted reminderMessage in the node input. The reminderMessage should be the action/item the user wants to be reminded about (e.g., "drink water", "call John", "posting to social networks").
- **For web search**: When user explicitly asks to "search the web", "use web search", "look up online", etc., use \`http_search\` tool with \`tool-host\` service. Do NOT use \`semantic_search\` for web search requests.
- Only use tools that exist: \`read_file\`, \`write_file\`, \`http_get\`, \`http_search\`. Never invent new tool names.
- Only use tools that exist: \`shell\`, \`http_get\`, \`http_search\`. Never invent new tool names.
- Output only valid JSON. No trailing commas, no comments.`;

View File

@@ -14,8 +14,6 @@ describe("GeneratorService shell tool response handling", () => {
let generatorService: GeneratorService;
let mockOllama: OllamaAdapter;
let mockModelRouter: ModelRouter;
let capturedEnvelope: Envelope | null = null;
let capturedPrompt: string | null = null;
beforeEach(() => {
// Mock OllamaAdapter
@@ -45,12 +43,6 @@ describe("GeneratorService shell tool response handling", () => {
modelRouter: mockModelRouter,
});
// Capture sent messages to inspect prompts
const originalSend = generatorService.send.bind(generatorService);
generatorService.send = vi.fn((envelope: Envelope) => {
capturedEnvelope = envelope;
originalSend(envelope);
});
});
describe("shell tool stdout extraction", () => {
@@ -84,14 +76,15 @@ describe("GeneratorService shell tool response handling", () => {
},
};
generatorService.handleEnvelope(envelope);
(generatorService as any).handleEnvelope(envelope);
// Wait for async processing
await new Promise((resolve) => setTimeout(resolve, 100));
expect(mockOllama.generate).toHaveBeenCalled();
const callArgs = (mockOllama.generate as ReturnType<typeof vi.fn>).mock.calls[0];
const prompt = callArgs[0] as string;
expect(callArgs).toBeDefined();
const prompt = callArgs![0] as string;
expect(prompt).toContain("File content from cat command");
expect(prompt).toContain("Summarize the file content");
@@ -127,14 +120,15 @@ describe("GeneratorService shell tool response handling", () => {
},
};
generatorService.handleEnvelope(envelope);
(generatorService as any).handleEnvelope(envelope);
// Wait for async processing
await new Promise((resolve) => setTimeout(resolve, 100));
expect(mockOllama.generate).toHaveBeenCalled();
const callArgs = (mockOllama.generate as ReturnType<typeof vi.fn>).mock.calls[0];
const prompt = callArgs[0] as string;
expect(callArgs).toBeDefined();
const prompt = callArgs![0] as string;
expect(prompt).toContain("Main output");
expect(prompt).toContain("[stderr: Warning: file not found]");
@@ -170,14 +164,15 @@ describe("GeneratorService shell tool response handling", () => {
},
};
generatorService.handleEnvelope(envelope);
(generatorService as any).handleEnvelope(envelope);
// Wait for async processing
await new Promise((resolve) => setTimeout(resolve, 100));
expect(mockOllama.generate).toHaveBeenCalled();
const callArgs = (mockOllama.generate as ReturnType<typeof vi.fn>).mock.calls[0];
const prompt = callArgs[0] as string;
expect(callArgs).toBeDefined();
const prompt = callArgs![0] as string;
// Empty stdout should not break the prompt
expect(prompt).toContain("Process this");
@@ -222,14 +217,15 @@ describe("GeneratorService shell tool response handling", () => {
},
};
generatorService.handleEnvelope(envelope);
(generatorService as any).handleEnvelope(envelope);
// Wait for async processing
await new Promise((resolve) => setTimeout(resolve, 100));
expect(mockOllama.generate).toHaveBeenCalled();
const callArgs = (mockOllama.generate as ReturnType<typeof vi.fn>).mock.calls[0];
const prompt = callArgs[0] as string;
expect(callArgs).toBeDefined();
const prompt = callArgs![0] as string;
expect(prompt).toContain("First file content");
expect(prompt).toContain("Second file content");
@@ -264,14 +260,15 @@ describe("GeneratorService shell tool response handling", () => {
},
};
generatorService.handleEnvelope(envelope);
(generatorService as any).handleEnvelope(envelope);
// Wait for async processing
await new Promise((resolve) => setTimeout(resolve, 100));
expect(mockOllama.generate).toHaveBeenCalled();
const callArgs = (mockOllama.generate as ReturnType<typeof vi.fn>).mock.calls[0];
const prompt = callArgs[0] as string;
expect(callArgs).toBeDefined();
const prompt = callArgs![0] as string;
expect(prompt).toContain("User goal: Analyze the configuration");
expect(prompt).toContain("Configuration file content");
@@ -307,14 +304,15 @@ describe("GeneratorService shell tool response handling", () => {
},
};
generatorService.handleEnvelope(envelope);
(generatorService as any).handleEnvelope(envelope);
// Wait for async processing
await new Promise((resolve) => setTimeout(resolve, 100));
expect(mockOllama.generate).toHaveBeenCalled();
const callArgs = (mockOllama.generate as ReturnType<typeof vi.fn>).mock.calls[0];
const prompt = callArgs[0] as string;
expect(callArgs).toBeDefined();
const prompt = callArgs![0] as string;
expect(prompt).toContain("Output content");
expect(prompt).not.toContain("[stderr:");
@@ -361,14 +359,15 @@ describe("GeneratorService shell tool response handling", () => {
},
};
generatorService.handleEnvelope(envelope);
(generatorService as any).handleEnvelope(envelope);
// Wait for async processing
await new Promise((resolve) => setTimeout(resolve, 100));
expect(mockOllama.generate).toHaveBeenCalled();
const callArgs = (mockOllama.generate as ReturnType<typeof vi.fn>).mock.calls[0];
const prompt = callArgs[0] as string;
expect(callArgs).toBeDefined();
const prompt = callArgs![0] as string;
expect(prompt).toContain("Local file content");
expect(prompt).toContain("Web page content");