micro-models-agent 0.2.63 → 0.2.65

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (114) hide show
  1. package/README.md +401 -354
  2. package/dist/agent/loop.d.ts.map +1 -1
  3. package/dist/agent/loop.js +254 -14
  4. package/dist/agent/loop.js.map +1 -1
  5. package/dist/agent/system-prompt.d.ts +16 -16
  6. package/dist/agent/system-prompt.d.ts.map +1 -1
  7. package/dist/agent/system-prompt.js +104 -67
  8. package/dist/agent/system-prompt.js.map +1 -1
  9. package/dist/agent/tool-executor.d.ts +2 -10
  10. package/dist/agent/tool-executor.d.ts.map +1 -1
  11. package/dist/agent/tool-executor.js +92 -1
  12. package/dist/agent/tool-executor.js.map +1 -1
  13. package/dist/async-map.d.ts +6 -0
  14. package/dist/async-map.d.ts.map +1 -0
  15. package/dist/async-map.js +16 -0
  16. package/dist/async-map.js.map +1 -0
  17. package/dist/blog-api/types/index.d.ts +2 -0
  18. package/dist/blog-api/types/index.d.ts.map +1 -0
  19. package/dist/blog-api/types/index.js +2 -0
  20. package/dist/blog-api/types/index.js.map +1 -0
  21. package/dist/cli/config.js +1 -1
  22. package/dist/cli/config.js.map +1 -1
  23. package/dist/cli.js +2 -2
  24. package/dist/cli.js.map +1 -1
  25. package/dist/config/config.d.ts +10 -0
  26. package/dist/config/config.d.ts.map +1 -1
  27. package/dist/config/config.js +29 -2
  28. package/dist/config/config.js.map +1 -1
  29. package/dist/config/types.d.ts +16 -1
  30. package/dist/config/types.d.ts.map +1 -1
  31. package/dist/examples.d.ts +22 -0
  32. package/dist/examples.d.ts.map +1 -0
  33. package/dist/examples.js +45 -0
  34. package/dist/examples.js.map +1 -0
  35. package/dist/fibonacci.d.ts +19 -0
  36. package/dist/fibonacci.d.ts.map +1 -0
  37. package/dist/fibonacci.js +61 -0
  38. package/dist/fibonacci.js.map +1 -0
  39. package/dist/llm/lmstudio-native.d.ts +10 -0
  40. package/dist/llm/lmstudio-native.d.ts.map +1 -0
  41. package/dist/llm/lmstudio-native.js +179 -0
  42. package/dist/llm/lmstudio-native.js.map +1 -0
  43. package/dist/llm/openai-compat.js +1 -1
  44. package/dist/plugins/builtin/lint-on-write/index.ts +96 -96
  45. package/dist/plugins/builtin/notify/index.js +6 -6
  46. package/dist/plugins/builtin/notify/index.ts +104 -104
  47. package/dist/repl.d.ts +5 -0
  48. package/dist/repl.d.ts.map +1 -0
  49. package/dist/repl.js +472 -0
  50. package/dist/repl.js.map +1 -0
  51. package/dist/skills/builtin/agent-test/SKILL.md +68 -68
  52. package/dist/skills/builtin/grill-me/SKILL.md +46 -46
  53. package/dist/sort.d.ts +8 -0
  54. package/dist/sort.d.ts.map +1 -0
  55. package/dist/sort.js +36 -0
  56. package/dist/sort.js.map +1 -0
  57. package/dist/stack.d.ts +9 -0
  58. package/dist/stack.d.ts.map +1 -0
  59. package/dist/stack.js +22 -0
  60. package/dist/stack.js.map +1 -0
  61. package/dist/test-run.d.ts +2 -0
  62. package/dist/test-run.d.ts.map +1 -0
  63. package/dist/test-run.js +13 -0
  64. package/dist/test-run.js.map +1 -0
  65. package/dist/tools/bash.d.ts.map +1 -1
  66. package/dist/tools/bash.js +19 -0
  67. package/dist/tools/bash.js.map +1 -1
  68. package/dist/tools/fs/write-file.d.ts.map +1 -1
  69. package/dist/tools/fs/write-file.js +13 -2
  70. package/dist/tools/fs/write-file.js.map +1 -1
  71. package/dist/tools/native/plan.d.ts +1 -1
  72. package/dist/tools/native/plan.d.ts.map +1 -1
  73. package/dist/tools/native/plan.js +85 -16
  74. package/dist/tools/native/plan.js.map +1 -1
  75. package/dist/tools/native/scaffold.d.ts +5 -0
  76. package/dist/tools/native/scaffold.d.ts.map +1 -0
  77. package/dist/tools/native/scaffold.js +246 -0
  78. package/dist/tools/native/scaffold.js.map +1 -0
  79. package/dist/tools/plan.d.ts +9 -0
  80. package/dist/tools/plan.d.ts.map +1 -1
  81. package/dist/tools/plan.js +27 -2
  82. package/dist/tools/plan.js.map +1 -1
  83. package/dist/tools/registry.d.ts.map +1 -1
  84. package/dist/tools/registry.js +3 -0
  85. package/dist/tools/registry.js.map +1 -1
  86. package/dist/tools/subagent.d.ts +16 -1
  87. package/dist/tools/subagent.d.ts.map +1 -1
  88. package/dist/tools/subagent.js +99 -10
  89. package/dist/tools/subagent.js.map +1 -1
  90. package/dist/ui/components/diff-view.d.ts +8 -0
  91. package/dist/ui/components/diff-view.d.ts.map +1 -0
  92. package/dist/ui/components/diff-view.js +25 -0
  93. package/dist/ui/components/diff-view.js.map +1 -0
  94. package/dist/ui/double-press.d.ts +9 -0
  95. package/dist/ui/double-press.d.ts.map +1 -0
  96. package/dist/ui/double-press.js +18 -0
  97. package/dist/ui/double-press.js.map +1 -0
  98. package/dist/ui/opentui-renderer.d.ts +53 -0
  99. package/dist/ui/opentui-renderer.d.ts.map +1 -0
  100. package/dist/ui/opentui-renderer.js +463 -0
  101. package/dist/ui/opentui-renderer.js.map +1 -0
  102. package/dist/utils/memoize.d.ts +14 -0
  103. package/dist/utils/memoize.d.ts.map +1 -0
  104. package/dist/utils/memoize.js +51 -0
  105. package/dist/utils/memoize.js.map +1 -0
  106. package/dist/utils/types.d.ts +6 -0
  107. package/dist/utils/types.d.ts.map +1 -0
  108. package/dist/utils/types.js +2 -0
  109. package/dist/utils/types.js.map +1 -0
  110. package/dist/utils.d.ts +22 -0
  111. package/dist/utils.d.ts.map +1 -0
  112. package/dist/utils.js +81 -0
  113. package/dist/utils.js.map +1 -0
  114. package/package.json +2 -2
@@ -0,0 +1,246 @@
1
+ import { writeFileSync, mkdirSync } from 'node:fs';
2
+ import { join, dirname } from 'node:path';
3
+ import { resolvePath, normalizePath } from '../fs/path-utils.js';
4
+ import { fsError, fsOk } from '../fs/types.js';
5
+ const TEMPLATES = {
6
+ 'vite-react-ts': {
7
+ name: 'Vite + React + TypeScript',
8
+ files: {
9
+ 'package.json': (dir) => JSON.stringify({
10
+ name: dir || 'app',
11
+ private: true,
12
+ version: '0.0.0',
13
+ type: 'module',
14
+ scripts: { dev: 'vite', build: 'tsc -b && vite build', preview: 'vite preview' },
15
+ dependencies: { react: '^19.0.0', 'react-dom': '^19.0.0' },
16
+ devDependencies: {
17
+ '@types/react': '^19.0.0',
18
+ '@types/react-dom': '^19.0.0',
19
+ '@vitejs/plugin-react': '^4.3.0',
20
+ typescript: '^5.7.0',
21
+ vite: '^6.0.0',
22
+ },
23
+ }, null, 2),
24
+ 'vite.config.ts': `import { defineConfig } from 'vite'
25
+ import react from '@vitejs/plugin-react'
26
+
27
+ export default defineConfig({
28
+ plugins: [react()],
29
+ })
30
+ `,
31
+ 'tsconfig.json': `{
32
+ "compilerOptions": {
33
+ "target": "ES2020",
34
+ "useDefineForClassFields": true,
35
+ "lib": ["ES2020", "DOM", "DOM.Iterable"],
36
+ "module": "ESNext",
37
+ "skipLibCheck": true,
38
+ "moduleResolution": "bundler",
39
+ "allowImportingTsExtensions": true,
40
+ "isolatedModules": true,
41
+ "moduleDetection": "force",
42
+ "noEmit": true,
43
+ "jsx": "react-jsx",
44
+ "strict": true,
45
+ "noUnusedLocals": true,
46
+ "noUnusedParameters": true,
47
+ "noFallthroughCasesInSwitch": true
48
+ },
49
+ "include": ["src"]
50
+ }
51
+ `,
52
+ 'index.html': `<!DOCTYPE html>
53
+ <html lang="en">
54
+ <head>
55
+ <meta charset="UTF-8" />
56
+ <meta name="viewport" content="width=device-width, initial-scale=1.0" />
57
+ <title>Vite App</title>
58
+ </head>
59
+ <body>
60
+ <div id="root"></div>
61
+ <script type="module" src="/src/main.tsx"></script>
62
+ </body>
63
+ </html>
64
+ `,
65
+ 'src/main.tsx': `import { StrictMode } from 'react'
66
+ import { createRoot } from 'react-dom/client'
67
+ import App from './App'
68
+
69
+ createRoot(document.getElementById('root')!).render(
70
+ <StrictMode>
71
+ <App />
72
+ </StrictMode>,
73
+ )
74
+ `,
75
+ 'src/App.tsx': `function App() {
76
+ return (
77
+ <div>
78
+ <h1>Hello Vite + React</h1>
79
+ </div>
80
+ )
81
+ }
82
+
83
+ export default App
84
+ `,
85
+ },
86
+ },
87
+ 'vite-vanilla-ts': {
88
+ name: 'Vite + Vanilla TypeScript',
89
+ files: {
90
+ 'package.json': (dir) => JSON.stringify({
91
+ name: dir || 'app',
92
+ private: true,
93
+ version: '0.0.0',
94
+ type: 'module',
95
+ scripts: { dev: 'vite', build: 'tsc && vite build', preview: 'vite preview' },
96
+ devDependencies: { typescript: '^5.7.0', vite: '^6.0.0' },
97
+ }, null, 2),
98
+ 'vite.config.ts': `import { defineConfig } from 'vite'
99
+
100
+ export default defineConfig({})
101
+ `,
102
+ 'tsconfig.json': `{
103
+ "compilerOptions": {
104
+ "target": "ES2020",
105
+ "useDefineForClassFields": true,
106
+ "lib": ["ES2020", "DOM", "DOM.Iterable"],
107
+ "module": "ESNext",
108
+ "skipLibCheck": true,
109
+ "moduleResolution": "bundler",
110
+ "allowImportingTsExtensions": true,
111
+ "isolatedModules": true,
112
+ "moduleDetection": "force",
113
+ "noEmit": true,
114
+ "strict": true
115
+ },
116
+ "include": ["src"]
117
+ }
118
+ `,
119
+ 'index.html': `<!DOCTYPE html>
120
+ <html lang="en">
121
+ <head>
122
+ <meta charset="UTF-8" />
123
+ <meta name="viewport" content="width=device-width, initial-scale=1.0" />
124
+ <title>Vite App</title>
125
+ </head>
126
+ <body>
127
+ <div id="root"></div>
128
+ <script type="module" src="/src/main.ts"></script>
129
+ </body>
130
+ </html>
131
+ `,
132
+ 'src/main.ts': `console.log('Hello from Vite!')
133
+ `,
134
+ },
135
+ },
136
+ 'node-express-ts': {
137
+ name: 'Node.js + Express + TypeScript',
138
+ files: {
139
+ 'package.json': (dir) => JSON.stringify({
140
+ name: dir || 'app',
141
+ private: true,
142
+ version: '0.0.0',
143
+ type: 'module',
144
+ scripts: { dev: 'tsx watch src/index.ts', build: 'tsc', start: 'node dist/index.js' },
145
+ dependencies: { express: '^4.21.0' },
146
+ devDependencies: {
147
+ '@types/express': '^5.0.0',
148
+ '@types/node': '^22.0.0',
149
+ typescript: '^5.7.0',
150
+ tsx: '^4.0.0',
151
+ },
152
+ }, null, 2),
153
+ 'tsconfig.json': `{
154
+ "compilerOptions": {
155
+ "target": "ES2022",
156
+ "module": "ESNext",
157
+ "moduleResolution": "bundler",
158
+ "outDir": "dist",
159
+ "rootDir": "src",
160
+ "strict": true,
161
+ "esModuleInterop": true,
162
+ "skipLibCheck": true
163
+ },
164
+ "include": ["src"]
165
+ }
166
+ `,
167
+ 'src/index.ts': `import express from 'express'
168
+
169
+ const app = express()
170
+ const PORT = process.env.PORT || 3000
171
+
172
+ app.get('/', (req, res) => {
173
+ res.json({ message: 'Hello from Express!' })
174
+ })
175
+
176
+ app.listen(PORT, () => {
177
+ console.log(\`Server running on port \${PORT}\`)
178
+ })
179
+ `,
180
+ },
181
+ },
182
+ };
183
+ export const scaffoldDefinition = {
184
+ type: 'function',
185
+ function: {
186
+ name: 'scaffold',
187
+ description: 'Create a complete project structure programmatically. Supports: vite-react-ts, vite-vanilla-ts, node-express-ts. Creates all files at once (package.json, config, source files). Use this INSTEAD of creating files manually for known project types.',
188
+ parameters: {
189
+ type: 'object',
190
+ properties: {
191
+ template: {
192
+ type: 'string',
193
+ enum: ['vite-react-ts', 'vite-vanilla-ts', 'node-express-ts'],
194
+ description: 'Project template to scaffold',
195
+ },
196
+ dir: {
197
+ type: 'string',
198
+ description: 'Directory name for the project (e.g. "todo-app")',
199
+ },
200
+ },
201
+ required: ['template', 'dir'],
202
+ },
203
+ },
204
+ };
205
+ export const scaffoldHandler = {
206
+ name: 'scaffold',
207
+ definition: scaffoldDefinition,
208
+ async execute(args, ctx) {
209
+ const template = String(args.template ?? '');
210
+ const dir = String(args.dir ?? '');
211
+ if (!template || !TEMPLATES[template]) {
212
+ return fsError(`Unknown template: "${template}". Available: ${Object.keys(TEMPLATES).join(', ')}`);
213
+ }
214
+ if (!dir) {
215
+ return fsError('dir is required. Usage: scaffold({template:"vite-react-ts", dir:"todo-app"})');
216
+ }
217
+ const resolved = resolvePath(dir, ctx.cwd);
218
+ if (!resolved.ok)
219
+ return fsError(resolved.error);
220
+ const projectDir = resolved.abs;
221
+ const tmpl = TEMPLATES[template];
222
+ const createdFiles = [];
223
+ try {
224
+ // Create project directory
225
+ mkdirSync(projectDir, { recursive: true });
226
+ for (const [relPath, content] of Object.entries(tmpl.files)) {
227
+ const filePath = join(projectDir, relPath);
228
+ const fileDir = dirname(filePath);
229
+ // Create parent directories
230
+ mkdirSync(fileDir, { recursive: true });
231
+ // Generate content (some files need the dir name)
232
+ const fileContent = typeof content === 'function'
233
+ ? content(dir)
234
+ : content;
235
+ writeFileSync(filePath, fileContent, 'utf-8');
236
+ createdFiles.push(relPath);
237
+ }
238
+ const fileList = createdFiles.map(f => ` ✅ ${f}`).join('\n');
239
+ return fsOk(`Scaffolded ${tmpl.name} project in ${normalizePath(dir)}/\n\nCreated ${createdFiles.length} files:\n${fileList}\n\nNext steps:\n cd ${dir}\n npm install\n npm run dev`);
240
+ }
241
+ catch (e) {
242
+ return fsError(`Scaffold failed: ${e.message}`);
243
+ }
244
+ },
245
+ };
246
+ //# sourceMappingURL=scaffold.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"scaffold.js","sourceRoot":"","sources":["../../../src/tools/native/scaffold.ts"],"names":[],"mappings":"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"}
@@ -21,6 +21,15 @@ export declare function showPlan(): string;
21
21
  export declare function clearPlan(): string;
22
22
  /** Возвращает количество незавершённых шагов плана (0 = все готово или нет плана) */
23
23
  export declare function getPlanPendingCount(): number;
24
+ /** Возвращает заголовок шага плана по его ID (или null если плана нет/шаг не найден) */
25
+ export declare function getPlanStepTitle(stepId: number): string | null;
26
+ /** Возвращает следующий pending шаг плана (или null) */
27
+ export declare function getNextPendingStep(): PlanStep | null;
28
+ /** Извлекает ожидаемую директорию из заголовка шага.
29
+ * Например: "Create todo-app/package.json" → "todo-app"
30
+ * "Создать index.html в src/" → "src"
31
+ * Возвращает null если директория не найдена. */
32
+ export declare function extractDirFromStepTitle(title: string): string | null;
24
33
  /** Парсит аргументы команды plan (create, done, progress, show, clear) */
25
34
  export declare function parsePlanCommand(args: string): {
26
35
  action: string;
@@ -1 +1 @@
1
- {"version":3,"file":"plan.d.ts","sourceRoot":"","sources":["../../src/tools/plan.ts"],"names":[],"mappings":"AAmBA,gBAAgB;AAChB,MAAM,WAAW,QAAQ;IACvB,EAAE,EAAE,MAAM,CAAC;IACX,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,SAAS,GAAG,aAAa,GAAG,MAAM,GAAG,SAAS,CAAC;CACxD;AAED,kBAAkB;AAClB,MAAM,WAAW,IAAI;IACnB,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,QAAQ,EAAE,CAAC;IAClB,SAAS,EAAE,MAAM,CAAC;IAClB,SAAS,EAAE,MAAM,CAAC;CACnB;AAuBD,6CAA6C;AAC7C,wBAAgB,UAAU,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,GAAG,MAAM,CAahE;AAED,kCAAkC;AAClC,wBAAgB,cAAc,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,QAAQ,CAAC,QAAQ,CAAC,GAAG,MAAM,CAWjF;AAED,2CAA2C;AAC3C,wBAAgB,QAAQ,IAAI,MAAM,CAIjC;AAED,2BAA2B;AAC3B,wBAAgB,SAAS,IAAI,MAAM,CAKlC;AAED,qFAAqF;AACrF,wBAAgB,mBAAmB,IAAI,MAAM,CAI5C;AAqBD,0EAA0E;AAC1E,wBAAgB,gBAAgB,CAAC,IAAI,EAAE,MAAM,GAAG;IAAE,MAAM,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,EAAE,CAAA;CAAE,CAKnF"}
1
+ {"version":3,"file":"plan.d.ts","sourceRoot":"","sources":["../../src/tools/plan.ts"],"names":[],"mappings":"AAmBA,gBAAgB;AAChB,MAAM,WAAW,QAAQ;IACvB,EAAE,EAAE,MAAM,CAAC;IACX,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,SAAS,GAAG,aAAa,GAAG,MAAM,GAAG,SAAS,CAAC;CACxD;AAED,kBAAkB;AAClB,MAAM,WAAW,IAAI;IACnB,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,QAAQ,EAAE,CAAC;IAClB,SAAS,EAAE,MAAM,CAAC;IAClB,SAAS,EAAE,MAAM,CAAC;CACnB;AAuBD,6CAA6C;AAC7C,wBAAgB,UAAU,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,GAAG,MAAM,CAahE;AAED,kCAAkC;AAClC,wBAAgB,cAAc,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,QAAQ,CAAC,QAAQ,CAAC,GAAG,MAAM,CAWjF;AAED,2CAA2C;AAC3C,wBAAgB,QAAQ,IAAI,MAAM,CAIjC;AAED,2BAA2B;AAC3B,wBAAgB,SAAS,IAAI,MAAM,CAKlC;AAED,qFAAqF;AACrF,wBAAgB,mBAAmB,IAAI,MAAM,CAI5C;AAED,wFAAwF;AACxF,wBAAgB,gBAAgB,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAK9D;AAED,wDAAwD;AACxD,wBAAgB,kBAAkB,IAAI,QAAQ,GAAG,IAAI,CAIpD;AAED;;;kDAGkD;AAClD,wBAAgB,uBAAuB,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAKpE;AAqBD,0EAA0E;AAC1E,wBAAgB,gBAAgB,CAAC,IAAI,EAAE,MAAM,GAAG;IAAE,MAAM,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,EAAE,CAAA;CAAE,CAKnF"}
@@ -1,4 +1,4 @@
1
- import { readFileSync, writeFileSync, existsSync, mkdirSync } from 'node:fs';
1
+ import { readFileSync, writeFileSync, existsSync, mkdirSync, unlinkSync } from 'node:fs';
2
2
  import { join } from 'node:path';
3
3
  import { homedir } from 'node:os';
4
4
  import { getTheme } from '../styling/index.js';
@@ -75,7 +75,7 @@ export function clearPlan() {
75
75
  if (!plan)
76
76
  return 'No active plan to clear.';
77
77
  try {
78
- require('node:fs').unlinkSync(PLAN_FILE);
78
+ unlinkSync(PLAN_FILE);
79
79
  }
80
80
  catch { /* ignore */ }
81
81
  return `Plan "${plan.name}" cleared.`;
@@ -87,6 +87,31 @@ export function getPlanPendingCount() {
87
87
  return 0;
88
88
  return plan.steps.filter(s => s.status !== 'done' && s.status !== 'skipped').length;
89
89
  }
90
+ /** Возвращает заголовок шага плана по его ID (или null если плана нет/шаг не найден) */
91
+ export function getPlanStepTitle(stepId) {
92
+ const plan = loadPlan();
93
+ if (!plan)
94
+ return null;
95
+ const step = plan.steps.find(s => s.id === stepId);
96
+ return step?.title ?? null;
97
+ }
98
+ /** Возвращает следующий pending шаг плана (или null) */
99
+ export function getNextPendingStep() {
100
+ const plan = loadPlan();
101
+ if (!plan)
102
+ return null;
103
+ return plan.steps.find(s => s.status === 'pending') ?? null;
104
+ }
105
+ /** Извлекает ожидаемую директорию из заголовка шага.
106
+ * Например: "Create todo-app/package.json" → "todo-app"
107
+ * "Создать index.html в src/" → "src"
108
+ * Возвращает null если директория не найдена. */
109
+ export function extractDirFromStepTitle(title) {
110
+ // Паттерн: "Create dir/file" или "Создать file в dir/"
111
+ const match = title.match(/(?:Create|Создать|Add|Добавить)\s+(\w[\w-]*)\//i)
112
+ || title.match(/(?:Create|Создать|Add|Добавить)\s+\S+\s+(?:in|в)\s+(\w[\w-]*)\//i);
113
+ return match?.[1] ?? null;
114
+ }
90
115
  /** Форматирует план для отображения (с иконками и прогрессом) */
91
116
  function formatPlan(plan) {
92
117
  const theme = getTheme();
@@ -1 +1 @@
1
- {"version":3,"file":"plan.js","sourceRoot":"","sources":["../../src/tools/plan.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"plan.js","sourceRoot":"","sources":["../../src/tools/plan.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"registry.d.ts","sourceRoot":"","sources":["../../src/tools/registry.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAgBtD,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,WAAW,CAAC;AAE5C;;;;;;;GAOG;AAEH,MAAM,WAAW,cAAc;IAC7B,IAAI,EAAE,UAAU,CAAC;IACjB,QAAQ,EAAE;QACR,IAAI,EAAE,MAAM,CAAC;QACb,WAAW,EAAE,MAAM,CAAC;QACpB,UAAU,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;KACrC,CAAC;CACH;AAED,MAAM,WAAW,QAAQ;IACvB,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,CAAC;IACb,SAAS,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CACpC;AAED,MAAM,MAAM,UAAU,GAAG,UAAU,CAAC;AA0CpC;;;GAGG;AACH,qBAAa,YAAY;IACvB,2EAA2E;IAC3E,cAAc,IAAI,cAAc,EAAE;IAIlC,UAAU,CAAC,OAAO,EAAE,WAAW,GAAG,OAAO;IAIzC,WAAW,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO;CAGnC"}
1
+ {"version":3,"file":"registry.d.ts","sourceRoot":"","sources":["../../src/tools/registry.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAiBtD,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,WAAW,CAAC;AAE5C;;;;;;;GAOG;AAEH,MAAM,WAAW,cAAc;IAC7B,IAAI,EAAE,UAAU,CAAC;IACjB,QAAQ,EAAE;QACR,IAAI,EAAE,MAAM,CAAC;QACb,WAAW,EAAE,MAAM,CAAC;QACpB,UAAU,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;KACrC,CAAC;CACH;AAED,MAAM,WAAW,QAAQ;IACvB,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,CAAC;IACb,SAAS,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CACpC;AAED,MAAM,MAAM,UAAU,GAAG,UAAU,CAAC;AA4CpC;;;GAGG;AACH,qBAAa,YAAY;IACvB,2EAA2E;IAC3E,cAAc,IAAI,cAAc,EAAE;IAIlC,UAAU,CAAC,OAAO,EAAE,WAAW,GAAG,OAAO;IAIzC,WAAW,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO;CAGnC"}
@@ -2,6 +2,7 @@ import { readFileDefinition } from './fs/read-file.js';
2
2
  import { writeFileDefinition } from './fs/write-file.js';
3
3
  import { editFileDefinition } from './fs/edit-file.js';
4
4
  import { listDirDefinition } from './fs/list-dir.js';
5
+ import { scaffoldDefinition } from './native/scaffold.js';
5
6
  import { createDirDefinition } from './fs/create-dir.js';
6
7
  import { deleteFileDefinition } from './fs/delete-file.js';
7
8
  import { copyFileDefinition } from './fs/copy-file.js';
@@ -33,6 +34,8 @@ const ALL_DEFINITIONS = [
33
34
  },
34
35
  // Bash
35
36
  bashDefinition,
37
+ // Scaffold
38
+ scaffoldDefinition,
36
39
  // FS
37
40
  readFileDefinition,
38
41
  writeFileDefinition,
@@ -1 +1 @@
1
- {"version":3,"file":"registry.js","sourceRoot":"","sources":["../../src/tools/registry.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAC;AACvD,OAAO,EAAE,mBAAmB,EAAE,MAAM,oBAAoB,CAAC;AACzD,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAC;AACvD,OAAO,EAAE,iBAAiB,EAAE,MAAM,kBAAkB,CAAC;AACrD,OAAO,EAAE,mBAAmB,EAAE,MAAM,oBAAoB,CAAC;AACzD,OAAO,EAAE,oBAAoB,EAAE,MAAM,qBAAqB,CAAC;AAC3D,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAC;AACvD,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAC;AACvD,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAC;AACvD,OAAO,EAAE,oBAAoB,EAAE,MAAM,qBAAqB,CAAC;AAC3D,OAAO,EAAE,oBAAoB,EAAE,MAAM,qBAAqB,CAAC;AAC3D,OAAO,EAAE,cAAc,EAAE,MAAM,cAAc,CAAC;AAC9C,OAAO,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAC3C,OAAO,EAAE,mBAAmB,EAAE,MAAM,iBAAiB,CAAC;AACtD,OAAO,EAAE,kBAAkB,EAAE,MAAM,gBAAgB,CAAC;AA6BpD,uDAAuD;AACvD,MAAM,eAAe,GAAqB;IACxC,SAAS;IACT;QACE,IAAI,EAAE,UAAU;QAChB,QAAQ,EAAE;YACR,IAAI,EAAE,UAAU;YAChB,WAAW,EAAE,6MAA6M;YAC1N,UAAU,EAAE;gBACV,IAAI,EAAE,QAAQ;gBACd,UAAU,EAAE;oBACV,IAAI,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,2CAA2C,EAAE;oBAClF,aAAa,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,oEAAoE,EAAE;iBACrH;gBACD,QAAQ,EAAE,CAAC,MAAM,CAAC;aACnB;SACF;KACF;IACD,OAAO;IACP,cAAc;IACd,KAAK;IACL,kBAAkB;IAClB,mBAAmB;IACnB,kBAAkB;IAClB,iBAAiB;IACjB,mBAAmB;IACnB,oBAAoB;IACpB,kBAAkB;IAClB,kBAAkB;IAClB,kBAAkB;IAClB,oBAAoB;IACpB,oBAAoB;IACpB,cAAc;IACd,MAAM;IACN,mBAAmB;IACnB,kBAAkB;CACnB,CAAC;AAEF,MAAM,gBAAgB,GAAG,IAAI,GAAG,CAAC,eAAe,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC;AAE5E;;;GAGG;AACH,MAAM,OAAO,YAAY;IACvB,2EAA2E;IAC3E,cAAc;QACZ,OAAO,eAAe,CAAC;IACzB,CAAC;IAED,UAAU,CAAC,OAAoB;QAC7B,OAAO,OAAO,CAAC,IAAI,KAAK,WAAW,IAAI,OAAO,CAAC,OAAO,KAAK,EAAE,CAAC;IAChE,CAAC;IAED,WAAW,CAAC,IAAY;QACtB,OAAO,gBAAgB,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;IACpC,CAAC;CACF"}
1
+ {"version":3,"file":"registry.js","sourceRoot":"","sources":["../../src/tools/registry.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAC;AACvD,OAAO,EAAE,mBAAmB,EAAE,MAAM,oBAAoB,CAAC;AACzD,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAC;AACvD,OAAO,EAAE,iBAAiB,EAAE,MAAM,kBAAkB,CAAC;AACrD,OAAO,EAAE,kBAAkB,EAAE,MAAM,sBAAsB,CAAC;AAC1D,OAAO,EAAE,mBAAmB,EAAE,MAAM,oBAAoB,CAAC;AACzD,OAAO,EAAE,oBAAoB,EAAE,MAAM,qBAAqB,CAAC;AAC3D,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAC;AACvD,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAC;AACvD,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAC;AACvD,OAAO,EAAE,oBAAoB,EAAE,MAAM,qBAAqB,CAAC;AAC3D,OAAO,EAAE,oBAAoB,EAAE,MAAM,qBAAqB,CAAC;AAC3D,OAAO,EAAE,cAAc,EAAE,MAAM,cAAc,CAAC;AAC9C,OAAO,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAC3C,OAAO,EAAE,mBAAmB,EAAE,MAAM,iBAAiB,CAAC;AACtD,OAAO,EAAE,kBAAkB,EAAE,MAAM,gBAAgB,CAAC;AA6BpD,uDAAuD;AACvD,MAAM,eAAe,GAAqB;IACxC,SAAS;IACT;QACE,IAAI,EAAE,UAAU;QAChB,QAAQ,EAAE;YACR,IAAI,EAAE,UAAU;YAChB,WAAW,EAAE,6MAA6M;YAC1N,UAAU,EAAE;gBACV,IAAI,EAAE,QAAQ;gBACd,UAAU,EAAE;oBACV,IAAI,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,2CAA2C,EAAE;oBAClF,aAAa,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,oEAAoE,EAAE;iBACrH;gBACD,QAAQ,EAAE,CAAC,MAAM,CAAC;aACnB;SACF;KACF;IACD,OAAO;IACP,cAAc;IACd,WAAW;IACX,kBAAkB;IAClB,KAAK;IACL,kBAAkB;IAClB,mBAAmB;IACnB,kBAAkB;IAClB,iBAAiB;IACjB,mBAAmB;IACnB,oBAAoB;IACpB,kBAAkB;IAClB,kBAAkB;IAClB,kBAAkB;IAClB,oBAAoB;IACpB,oBAAoB;IACpB,cAAc;IACd,MAAM;IACN,mBAAmB;IACnB,kBAAkB;CACnB,CAAC;AAEF,MAAM,gBAAgB,GAAG,IAAI,GAAG,CAAC,eAAe,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC;AAE5E;;;GAGG;AACH,MAAM,OAAO,YAAY;IACvB,2EAA2E;IAC3E,cAAc;QACZ,OAAO,eAAe,CAAC;IACzB,CAAC;IAED,UAAU,CAAC,OAAoB;QAC7B,OAAO,OAAO,CAAC,IAAI,KAAK,WAAW,IAAI,OAAO,CAAC,OAAO,KAAK,EAAE,CAAC;IAChE,CAAC;IAED,WAAW,CAAC,IAAY;QACtB,OAAO,gBAAgB,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;IACpC,CAAC;CACF"}
@@ -31,6 +31,21 @@ export interface IsolatedLoopResult {
31
31
  * @returns Текстовый контекст для system prompt субагента
32
32
  */
33
33
  export declare function buildSubagentContext(cwd: string): string;
34
+ /**
35
+ * Контекст для specialist'а — фокусированное описание ошибки.
36
+ *
37
+ * @param toolName - имя упавшего инструмента
38
+ * @param toolArgs - аргументы которые были переданы
39
+ * @param errorOutput - текст ошибки
40
+ * @param userTask - исходный запрос пользователя (краткое описание)
41
+ * @param attemptCount - сколько раз ошибка повторилась
42
+ * @returns Текст задачи для specialist'а
43
+ */
44
+ export declare function buildSpecialistTask(toolName: string, toolArgs: Record<string, unknown>, errorOutput: string, userTask: string, attemptCount: number): string;
45
+ /**
46
+ * Проверяет является ли ошибка тривиальной (не требует specialist).
47
+ */
48
+ export declare function isTrivialError(toolName: string, errorOutput: string): boolean;
34
49
  /**
35
50
  * Извлекает все JSON-блоки из тегов <tool_call>...</tool_call>.
36
51
  * Дублируется из loop.ts для изоляции субагентов.
@@ -79,7 +94,7 @@ export declare function doChat(provider: LLMProvider, messages: ChatMessage[], r
79
94
  *
80
95
  * @returns Результат: созданные файлы, ошибки, краткое описание, количество ходов
81
96
  */
82
- export declare function runIsolatedLoop(provider: LLMProvider, registry: ToolRegistry, task: string, existingFiles: string, cwd: string, quiet: boolean, renderer: OutputRenderer, toolExecutor?: ToolExecutor, mode?: string): Promise<IsolatedLoopResult>;
97
+ export declare function runIsolatedLoop(provider: LLMProvider, registry: ToolRegistry, task: string, existingFiles: string, cwd: string, quiet: boolean, renderer: OutputRenderer, toolExecutor?: ToolExecutor, mode?: string, toolModel?: string, maxStepsParam?: number): Promise<IsolatedLoopResult>;
83
98
  import type { ToolDefinition } from './registry.js';
84
99
  export declare const subagentDefinition: ToolDefinition;
85
100
  //# sourceMappingURL=subagent.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"subagent.d.ts","sourceRoot":"","sources":["../../src/tools/subagent.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,WAAW,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AACnE,OAAO,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAE7C,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,2BAA2B,CAAC;AAI9D,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,mBAAmB,CAAC;AAIxD;;;;;;;;;;;;;GAaG;AAIH,0DAA0D;AAC1D,MAAM,WAAW,kBAAkB;IACjC,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,MAAM,EAAE,MAAM,EAAE,CAAC;IACjB,OAAO,EAAE,MAAM,CAAC;IAChB,KAAK,EAAE,MAAM,CAAC;CACf;AAID;;;;;;GAMG;AACH,wBAAgB,oBAAoB,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAwDxD;AAID;;;;;;GAMG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,EAAE,CA+C9D;AAED;;;;;GAKG;AACH,wBAAgB,gBAAgB,CAAC,MAAM,EAAE,GAAG,GAAG;IAAE,KAAK,EAAE,OAAO,CAAC;IAAC,IAAI,CAAC,EAAE,MAAM,CAAC;IAAC,GAAG,CAAC,EAAE,MAAM,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,CAmD7G;AAID;;;;;;;;;;;GAWG;AACH,wBAAsB,MAAM,CAC1B,QAAQ,EAAE,WAAW,EACrB,QAAQ,EAAE,WAAW,EAAE,EACvB,QAAQ,EAAE,cAAc,EACxB,MAAM,CAAC,EAAE,WAAW,EACpB,OAAO,SAAI,EACX,YAAY,UAAQ,EACpB,MAAM,GAAE,MAAM,GAAG,UAAmB,EACpC,SAAS,CAAC,EAAE,MAAM,GACjB,OAAO,CAAC;IAAE,QAAQ,EAAE,MAAM,CAAC;IAAC,SAAS,EAAE,MAAM,CAAA;CAAE,CAAC,CA+JlD;AAwFD;;;;;;;;;;;GAWG;AACH,wBAAsB,eAAe,CACnC,QAAQ,EAAE,WAAW,EACrB,QAAQ,EAAE,YAAY,EACtB,IAAI,EAAE,MAAM,EACZ,aAAa,EAAE,MAAM,EACrB,GAAG,EAAE,MAAM,EACX,KAAK,EAAE,OAAO,EACd,QAAQ,EAAE,cAAc,EACxB,YAAY,CAAC,EAAE,YAAY,EAC3B,IAAI,CAAC,EAAE,MAAM,GACZ,OAAO,CAAC,kBAAkB,CAAC,CAkL7B;AAID,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,eAAe,CAAC;AAEpD,eAAO,MAAM,kBAAkB,EAAE,cAchC,CAAC"}
1
+ {"version":3,"file":"subagent.d.ts","sourceRoot":"","sources":["../../src/tools/subagent.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,WAAW,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAEnE,OAAO,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAE7C,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,2BAA2B,CAAC;AAI9D,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,mBAAmB,CAAC;AAIxD;;;;;;;;;;;;;GAaG;AAIH,0DAA0D;AAC1D,MAAM,WAAW,kBAAkB;IACjC,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,MAAM,EAAE,MAAM,EAAE,CAAC;IACjB,OAAO,EAAE,MAAM,CAAC;IAChB,KAAK,EAAE,MAAM,CAAC;CACf;AAID;;;;;;GAMG;AACH,wBAAgB,oBAAoB,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAwDxD;AAED;;;;;;;;;GASG;AACH,wBAAgB,mBAAmB,CACjC,QAAQ,EAAE,MAAM,EAChB,QAAQ,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EACjC,WAAW,EAAE,MAAM,EACnB,QAAQ,EAAE,MAAM,EAChB,YAAY,EAAE,MAAM,GACnB,MAAM,CAmBR;AAsBD;;GAEG;AACH,wBAAgB,cAAc,CAAC,QAAQ,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,GAAG,OAAO,CAgB7E;AAID;;;;;;GAMG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,EAAE,CA+C9D;AAED;;;;;GAKG;AACH,wBAAgB,gBAAgB,CAAC,MAAM,EAAE,GAAG,GAAG;IAAE,KAAK,EAAE,OAAO,CAAC;IAAC,IAAI,CAAC,EAAE,MAAM,CAAC;IAAC,GAAG,CAAC,EAAE,MAAM,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,CAmD7G;AAID;;;;;;;;;;;GAWG;AACH,wBAAsB,MAAM,CAC1B,QAAQ,EAAE,WAAW,EACrB,QAAQ,EAAE,WAAW,EAAE,EACvB,QAAQ,EAAE,cAAc,EACxB,MAAM,CAAC,EAAE,WAAW,EACpB,OAAO,SAAI,EACX,YAAY,UAAQ,EACpB,MAAM,GAAE,MAAM,GAAG,UAAmB,EACpC,SAAS,CAAC,EAAE,MAAM,GACjB,OAAO,CAAC;IAAE,QAAQ,EAAE,MAAM,CAAC;IAAC,SAAS,EAAE,MAAM,CAAA;CAAE,CAAC,CA+KlD;AAyFD;;;;;;;;;;;GAWG;AACH,wBAAsB,eAAe,CACnC,QAAQ,EAAE,WAAW,EACrB,QAAQ,EAAE,YAAY,EACtB,IAAI,EAAE,MAAM,EACZ,aAAa,EAAE,MAAM,EACrB,GAAG,EAAE,MAAM,EACX,KAAK,EAAE,OAAO,EACd,QAAQ,EAAE,cAAc,EACxB,YAAY,CAAC,EAAE,YAAY,EAC3B,IAAI,CAAC,EAAE,MAAM,EACb,SAAS,CAAC,EAAE,MAAM,EAClB,aAAa,CAAC,EAAE,MAAM,GACrB,OAAO,CAAC,kBAAkB,CAAC,CA6L7B;AAID,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,eAAe,CAAC;AAEpD,eAAO,MAAM,kBAAkB,EAAE,cAchC,CAAC"}
@@ -1,4 +1,5 @@
1
1
  import { jsonrepair } from 'jsonrepair';
2
+ import { LMStudioNative } from '../llm/lmstudio-native.js';
2
3
  import { ContextManager } from '../agent/context.js';
3
4
  import { buildSystemPrompt } from '../agent/system-prompt.js';
4
5
  import { checkFileSyntax } from './syntax-check.js';
@@ -72,6 +73,73 @@ export function buildSubagentContext(cwd) {
72
73
  catch { /* no tsconfig */ }
73
74
  return lines.join('\n');
74
75
  }
76
+ /**
77
+ * Контекст для specialist'а — фокусированное описание ошибки.
78
+ *
79
+ * @param toolName - имя упавшего инструмента
80
+ * @param toolArgs - аргументы которые были переданы
81
+ * @param errorOutput - текст ошибки
82
+ * @param userTask - исходный запрос пользователя (краткое описание)
83
+ * @param attemptCount - сколько раз ошибка повторилась
84
+ * @returns Текст задачи для specialist'а
85
+ */
86
+ export function buildSpecialistTask(toolName, toolArgs, errorOutput, userTask, attemptCount) {
87
+ const argsStr = JSON.stringify(toolArgs, null, 2);
88
+ return [
89
+ `The tool "${toolName}" has failed ${attemptCount} times with the same error while working on: "${userTask.slice(0, 200)}"`,
90
+ '',
91
+ `Failed tool call:`,
92
+ ` Tool: ${toolName}`,
93
+ ` Arguments: ${argsStr}`,
94
+ '',
95
+ `Error output:`,
96
+ ` ${errorOutput.slice(0, 500)}`,
97
+ '',
98
+ `Your task: Diagnose WHY this tool call fails and FIX the underlying problem.`,
99
+ ` - Read the relevant files to understand the actual state`,
100
+ ` - Fix the root cause (wrong path, missing file, syntax error, etc.)`,
101
+ ` - If the tool call arguments are wrong, correct them`,
102
+ ` - If the file doesn't exist, create it`,
103
+ ` - Return a clear summary of what you found and what you fixed`,
104
+ ].join('\n');
105
+ }
106
+ /** Паттерны ошибок которые НЕ триггерят specialist (trivial) */
107
+ const TRIVIAL_ERROR_PATTERNS = [
108
+ /no results? found/i,
109
+ /pattern .* matched 0 results/i,
110
+ /0 files? matched/i,
111
+ /command not found.*grep/i,
112
+ /not a directory/i,
113
+ ];
114
+ /** Паттерны ошибок которые ВСЕГДА требуют specialist (не trivial) */
115
+ const NON_TRIVIAL_ERROR_PATTERNS = [
116
+ /unexpected token/i,
117
+ /syntaxerror/i,
118
+ /cannot find module/i,
119
+ /module not found/i,
120
+ /permission denied/i,
121
+ /enoent/i,
122
+ /eacces/i,
123
+ ];
124
+ /**
125
+ * Проверяет является ли ошибка тривиальной (не требует specialist).
126
+ */
127
+ export function isTrivialError(toolName, errorOutput) {
128
+ // Синтаксические и критические ошибки — ВСЕГДА не trivial
129
+ if (NON_TRIVIAL_ERROR_PATTERNS.some(p => p.test(errorOutput))) {
130
+ return false;
131
+ }
132
+ // grep_search/glob_search с 0 результатами — нормальное поведение
133
+ if (toolName === 'grep_search' || toolName === 'glob_search') {
134
+ if (/0 results|0 files|no match/i.test(errorOutput) && errorOutput.length < 200) {
135
+ return true;
136
+ }
137
+ }
138
+ // Любая ошибка < 10 символов — скорее всего trivia
139
+ if (errorOutput.length < 10)
140
+ return true;
141
+ return TRIVIAL_ERROR_PATTERNS.some(p => p.test(errorOutput));
142
+ }
75
143
  // ─── Tool call parsing ───────────────────────────────────
76
144
  /**
77
145
  * Извлекает все JSON-блоки из тегов <tool_call>...</tool_call>.
@@ -145,7 +213,7 @@ export function validateToolCall(parsed) {
145
213
  if (!parsed || typeof parsed !== 'object') {
146
214
  return { valid: false, error: 'Not an object' };
147
215
  }
148
- const VALID_TOOLS = new Set(['bash', 'plan', 'todo', 'question', 'approve', 'theme', 'user_profile', 'subagent', 'read_file', 'write_file', 'edit_file', 'list_dir', 'create_dir', 'delete_file', 'copy_file', 'move_file', 'file_info', 'glob_search', 'grep_search', 'tree', 'web_search', 'web_fetch']);
216
+ const VALID_TOOLS = new Set(['bash', 'plan', 'todo', 'question', 'approve', 'theme', 'user_profile', 'subagent', 'read_file', 'write_file', 'edit_file', 'list_dir', 'create_dir', 'delete_file', 'copy_file', 'move_file', 'file_info', 'glob_search', 'grep_search', 'tree', 'web_search', 'web_fetch', 'scaffold']);
149
217
  if (!parsed.name || !VALID_TOOLS.has(parsed.name)) {
150
218
  return { valid: false, error: `Unknown tool: ${parsed.name}` };
151
219
  }
@@ -331,6 +399,21 @@ export async function doChat(provider, messages, renderer, signal, retries = 1,
331
399
  return retryResult;
332
400
  }
333
401
  }
402
+ // Phase 2.5: Emergency — принудительно генерируем content с низкой температурой
403
+ // Когда reasoning есть, но content пустой — модель "застряла" в thinking loop
404
+ if (lastReasoningText.trim()) {
405
+ logInfo('DOCHAT', `emergency: forcing content with low temperature`);
406
+ renderer.writeDim(`[emergency: forcing content with temperature=0.1]`);
407
+ const emergencyMessages = [
408
+ ...messages,
409
+ { role: 'user', content: '[System] You MUST produce a response now. Do NOT use thinking tags. Reply with a tool call or a direct answer. Any response is better than empty.' },
410
+ ];
411
+ const emergencyResult = await doChatOnce(provider, emergencyMessages, renderer, signal, false, showThinking, caller, maxTokens, 0.1);
412
+ if (emergencyResult.response.trim()) {
413
+ logInfo('DOCHAT', `emergency succeeded: ${emergencyResult.response.length} chars`);
414
+ return emergencyResult;
415
+ }
416
+ }
334
417
  // Phase 3: Fallback — используем reasoning как content
335
418
  if (llmCfg.fallbackToReasoning && lastReasoningText.trim()) {
336
419
  logInfo('DOCHAT', `fallback: using reasoning as content (${lastReasoningText.length} chars)`);
@@ -343,7 +426,7 @@ export async function doChat(provider, messages, renderer, signal, retries = 1,
343
426
  * Одиночный вызов LLM без retry логики.
344
427
  * Используется для retry с другими параметрами (например, enableThinking: false).
345
428
  */
346
- async function doChatOnce(provider, messages, renderer, signal, enableThinking = true, showThinking = false, caller = 'main', maxTokens) {
429
+ async function doChatOnce(provider, messages, renderer, signal, enableThinking = true, showThinking = false, caller = 'main', maxTokens, temperature = 0.7) {
347
430
  const startTime = performance.now();
348
431
  const fullText = [];
349
432
  let started = false;
@@ -352,7 +435,7 @@ async function doChatOnce(provider, messages, renderer, signal, enableThinking =
352
435
  renderer.writeSpinner();
353
436
  try {
354
437
  let buf = '';
355
- for await (const chunk of provider.chat(messages, { temperature: 0.7, signal, showThinking, enableThinking, max_tokens: maxTokens })) {
438
+ for await (const chunk of provider.chat(messages, { temperature, signal, showThinking, enableThinking, max_tokens: maxTokens })) {
356
439
  if (!chunk.content && !chunk.finish_reason)
357
440
  continue;
358
441
  if (chunk.content) {
@@ -418,11 +501,17 @@ async function doChatOnce(provider, messages, renderer, signal, enableThinking =
418
501
  *
419
502
  * @returns Результат: созданные файлы, ошибки, краткое описание, количество ходов
420
503
  */
421
- export async function runIsolatedLoop(provider, registry, task, existingFiles, cwd, quiet, renderer, toolExecutor, mode) {
504
+ export async function runIsolatedLoop(provider, registry, task, existingFiles, cwd, quiet, renderer, toolExecutor, mode, toolModel, maxStepsParam) {
422
505
  const createdFiles = [];
423
506
  const errors = [];
424
507
  const startTime = performance.now();
425
- logInfo('SUBAGENT', `START | task: "${task.slice(0, 200)}" | context window: ${provider.contextWindow}`);
508
+ // Two-model pipeline: если toolModel задана, создаём отдельный провайдер
509
+ let effectiveProvider = provider;
510
+ if (toolModel && provider instanceof LMStudioNative) {
511
+ effectiveProvider = new LMStudioNative(provider.baseUrl, toolModel, provider.contextWindow);
512
+ logInfo('SUBAGENT', `using tool model: ${toolModel} (main: ${provider.model})`);
513
+ }
514
+ logInfo('SUBAGENT', `START | task: "${task.slice(0, 200)}" | context window: ${effectiveProvider.contextWindow}`);
426
515
  // Always build auto-context from project, even if model didn't pass existingFiles
427
516
  const autoContext = buildSubagentContext(cwd);
428
517
  const mergedContext = existingFiles
@@ -439,8 +528,8 @@ export async function runIsolatedLoop(provider, registry, task, existingFiles, c
439
528
  { role: 'system', content: systemPrompt },
440
529
  { role: 'user', content: task + contextInfo },
441
530
  ];
442
- const ctx = new ContextManager(provider.contextWindow);
443
- const maxSteps = 20;
531
+ const ctx = new ContextManager(effectiveProvider.contextWindow);
532
+ const maxSteps = maxStepsParam ?? 20;
444
533
  let toolCallCount = 0;
445
534
  for (let step = 0; step < maxSteps; step++) {
446
535
  await ctx.updateTokens(messages);
@@ -457,7 +546,7 @@ export async function runIsolatedLoop(provider, registry, task, existingFiles, c
457
546
  const hasToolResult = messages.some(m => m.role === 'tool');
458
547
  const llmCfg = getLLMConfig();
459
548
  const maxTokens = hasToolResult ? llmCfg.maxTokensAfterTool : undefined;
460
- const { response } = await doChat(provider, messages, renderer, renderer?.abortSignal, 1, false, 'subagent', maxTokens);
549
+ const { response } = await doChat(effectiveProvider, messages, renderer, renderer?.abortSignal, 1, false, 'subagent', maxTokens);
461
550
  if (!response.trim()) {
462
551
  logDebug('SUBAGENT', `empty response at step ${step}, stopping`);
463
552
  break;
@@ -575,11 +664,11 @@ export const subagentDefinition = {
575
664
  type: 'function',
576
665
  function: {
577
666
  name: 'subagent',
578
- description: 'Delegate a task to an isolated agent in a fresh context. Use for EACH file when creating 3+ new files. Arguments: task (required, what to do), existingFiles (optional, comma-separated files for context).',
667
+ description: 'Delegate a task to an isolated agent with a FRESH context (no history of prior errors). Use for: (1) each file when creating 3+ new files, (2) any task where you are stuck or making repeated errors, (3) simple single-step operations (bash, file read/write). The subagent has all tools and starts clean — ideal when accumulated context is causing confusion.',
579
668
  parameters: {
580
669
  type: 'object',
581
670
  properties: {
582
- task: { type: 'string', description: 'What the subagent should create/fix/check' },
671
+ task: { type: 'string', description: 'What the subagent should do — be specific and include file paths' },
583
672
  existingFiles: { type: 'string', description: 'Comma-separated files the subagent can read for context (optional)' },
584
673
  },
585
674
  required: ['task'],