neoctl 0.1.21 → 0.1.23

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.
@@ -0,0 +1,351 @@
1
+ import { readFileSync } from "node:fs";
2
+ import path from "node:path";
3
+ import { supportsImageInput } from "../../model/context-window.js";
4
+ import { createToolResultMessage } from "../../types/messages.js";
5
+ const DEFAULT_TIMEOUT_MS = 120_000;
6
+ export function createVisionTool(options = {}) {
7
+ return {
8
+ name: "vision",
9
+ description: "Inspect, describe, OCR, or answer questions about images from the current/prior conversation using the current vision-capable model. Accepts imageRefs such as [img#1], image 1, Generated image 1, filenames, or stored image paths; if omitted, defaults to the latest prior image. This tool is visible only when the current model is not known to lack image input support.",
10
+ inputSchema: {
11
+ type: "object",
12
+ properties: {
13
+ prompt: { type: "string", description: "Question/instruction for visual analysis, OCR, object identification, chart reading, etc." },
14
+ imageRefs: { type: "array", description: "Labels, numeric refs, filenames, or storage paths of prior conversation images, e.g. [img#1], image 1, Generated image 1, or C:\\...\\image.base64.txt.", items: { type: "string" } },
15
+ useLatestImage: { type: "boolean", description: "When imageRefs is omitted, use the latest prior conversation image. Defaults to true." },
16
+ model: { type: "string", description: "Optional model override. Defaults to the current main-loop model; the model must support image input." },
17
+ maxOutputTokens: { type: "integer", description: "Optional maximum output tokens for the vision response." },
18
+ },
19
+ required: ["prompt"],
20
+ additionalProperties: false,
21
+ },
22
+ metadata: {
23
+ readOnly: true,
24
+ concurrent: true,
25
+ visible: true,
26
+ maxResultSizeChars: 24000,
27
+ },
28
+ isEnabled(context) {
29
+ if (!context)
30
+ return false;
31
+ const model = resolveVisionModel(undefined, context, options);
32
+ return Boolean(model) && supportsImageInput(model) === true;
33
+ },
34
+ validate(input) {
35
+ const record = input;
36
+ return {
37
+ prompt: record.prompt ?? "",
38
+ imageRefs: record.imageRefs,
39
+ useLatestImage: record.useLatestImage ?? true,
40
+ model: record.model,
41
+ maxOutputTokens: record.maxOutputTokens,
42
+ };
43
+ },
44
+ validateInput(input, context) {
45
+ if (!input.prompt.trim())
46
+ return { ok: false, message: "vision prompt cannot be empty" };
47
+ if (input.imageRefs !== undefined && (!Array.isArray(input.imageRefs) || input.imageRefs.some((ref) => !ref.trim()))) {
48
+ return { ok: false, message: "vision imageRefs must contain non-empty strings" };
49
+ }
50
+ if (input.maxOutputTokens !== undefined && (!Number.isInteger(input.maxOutputTokens) || input.maxOutputTokens <= 0)) {
51
+ return { ok: false, message: "vision maxOutputTokens must be a positive integer" };
52
+ }
53
+ const model = resolveVisionModel(input, context, options);
54
+ if (!model)
55
+ return { ok: false, message: "vision requires a configured current model or a model parameter" };
56
+ if (supportsImageInput(model) !== true) {
57
+ return { ok: false, message: `vision requires a model that is explicitly marked as supporting image input; ${model} is not marked imageInput=true in model metadata` };
58
+ }
59
+ return { ok: true, value: { ...input, model } };
60
+ },
61
+ isConcurrencySafe() {
62
+ return true;
63
+ },
64
+ async call(input, context, callOptions) {
65
+ const gateway = context.options?.modelGateway ?? options.modelGateway;
66
+ if (!gateway) {
67
+ return { ok: false, output: { error: "vision requires a model gateway in tool context" } };
68
+ }
69
+ const model = resolveVisionModel(input, context, options);
70
+ const timeoutMs = options.timeoutMs ?? parsePositiveNumber(process.env.VISION_TIMEOUT_MS) ?? parsePositiveNumber(process.env.MODEL_TIMEOUT_MS) ?? DEFAULT_TIMEOUT_MS;
71
+ const startedAt = Date.now();
72
+ try {
73
+ const images = resolveVisionImages(input, context.messages);
74
+ if (images.length === 0) {
75
+ const available = formatAvailableImageRefs(collectConversationImages(context.messages));
76
+ throw new Error(`vision requires at least one source image. Provide imageRefs or keep useLatestImage enabled. Available imageRefs: ${available}`);
77
+ }
78
+ callOptions.onProgress?.({ toolName: "vision", message: `Inspecting ${images.length} image(s) with ${model ?? "current model"}` });
79
+ const result = await callVisionModel({
80
+ gateway,
81
+ model,
82
+ prompt: input.prompt,
83
+ images,
84
+ timeoutMs,
85
+ maxOutputTokens: input.maxOutputTokens,
86
+ reasoning: normalizeReasoning(context.options?.reasoning),
87
+ signal: context.abortSignal,
88
+ });
89
+ const durationMs = Date.now() - startedAt;
90
+ const output = {
91
+ provider: "model-gateway",
92
+ model,
93
+ prompt: input.prompt,
94
+ imageRefs: images.map((image) => formatSourceImageRef(image)).filter((ref) => Boolean(ref)),
95
+ sourceImages: images.length,
96
+ images: images.map((image) => ({
97
+ index: image.index,
98
+ label: image.label,
99
+ mimeType: image.mimeType,
100
+ filename: image.filename,
101
+ storagePath: image.storagePath,
102
+ })),
103
+ text: result.text,
104
+ durationMs,
105
+ usage: result.usage,
106
+ };
107
+ return {
108
+ ok: result.text.trim().length > 0,
109
+ output,
110
+ summary: result.text.trim() ? `vision inspected ${images.length} image(s) in ${durationMs}ms` : `vision returned no text after ${durationMs}ms`,
111
+ };
112
+ }
113
+ catch (error) {
114
+ return {
115
+ ok: false,
116
+ output: {
117
+ provider: "model-gateway",
118
+ model,
119
+ error: error instanceof Error ? error.message : String(error),
120
+ durationMs: Date.now() - startedAt,
121
+ },
122
+ };
123
+ }
124
+ },
125
+ mapResult(result) {
126
+ const output = result.output;
127
+ if (!isVisionToolOutput(output))
128
+ return output;
129
+ return {
130
+ ...output,
131
+ images: output.images.map((image) => ({
132
+ index: image.index,
133
+ label: image.label,
134
+ mimeType: image.mimeType,
135
+ filename: image.filename,
136
+ storagePath: image.storagePath,
137
+ })),
138
+ };
139
+ },
140
+ renderToolResultMessage(result, request) {
141
+ if (!request)
142
+ return undefined;
143
+ const output = this.mapResult ? this.mapResult(result, request) : result.output;
144
+ return createToolResultMessage(request, result.ok, output);
145
+ },
146
+ };
147
+ }
148
+ export const visionTool = createVisionTool();
149
+ function resolveVisionModel(input, context, options) {
150
+ return input?.model?.trim() || options.model?.trim() || context.options?.mainLoopModel?.trim() || process.env.MODEL?.trim() || process.env.OPENAI_MODEL?.trim();
151
+ }
152
+ function resolveVisionImages(input, messages) {
153
+ const refs = input.imageRefs ?? [];
154
+ if (refs.length > 0)
155
+ return resolveReferencedImages(messages, refs);
156
+ if (input.useLatestImage === false)
157
+ return [];
158
+ const latest = latestConversationImage(messages);
159
+ return latest ? [latest] : [];
160
+ }
161
+ function resolveReferencedImages(messages, refs) {
162
+ if (!messages || refs.length === 0)
163
+ return [];
164
+ const imageBlocks = collectConversationImages(messages);
165
+ return refs.map((ref, index) => {
166
+ const found = findReferencedImage(imageBlocks, ref);
167
+ if (!found)
168
+ throw new Error(`vision could not find referenced image: ${ref}. Available imageRefs: ${formatAvailableImageRefs(imageBlocks)}`);
169
+ return { ...found, filename: found.filename || imageFilename(found.mimeType, index) };
170
+ });
171
+ }
172
+ function findReferencedImage(images, ref) {
173
+ const normalizedRef = normalizeImageRef(ref);
174
+ if (!normalizedRef)
175
+ return undefined;
176
+ for (let i = images.length - 1; i >= 0; i -= 1) {
177
+ const image = images[i];
178
+ const candidates = [
179
+ image.label,
180
+ image.filename,
181
+ image.storagePath,
182
+ image.storagePath ? path.basename(image.storagePath) : undefined,
183
+ ];
184
+ if (candidates.some((candidate) => normalizeImageRef(candidate ?? "") === normalizedRef))
185
+ return image;
186
+ }
187
+ const numericRef = parseImageRefNumber(normalizedRef);
188
+ if (numericRef !== undefined)
189
+ return images[numericRef - 1];
190
+ return undefined;
191
+ }
192
+ function formatSourceImageRef(image) {
193
+ const ref = image.label?.trim() || image.filename || String(image.index + 1);
194
+ return image.storagePath ? `${ref} (${image.storagePath})` : ref;
195
+ }
196
+ function formatAvailableImageRefs(images) {
197
+ if (images.length === 0)
198
+ return "none";
199
+ return images
200
+ .map(formatSourceImageRef)
201
+ .filter((ref) => Boolean(ref))
202
+ .slice(-10)
203
+ .join(", ");
204
+ }
205
+ function latestConversationImage(messages) {
206
+ const images = collectConversationImages(messages);
207
+ return images[images.length - 1];
208
+ }
209
+ function collectConversationImages(messages) {
210
+ if (!messages)
211
+ return [];
212
+ const images = [];
213
+ for (const message of messages) {
214
+ for (const block of message.blocks) {
215
+ if (block.type !== "image")
216
+ continue;
217
+ const parsedInline = parseImageData(block.data);
218
+ const stored = readStoredImageDataSync(block.storage?.path);
219
+ const parsedStored = parseImageData(stored);
220
+ const mimeType = block.mimeType || parsedInline.mimeType || parsedStored.mimeType;
221
+ const base64 = parsedInline.base64 || parsedStored.base64;
222
+ if (!base64 || !mimeType)
223
+ continue;
224
+ images.push({
225
+ index: images.length,
226
+ base64: normalizeBase64ImageData(base64),
227
+ mimeType,
228
+ filename: imageFilename(mimeType, images.length),
229
+ label: block.label,
230
+ storagePath: block.storage?.path,
231
+ storageFormat: block.storage?.format,
232
+ });
233
+ }
234
+ }
235
+ return images;
236
+ }
237
+ function parseImageData(value) {
238
+ if (!value)
239
+ return {};
240
+ const match = /^data:([^;,]+);base64,(.*)$/su.exec(value.trim());
241
+ if (match)
242
+ return { mimeType: match[1], base64: match[2] };
243
+ return { base64: value };
244
+ }
245
+ function readStoredImageDataSync(filepath) {
246
+ if (!filepath)
247
+ return undefined;
248
+ try {
249
+ return readFileSync(filepath, "utf8");
250
+ }
251
+ catch {
252
+ return undefined;
253
+ }
254
+ }
255
+ function normalizeBase64ImageData(value) {
256
+ return value.replace(/^data:[^;,]+;base64,/su, "").replace(/\s+/gu, "");
257
+ }
258
+ function imageFilename(mimeType, index) {
259
+ const subtype = mimeType.split("/")[1]?.split(";")[0]?.trim() || "png";
260
+ const extension = subtype === "jpeg" ? "jpg" : subtype.replace(/[^a-z0-9]/giu, "") || "png";
261
+ return `image-${index + 1}.${extension}`;
262
+ }
263
+ function normalizeImageRef(value) {
264
+ return value
265
+ .trim()
266
+ .toLowerCase()
267
+ .replace(/[。.!?]+$/gu, "")
268
+ .replace(/\\/gu, "/")
269
+ .replace(/\s+/gu, " ");
270
+ }
271
+ function parseImageRefNumber(normalizedRef) {
272
+ const match = /^(?:\[?img#?|image(?:\s+|-)?)?(\d+)\]?$/iu.exec(normalizedRef);
273
+ if (!match)
274
+ return undefined;
275
+ const value = Number(match[1]);
276
+ return Number.isInteger(value) && value > 0 ? value : undefined;
277
+ }
278
+ async function callVisionModel(options) {
279
+ const userMessage = createVisionUserMessage(options.prompt, options.images);
280
+ const deltaParts = [];
281
+ const messageParts = [];
282
+ let usage;
283
+ for await (const event of options.gateway.stream({
284
+ model: options.model,
285
+ messages: [userMessage],
286
+ systemPrompt: "You are a vision analysis tool. Answer the user's image question accurately and concisely. If text is visible in the image, transcribe it when relevant.",
287
+ tools: [],
288
+ stream: false,
289
+ maxOutputTokens: options.maxOutputTokens,
290
+ reasoning: options.reasoning,
291
+ timeoutMs: options.timeoutMs,
292
+ cancellation: options.signal,
293
+ })) {
294
+ collectVisionModelEvent(event, deltaParts, messageParts);
295
+ if (event.type === "usage" || event.type === "response_completed" || event.type === "response_incomplete")
296
+ usage = event.usage ?? usage;
297
+ if (event.type === "error")
298
+ throw event.error;
299
+ }
300
+ const messageText = messageParts.join("\n").trim();
301
+ const deltaText = deltaParts.join("").trim();
302
+ return { text: messageText || deltaText, usage };
303
+ }
304
+ function createVisionUserMessage(prompt, images) {
305
+ const blocks = [
306
+ { type: "text", text: prompt },
307
+ ...images.map((image) => ({
308
+ type: "image",
309
+ mimeType: image.mimeType,
310
+ data: image.base64,
311
+ label: image.label ?? image.filename,
312
+ storage: image.storagePath && image.storageFormat ? { path: image.storagePath, format: image.storageFormat } : undefined,
313
+ })),
314
+ ];
315
+ return {
316
+ id: `vision-${Date.now().toString(36)}-${Math.random().toString(36).slice(2, 8)}`,
317
+ role: "user",
318
+ createdAt: new Date().toISOString(),
319
+ blocks,
320
+ };
321
+ }
322
+ function collectVisionModelEvent(event, deltaParts, messageParts) {
323
+ if (event.type === "assistant_delta")
324
+ deltaParts.push(event.text);
325
+ if (event.type === "assistant_message") {
326
+ const text = event.message.blocks
327
+ .filter((block) => block.type === "text")
328
+ .map((block) => block.text)
329
+ .join("\n")
330
+ .trim();
331
+ if (text)
332
+ messageParts.push(text);
333
+ }
334
+ }
335
+ function normalizeReasoning(value) {
336
+ if (value === null)
337
+ return null;
338
+ if (!value || typeof value !== "object")
339
+ return undefined;
340
+ return value;
341
+ }
342
+ function parsePositiveNumber(value) {
343
+ if (!value)
344
+ return undefined;
345
+ const parsed = Number(value);
346
+ return Number.isFinite(parsed) && parsed > 0 ? parsed : undefined;
347
+ }
348
+ function isVisionToolOutput(value) {
349
+ return !!value && typeof value === "object" && !Array.isArray(value) && value.provider === "model-gateway" && typeof value.text === "string";
350
+ }
351
+ //# sourceMappingURL=vision-tool.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"vision-tool.js","sourceRoot":"","sources":["../../../src/tools/builtins/vision-tool.ts"],"names":[],"mappings":"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"}
@@ -69,8 +69,10 @@ export interface ToolRuntimeOptions {
69
69
  debug?: boolean;
70
70
  verbose?: boolean;
71
71
  mainLoopModel?: string;
72
+ modelGateway?: import("../model/model-gateway.js").ModelGateway;
72
73
  tools?: ToolRegistryLike;
73
74
  thinkingConfig?: unknown;
75
+ reasoning?: import("../model/model-gateway.js").ReasoningConfig | null;
74
76
  activeSkill?: ActiveSkillRuntimeState;
75
77
  isNonInteractiveSession?: boolean;
76
78
  refreshTools?: () => Promise<void> | void;
@@ -1 +1 @@
1
- {"version":3,"file":"tool.js","sourceRoot":"","sources":["../../src/tools/tool.ts"],"names":[],"mappings":"AAgJA,MAAM,UAAU,sBAAsB,CAAC,IAAU,EAAE,OAAwB;IACzE,OAAO,OAAO,IAAI,CAAC,WAAW,KAAK,UAAU,CAAC,CAAC,CAAC,IAAI,CAAC,WAAW,CAAC,SAAS,EAAE,OAAO,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,WAAW,CAAC;AAC1G,CAAC"}
1
+ {"version":3,"file":"tool.js","sourceRoot":"","sources":["../../src/tools/tool.ts"],"names":[],"mappings":"AAkJA,MAAM,UAAU,sBAAsB,CAAC,IAAU,EAAE,OAAwB;IACzE,OAAO,OAAO,IAAI,CAAC,WAAW,KAAK,UAAU,CAAC,CAAC,CAAC,IAAI,CAAC,WAAW,CAAC,SAAS,EAAE,OAAO,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,WAAW,CAAC;AAC1G,CAAC"}
package/dist/web/index.js CHANGED
@@ -20,6 +20,7 @@ import { grepTool } from "../tools/builtins/grep-tool.js";
20
20
  import { searchTool } from "../tools/builtins/search-tool.js";
21
21
  import { planTool } from "../tools/builtins/plan-tool.js";
22
22
  import { createOpenAIImageGenerationTool } from "../tools/builtins/image-generation-tool.js";
23
+ import { createVisionTool } from "../tools/builtins/vision-tool.js";
23
24
  import { createAgentTool, resumeAgentTask } from "../agents/agent-tool.js";
24
25
  import { createTaskTools } from "../tasks/task-tools.js";
25
26
  import { TaskStore } from "../tasks/task-store.js";
@@ -120,6 +121,7 @@ export async function createWebRuntime(options = {}) {
120
121
  tools.register(readFileTool);
121
122
  tools.register(grepTool);
122
123
  tools.register(searchTool);
124
+ tools.register(createVisionTool({ modelGateway, model: modelConfig?.model }));
123
125
  if (modelConfig?.provider === "openai")
124
126
  tools.register(createOpenAIImageGenerationTool());
125
127
  tools.register(planTool);
@@ -191,6 +193,10 @@ function syncImageGenerationTool(runtime, provider) {
191
193
  if (provider === "openai")
192
194
  runtime.tools.register(createOpenAIImageGenerationTool());
193
195
  }
196
+ function syncVisionTool(runtime, model) {
197
+ runtime.tools.unregister("vision");
198
+ runtime.tools.register(createVisionTool({ modelGateway: runtime.modelGateway, model }));
199
+ }
194
200
  function formatCreatedEnvNotice(dotEnvPath) {
195
201
  return `Created default config file: ${dotEnvPath}\nSet MODEL_PROVIDER and the matching provider section (for example OPENAI_API_KEY or KIMI_API_KEY), then restart neo.`;
196
202
  }
@@ -423,6 +429,7 @@ export class WebRepl {
423
429
  this.runtime.agentRuntime.modelGateway = this.runtime.modelGateway;
424
430
  this.runtime.engine.setModelProvider({ modelGateway: this.runtime.modelGateway, model: config.model, fallbackModel: config.fallbackModel, reasoning: config.defaultReasoning });
425
431
  syncImageGenerationTool(this.runtime, config.provider);
432
+ syncVisionTool(this.runtime, config.model);
426
433
  this.runtime.defaultReasoning = config.defaultReasoning;
427
434
  const metrics = await this.runtime.engine.contextMetrics();
428
435
  this.setStatus({ ...this.status, metrics, activityTick: this.status.activityTick + 1 });
@@ -1079,6 +1086,7 @@ async function handleModelCommand(command, runtime) {
1079
1086
  runtime.agentRuntime.modelGateway = runtime.modelGateway;
1080
1087
  runtime.engine.setModelProvider({ modelGateway: runtime.modelGateway, model: config.model, fallbackModel: config.fallbackModel, reasoning: config.defaultReasoning });
1081
1088
  syncImageGenerationTool(runtime, config.provider);
1089
+ syncVisionTool(runtime, config.model);
1082
1090
  runtime.defaultReasoning = config.defaultReasoning;
1083
1091
  }
1084
1092
  }