nolo-cli 0.1.38 → 0.1.40
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.
- package/README.md +4 -4
- package/agent-runtime/agentRecordConfig.ts +0 -14
- package/agent-runtime/dialogWritePlan.ts +39 -0
- package/agent-runtime/hostAdapter.ts +4 -1
- package/agent-runtime/hybridRecordStore.ts +1 -1
- package/agent-runtime/index.ts +39 -18
- package/agent-runtime/localDialogRead.ts +23 -0
- package/agent-runtime/localLoop.ts +87 -7
- package/agent-runtime/localToolPolicy.ts +1 -17
- package/agent-runtime/localWorkspaceTools.ts +51 -110
- package/agent-runtime/noloWorkspaceTools.ts +371 -0
- package/agent-runtime/runtimeToolPolicy.ts +3 -14
- package/agent-runtime/runtimeToolSurface.ts +198 -0
- package/agent-runtime/types.ts +2 -1
- package/agentAliases.ts +8 -1
- package/agentRunCommand.ts +65 -95
- package/agentRuntimeLocal.ts +1 -7
- package/ai/agent/cliExecutor.ts +249 -34
- package/chat/messages/fetchMessages.ts +84 -0
- package/chat/messages/types.ts +185 -0
- package/cli/agentAliases.ts +8 -1
- package/cli/agentRunCommand.ts +65 -95
- package/cli/agentRuntimeLocal.ts +1 -7
- package/cli/cliEnvHelpers.ts +11 -7
- package/cli/client/agentRun.ts +94 -93
- package/cli/client/localRuntimeAdapter.ts +250 -69
- package/cli/commandRegistry.ts +2 -2
- package/cli/connectorRunArtifact.ts +0 -1
- package/cli/dialogCommands.ts +572 -0
- package/cli/dialogInternalCommandEntries.ts +4 -0
- package/cli/machineWsRunDispatch.ts +76 -39
- package/cli/offlineMarxistsAgentCommand.ts +6 -4
- package/cli/scriptCommandEntries.ts +0 -2
- package/cli/tui/readlineWorkspace.ts +69 -0
- package/cli/tui/session.ts +176 -1
- package/cliEnvHelpers.ts +11 -7
- package/client/agentConfigResolver.test.ts +4 -5
- package/client/agentRun.test.ts +307 -57
- package/client/agentRun.ts +94 -93
- package/client/localRuntimeAdapter.test.ts +332 -53
- package/client/localRuntimeAdapter.ts +250 -69
- package/client/localRuntimeDryRun.test.ts +23 -9
- package/client/localToolPolicy.test.ts +4 -4
- package/commandRegistry.ts +2 -2
- package/connectorRunArtifact.ts +0 -1
- package/database/server/db.ts +99 -0
- package/database/server/ensureDbOpen.ts +12 -0
- package/database/server/levelAuthorityStore.ts +20 -1
- package/database/server/memoryAuthorityStore.ts +133 -0
- package/database/server/serverStoreFactory.ts +118 -0
- package/dialogCommands.ts +572 -0
- package/dialogInternalCommandEntries.ts +4 -0
- package/machineWsRunDispatch.ts +76 -39
- package/offlineMarxistsAgentCommand.ts +6 -4
- package/package.json +11 -9
- package/scriptCommandEntries.ts +0 -2
- package/tui/readlineWorkspace.ts +69 -0
- package/tui/session.ts +176 -1
- package/agent-runtime/taskWorkspace.ts +0 -193
- package/agent-runtime/workspaceSession.ts +0 -76
- package/cli/client/taskWorktree.ts +0 -8
- package/cli/client/workspaceSession.ts +0 -11
- package/client/taskWorktree.ts +0 -8
- package/client/workspaceSession.test.ts +0 -57
- package/client/workspaceSession.ts +0 -11
|
@@ -5,6 +5,8 @@ import type {
|
|
|
5
5
|
} from "../agentRuntimeLocal";
|
|
6
6
|
import { request as httpRequest } from "node:http";
|
|
7
7
|
import { request as httpsRequest } from "node:https";
|
|
8
|
+
import { dirname, join } from "node:path";
|
|
9
|
+
import { fileURLToPath } from "node:url";
|
|
8
10
|
import {
|
|
9
11
|
buildLocalWorkspacePolicyToolNames,
|
|
10
12
|
buildLocalWorkspaceToolset,
|
|
@@ -19,6 +21,7 @@ import {
|
|
|
19
21
|
resolveCurrentRunRuntimeToolPolicy,
|
|
20
22
|
resolveLocalWorkspaceExecutorOptionsFromPolicy,
|
|
21
23
|
resolveRequestedRuntimeToolNames,
|
|
24
|
+
resolveRuntimeToolSurfaceForAgent,
|
|
22
25
|
shouldUsePlatformChatProvider,
|
|
23
26
|
} from "../agentRuntimeLocal";
|
|
24
27
|
import type { AgentRuntimeChatMessage } from "../../agent-runtime";
|
|
@@ -40,19 +43,41 @@ import {
|
|
|
40
43
|
} from "./hybridRecordStore";
|
|
41
44
|
import { executeLocalToolWithPolicy } from "./localToolPolicy";
|
|
42
45
|
import { taskRunFunctionSchema } from "../../ai/tools/agent/taskRunTool";
|
|
43
|
-
import { prepareTaskWorktree } from "./taskWorktree";
|
|
44
46
|
import {
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
47
|
+
MIMO_MONTH_AGENT_KEY,
|
|
48
|
+
NOLO_DEFAULT_AGENT_ID,
|
|
49
|
+
NOLO_DEFAULT_AGENT_KEY,
|
|
50
|
+
} from "../agentAliases";
|
|
51
|
+
import {
|
|
52
|
+
buildNoloWorkspaceCliToolExecutors,
|
|
53
|
+
buildNoloWorkspaceOpenAiTools,
|
|
54
|
+
filterNoloWorkspaceToolNames,
|
|
55
|
+
parseNoloWorkspaceToolArguments,
|
|
56
|
+
} from "../../agent-runtime/noloWorkspaceTools";
|
|
57
|
+
import { executeCli as defaultExecuteCli, type CliExecuteResult, type CliImageInput } from "../../ai/agent/cliExecutor";
|
|
58
|
+
import { buildCliPrompt } from "../../ai/agent/cliPrompt";
|
|
50
59
|
|
|
51
60
|
type EnvLike = Record<string, string | undefined>;
|
|
52
61
|
type FetchInput = Parameters<typeof fetch>[0];
|
|
53
62
|
type FetchInit = Parameters<typeof fetch>[1];
|
|
63
|
+
type LocalCliExecutor = (
|
|
64
|
+
provider: string,
|
|
65
|
+
prompt: string,
|
|
66
|
+
options: {
|
|
67
|
+
model?: string;
|
|
68
|
+
timeout?: number;
|
|
69
|
+
cwd?: string;
|
|
70
|
+
yolo?: boolean;
|
|
71
|
+
env?: Record<string, string | undefined>;
|
|
72
|
+
imageInputs?: CliImageInput[];
|
|
73
|
+
}
|
|
74
|
+
) => Promise<CliExecuteResult>;
|
|
54
75
|
const TRANSIENT_FETCH_MAX_ATTEMPTS = 8;
|
|
55
76
|
const TRANSIENT_FETCH_RETRY_BASE_DELAY_MS = 250;
|
|
77
|
+
export const BUILTIN_NOLO_AGENT_ID = NOLO_DEFAULT_AGENT_ID;
|
|
78
|
+
export const BUILTIN_NOLO_AGENT_KEY = NOLO_DEFAULT_AGENT_KEY;
|
|
79
|
+
const CLI_DIR = dirname(fileURLToPath(import.meta.url));
|
|
80
|
+
const CLI_ENTRYPOINT = join(CLI_DIR, "..", "index.ts");
|
|
56
81
|
|
|
57
82
|
export type CliLocalRuntimeDb = CliKvDb;
|
|
58
83
|
|
|
@@ -64,10 +89,9 @@ export type CliLocalRuntimeAdapterDeps = {
|
|
|
64
89
|
createId?: () => string;
|
|
65
90
|
fetchImpl?: typeof fetch;
|
|
66
91
|
cwd?: string;
|
|
67
|
-
useCwdAsTaskWorkspaceBase?: boolean;
|
|
68
92
|
output?: { write(chunk: string): unknown };
|
|
69
|
-
prepareTaskWorktree?: typeof prepareTaskWorktree;
|
|
70
93
|
localToolExecutors?: Record<string, (call: any) => Promise<{ content: string; metadata?: Record<string, unknown> }>>;
|
|
94
|
+
executeCli?: LocalCliExecutor;
|
|
71
95
|
sleep?: (ms: number) => Promise<void>;
|
|
72
96
|
loopbackRequest?: (input: FetchInput, init?: FetchInit) => Promise<Response>;
|
|
73
97
|
};
|
|
@@ -84,10 +108,6 @@ function resolveLocalUserId(env: EnvLike) {
|
|
|
84
108
|
return env.NOLO_LOCAL_USER_ID || env.NOLO_USER_ID || "local";
|
|
85
109
|
}
|
|
86
110
|
|
|
87
|
-
function shellModeEnabled(env: EnvLike) {
|
|
88
|
-
return ["worktree", "dangerous", "1", "true"].includes(env.NOLO_LOCAL_SHELL_MODE || "");
|
|
89
|
-
}
|
|
90
|
-
|
|
91
111
|
function parseLocalToolBudgets(env: EnvLike) {
|
|
92
112
|
const raw = env.NOLO_LOCAL_TOOL_BUDGETS?.trim();
|
|
93
113
|
if (!raw) return {};
|
|
@@ -242,36 +262,128 @@ function parseJsonObject(raw: string) {
|
|
|
242
262
|
}
|
|
243
263
|
}
|
|
244
264
|
|
|
265
|
+
function isCliProviderAgent(agentConfig: AgentRuntimeAgentConfig) {
|
|
266
|
+
return Boolean(
|
|
267
|
+
agentConfig.apiSource === "cli" ||
|
|
268
|
+
agentConfig.provider === "cli" ||
|
|
269
|
+
agentConfig.cliProvider
|
|
270
|
+
);
|
|
271
|
+
}
|
|
272
|
+
|
|
273
|
+
function resolveCliProviderName(agentConfig: AgentRuntimeAgentConfig) {
|
|
274
|
+
return (agentConfig.cliProvider || agentConfig.provider || "codex").trim() || "codex";
|
|
275
|
+
}
|
|
276
|
+
|
|
277
|
+
function stringifyRuntimeMessageContent(content: AgentRuntimeChatMessage["content"]) {
|
|
278
|
+
if (typeof content === "string") return content;
|
|
279
|
+
if (Array.isArray(content)) {
|
|
280
|
+
return content
|
|
281
|
+
.map((part) => {
|
|
282
|
+
if (typeof part === "string") return part;
|
|
283
|
+
if (part && typeof part === "object" && "text" in part) {
|
|
284
|
+
return String((part as any).text ?? "");
|
|
285
|
+
}
|
|
286
|
+
return JSON.stringify(part);
|
|
287
|
+
})
|
|
288
|
+
.filter((part) => part.trim())
|
|
289
|
+
.join("\n");
|
|
290
|
+
}
|
|
291
|
+
return content == null ? "" : String(content);
|
|
292
|
+
}
|
|
293
|
+
|
|
294
|
+
function buildPromptForCliProvider(messages: AgentRuntimeChatMessage[]) {
|
|
295
|
+
const systemPrompt = messages
|
|
296
|
+
.filter((message) => message.role === "system")
|
|
297
|
+
.map((message) => stringifyRuntimeMessageContent(message.content).trim())
|
|
298
|
+
.filter(Boolean)
|
|
299
|
+
.join("\n\n");
|
|
300
|
+
const taskPrompt = messages
|
|
301
|
+
.filter((message) => message.role !== "system")
|
|
302
|
+
.map((message) => {
|
|
303
|
+
const content = stringifyRuntimeMessageContent(message.content).trim();
|
|
304
|
+
if (!content) return "";
|
|
305
|
+
return `[${message.role}]\n${content}`;
|
|
306
|
+
})
|
|
307
|
+
.filter(Boolean)
|
|
308
|
+
.join("\n\n");
|
|
309
|
+
return buildCliPrompt(systemPrompt, taskPrompt);
|
|
310
|
+
}
|
|
311
|
+
|
|
312
|
+
function collectCliProviderImageInputs(messages: AgentRuntimeChatMessage[]) {
|
|
313
|
+
const urls: string[] = [];
|
|
314
|
+
for (const message of messages) {
|
|
315
|
+
if (!Array.isArray(message.content)) continue;
|
|
316
|
+
for (const part of message.content) {
|
|
317
|
+
if (
|
|
318
|
+
part &&
|
|
319
|
+
typeof part === "object" &&
|
|
320
|
+
(part as any).type === "image_url" &&
|
|
321
|
+
typeof (part as any).image_url?.url === "string" &&
|
|
322
|
+
(part as any).image_url.url.trim()
|
|
323
|
+
) {
|
|
324
|
+
urls.push((part as any).image_url.url.trim());
|
|
325
|
+
}
|
|
326
|
+
}
|
|
327
|
+
}
|
|
328
|
+
return urls;
|
|
329
|
+
}
|
|
330
|
+
|
|
245
331
|
function logLocalRuntimeDiagnostic(event: string, fields: Record<string, unknown>) {
|
|
332
|
+
if (
|
|
333
|
+
process.env.NOLO_LOCAL_RUNTIME_DEBUG !== "1" &&
|
|
334
|
+
process.env.NOLO_DEBUG !== "1"
|
|
335
|
+
) {
|
|
336
|
+
return;
|
|
337
|
+
}
|
|
246
338
|
console.error(`[nolo-local-runtime] ${event} ${JSON.stringify(fields)}`);
|
|
247
339
|
}
|
|
248
340
|
|
|
249
|
-
function
|
|
341
|
+
function summarizeOpenAiToolNames(tools: Array<Record<string, unknown>>) {
|
|
342
|
+
return tools
|
|
343
|
+
.map((tool) => {
|
|
344
|
+
const fn = tool.function;
|
|
345
|
+
return fn && typeof fn === "object" && "name" in fn && typeof fn.name === "string"
|
|
346
|
+
? fn.name
|
|
347
|
+
: null;
|
|
348
|
+
})
|
|
349
|
+
.filter((name): name is string => Boolean(name));
|
|
350
|
+
}
|
|
351
|
+
|
|
352
|
+
function shouldExposeLocalPlatformTools(agentKey?: string) {
|
|
353
|
+
return agentKey !== MIMO_MONTH_AGENT_KEY;
|
|
354
|
+
}
|
|
355
|
+
|
|
356
|
+
function buildOpenAiTools(args: { agentKey?: string; toolNames?: string[]; env: EnvLike }) {
|
|
250
357
|
const toolset = buildLocalWorkspaceToolsetForEnv(args);
|
|
358
|
+
const exposePlatformTools = shouldExposeLocalPlatformTools(args.agentKey);
|
|
251
359
|
return [
|
|
252
360
|
...buildLocalWorkspaceOpenAiTools({
|
|
253
361
|
toolNames: toolset.toolNames,
|
|
254
362
|
exposeShellTools: toolset.exposeShellTools,
|
|
255
363
|
}),
|
|
256
|
-
...buildServerPlatformOpenAiTools({ toolNames: args.toolNames }),
|
|
364
|
+
...(exposePlatformTools ? buildServerPlatformOpenAiTools({ toolNames: args.toolNames }) : []),
|
|
365
|
+
...(exposePlatformTools ? buildNoloWorkspaceOpenAiTools({ toolNames: args.toolNames }) : []),
|
|
257
366
|
];
|
|
258
367
|
}
|
|
259
368
|
|
|
260
369
|
function buildLocalWorkspaceToolsetForEnv(args: { toolNames?: string[]; env: EnvLike }) {
|
|
370
|
+
void args.env;
|
|
261
371
|
const toolset = buildLocalWorkspaceToolset({
|
|
262
372
|
declaredToolNames: args.toolNames,
|
|
263
|
-
exposeShellTools:
|
|
373
|
+
exposeShellTools: true,
|
|
264
374
|
});
|
|
265
375
|
return toolset;
|
|
266
376
|
}
|
|
267
377
|
|
|
268
378
|
function buildLocalPolicyToolNames(args: { toolNames?: string[]; env: EnvLike }) {
|
|
379
|
+
void args.env;
|
|
269
380
|
return [
|
|
270
381
|
...buildLocalWorkspacePolicyToolNames({
|
|
271
382
|
declaredToolNames: args.toolNames,
|
|
272
|
-
exposeShellTools:
|
|
383
|
+
exposeShellTools: true,
|
|
273
384
|
}),
|
|
274
385
|
...((args.toolNames ?? []).includes("taskRun") ? ["taskRun"] : []),
|
|
386
|
+
...filterNoloWorkspaceToolNames(args.toolNames),
|
|
275
387
|
];
|
|
276
388
|
}
|
|
277
389
|
|
|
@@ -287,13 +399,60 @@ function buildServerPlatformOpenAiTools(args: { toolNames?: string[] }) {
|
|
|
287
399
|
];
|
|
288
400
|
}
|
|
289
401
|
|
|
290
|
-
function
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
402
|
+
function buildCliWorkspaceToolExecutors(args: {
|
|
403
|
+
env: EnvLike;
|
|
404
|
+
cliEntrypoint?: string;
|
|
405
|
+
}) {
|
|
406
|
+
return buildNoloWorkspaceCliToolExecutors({
|
|
407
|
+
cliEntrypoint: args.cliEntrypoint ?? CLI_ENTRYPOINT,
|
|
408
|
+
env: args.env,
|
|
409
|
+
metadataKind: "cliWorkspaceTool",
|
|
410
|
+
});
|
|
411
|
+
}
|
|
412
|
+
|
|
413
|
+
export function isBuiltinNoloAgentRef(ref: unknown) {
|
|
414
|
+
if (typeof ref !== "string") return false;
|
|
415
|
+
const normalized = ref.trim();
|
|
416
|
+
return (
|
|
417
|
+
normalized === BUILTIN_NOLO_AGENT_KEY ||
|
|
418
|
+
normalized === BUILTIN_NOLO_AGENT_ID ||
|
|
419
|
+
normalized.endsWith(`-${BUILTIN_NOLO_AGENT_ID}`)
|
|
420
|
+
);
|
|
421
|
+
}
|
|
422
|
+
|
|
423
|
+
function isBuiltinNoloAgentConfig(agentConfig: AgentRuntimeAgentConfig | null | undefined) {
|
|
424
|
+
const key = agentConfig?.key || agentConfig?.rawRecord?.dbKey || agentConfig?.rawRecord?.agentKey;
|
|
425
|
+
const id = agentConfig?.rawRecord?.id;
|
|
426
|
+
return isBuiltinNoloAgentRef(key) || isBuiltinNoloAgentRef(id);
|
|
427
|
+
}
|
|
428
|
+
|
|
429
|
+
function withResolvedRuntimeToolSurface(
|
|
430
|
+
agentConfig: AgentRuntimeAgentConfig | null,
|
|
431
|
+
env: EnvLike
|
|
432
|
+
) {
|
|
433
|
+
if (!agentConfig) return agentConfig;
|
|
434
|
+
const currentUserId = resolveLocalUserId(env);
|
|
435
|
+
const rawRecord = (agentConfig as any).rawRecord ?? {};
|
|
436
|
+
const ownerId =
|
|
437
|
+
typeof rawRecord.userId === "string" && rawRecord.userId.trim()
|
|
438
|
+
? rawRecord.userId.trim()
|
|
439
|
+
: null;
|
|
440
|
+
const toolSurface = resolveRuntimeToolSurfaceForAgent({
|
|
441
|
+
explicitToolNames: agentConfig.toolNames,
|
|
442
|
+
currentUserId,
|
|
443
|
+
agentOwnerId: ownerId,
|
|
444
|
+
agentKey: rawRecord.dbKey ?? agentConfig.key,
|
|
445
|
+
isPublic: !isBuiltinNoloAgentConfig(agentConfig) && rawRecord.isPublic === true,
|
|
446
|
+
sharingLevel: typeof rawRecord.sharingLevel === "string" ? rawRecord.sharingLevel : null,
|
|
447
|
+
trustedPrivateInvocation: isBuiltinNoloAgentConfig(agentConfig),
|
|
448
|
+
runtimeHost: "cli",
|
|
449
|
+
});
|
|
450
|
+
return {
|
|
451
|
+
...agentConfig,
|
|
452
|
+
toolNames: toolSurface.finalToolNames,
|
|
453
|
+
toolSurface,
|
|
454
|
+
prompt: agentConfig.prompt,
|
|
455
|
+
};
|
|
297
456
|
}
|
|
298
457
|
|
|
299
458
|
function resolveRuntimeServerUrl(env: EnvLike) {
|
|
@@ -320,7 +479,7 @@ function buildServerPlatformToolExecutors(args: {
|
|
|
320
479
|
"Content-Type": "application/json",
|
|
321
480
|
Authorization: `Bearer ${authToken}`,
|
|
322
481
|
},
|
|
323
|
-
body: JSON.stringify(
|
|
482
|
+
body: JSON.stringify(parseNoloWorkspaceToolArguments(call.arguments)),
|
|
324
483
|
});
|
|
325
484
|
const text = await response.text().catch(() => "");
|
|
326
485
|
if (!response.ok) {
|
|
@@ -352,17 +511,13 @@ function buildLocalToolExecutors(args: {
|
|
|
352
511
|
env: args.env,
|
|
353
512
|
fetchImpl: args.fetchImpl,
|
|
354
513
|
}),
|
|
514
|
+
...buildCliWorkspaceToolExecutors({
|
|
515
|
+
env: args.env,
|
|
516
|
+
}),
|
|
355
517
|
...(args.localToolExecutors ?? {}),
|
|
356
518
|
};
|
|
357
519
|
}
|
|
358
520
|
|
|
359
|
-
function readLocalWorkspaceMode(agentConfig: AgentRuntimeAgentConfig | null) {
|
|
360
|
-
if (agentConfig?.localWorkspaceMode === "task-worktree") return "task-worktree";
|
|
361
|
-
const runtimeBinding = agentConfig?.runtimeBinding;
|
|
362
|
-
const value = runtimeBinding?.localWorkspaceMode ?? runtimeBinding?.workspaceMode;
|
|
363
|
-
return value === "task-worktree" ? "task-worktree" : "current";
|
|
364
|
-
}
|
|
365
|
-
|
|
366
521
|
async function resolveStore(deps: CliLocalRuntimeAdapterDeps) {
|
|
367
522
|
if (deps.store) return deps.store;
|
|
368
523
|
return createCliHybridRecordStore({
|
|
@@ -437,51 +592,28 @@ export function createCliLocalRuntimeAdapter(
|
|
|
437
592
|
const localToolBudgets = parseLocalToolBudgets(deps.env);
|
|
438
593
|
const localToolUsage = new Map<string, number>();
|
|
439
594
|
let activeAgentToolNames: string[] = [];
|
|
440
|
-
|
|
441
|
-
deps.useCwdAsTaskWorkspaceBase
|
|
442
|
-
? { defaultCwd: deps.cwd }
|
|
443
|
-
: { cwd: deps.cwd }
|
|
444
|
-
);
|
|
595
|
+
const workspaceRoot = deps.cwd ?? process.cwd();
|
|
445
596
|
let runtimeToolExecutionLimits: ReturnType<typeof resolveLocalWorkspaceExecutorOptionsFromPolicy> = {};
|
|
446
597
|
let localToolExecutors = buildLocalToolExecutors({
|
|
447
|
-
workspaceRoot
|
|
598
|
+
workspaceRoot,
|
|
448
599
|
env: deps.env,
|
|
449
600
|
fetchImpl,
|
|
450
601
|
localToolExecutors: deps.localToolExecutors,
|
|
451
602
|
...runtimeToolExecutionLimits,
|
|
452
603
|
});
|
|
453
604
|
|
|
454
|
-
async function activateAgentWorkspaceSession(args: {
|
|
455
|
-
agentRef: string;
|
|
456
|
-
agentConfig: AgentRuntimeAgentConfig | null;
|
|
457
|
-
}) {
|
|
458
|
-
const previousWorkspaceRoot = workspaceSession.workspaceRoot;
|
|
459
|
-
workspaceSession = await activateWorkspaceSession(workspaceSession, {
|
|
460
|
-
agentKey: args.agentConfig?.key ?? args.agentRef,
|
|
461
|
-
mode: readLocalWorkspaceMode(args.agentConfig),
|
|
462
|
-
env: deps.env,
|
|
463
|
-
prepareTaskWorkspace: deps.prepareTaskWorktree,
|
|
464
|
-
});
|
|
465
|
-
if (workspaceSession.workspaceRoot === previousWorkspaceRoot) return;
|
|
466
|
-
localToolExecutors = buildLocalToolExecutors({
|
|
467
|
-
workspaceRoot: workspaceSession.workspaceRoot,
|
|
468
|
-
env: deps.env,
|
|
469
|
-
fetchImpl,
|
|
470
|
-
localToolExecutors: deps.localToolExecutors,
|
|
471
|
-
...runtimeToolExecutionLimits,
|
|
472
|
-
});
|
|
473
|
-
deps.output?.write(formatWorkspaceSessionActivation(workspaceSession));
|
|
474
|
-
}
|
|
475
|
-
|
|
476
605
|
return {
|
|
477
606
|
host: "cli",
|
|
478
607
|
capabilities: ["leveldb-agent-config", "local-provider", "leveldb-persistence", "local-tools"],
|
|
479
608
|
loadAgentConfig: async (agentRef) => {
|
|
480
|
-
const agentConfig =
|
|
481
|
-
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
|
|
609
|
+
const agentConfig = withResolvedRuntimeToolSurface(
|
|
610
|
+
await readAgentFromStore({
|
|
611
|
+
agentRef,
|
|
612
|
+
store: await resolveStore(deps),
|
|
613
|
+
userId,
|
|
614
|
+
}),
|
|
615
|
+
deps.env
|
|
616
|
+
);
|
|
485
617
|
const requestedToolNames = agentConfig
|
|
486
618
|
? resolveRequestedRuntimeToolNames({ agentConfig })
|
|
487
619
|
: [];
|
|
@@ -492,9 +624,8 @@ export function createCliLocalRuntimeAdapter(
|
|
|
492
624
|
runtimeToolExecutionLimits = resolveLocalWorkspaceExecutorOptionsFromPolicy(
|
|
493
625
|
resolveCurrentRunRuntimeToolPolicy(agentConfig),
|
|
494
626
|
);
|
|
495
|
-
await activateAgentWorkspaceSession({ agentRef, agentConfig });
|
|
496
627
|
localToolExecutors = buildLocalToolExecutors({
|
|
497
|
-
workspaceRoot
|
|
628
|
+
workspaceRoot,
|
|
498
629
|
env: deps.env,
|
|
499
630
|
fetchImpl,
|
|
500
631
|
localToolExecutors: deps.localToolExecutors,
|
|
@@ -512,9 +643,53 @@ export function createCliLocalRuntimeAdapter(
|
|
|
512
643
|
userId,
|
|
513
644
|
now,
|
|
514
645
|
createId,
|
|
515
|
-
cwd:
|
|
646
|
+
cwd: workspaceRoot,
|
|
516
647
|
}),
|
|
517
648
|
resolveProvider: async (agentConfig) => {
|
|
649
|
+
if (isCliProviderAgent(agentConfig)) {
|
|
650
|
+
const provider = resolveCliProviderName(agentConfig);
|
|
651
|
+
logLocalRuntimeDiagnostic("provider.selected", {
|
|
652
|
+
agentKey: agentConfig.key,
|
|
653
|
+
transport: "local-cli",
|
|
654
|
+
apiSource: agentConfig.apiSource ?? null,
|
|
655
|
+
provider,
|
|
656
|
+
model: agentConfig.model ?? null,
|
|
657
|
+
cwd: workspaceRoot,
|
|
658
|
+
});
|
|
659
|
+
return {
|
|
660
|
+
model: agentConfig.model || provider,
|
|
661
|
+
complete: async (messages, options) => {
|
|
662
|
+
const executeCli = deps.executeCli ?? (defaultExecuteCli as LocalCliExecutor);
|
|
663
|
+
const imageUrls = collectCliProviderImageInputs(messages);
|
|
664
|
+
const imageInputs: CliImageInput[] | undefined =
|
|
665
|
+
imageUrls.length > 0
|
|
666
|
+
? imageUrls.map((url) => ({ source: url }))
|
|
667
|
+
: undefined;
|
|
668
|
+
const prompt = buildPromptForCliProvider(messages);
|
|
669
|
+
try {
|
|
670
|
+
const result = await executeCli(provider, prompt, {
|
|
671
|
+
...(agentConfig.model ? { model: agentConfig.model } : {}),
|
|
672
|
+
...(options?.timeoutMs ? { timeout: options.timeoutMs } : {}),
|
|
673
|
+
cwd: workspaceRoot,
|
|
674
|
+
yolo: true,
|
|
675
|
+
env: deps.env,
|
|
676
|
+
...(imageInputs ? { imageInputs } : {}),
|
|
677
|
+
});
|
|
678
|
+
return {
|
|
679
|
+
content: result.text,
|
|
680
|
+
model: agentConfig.model || provider,
|
|
681
|
+
raw: result.raw,
|
|
682
|
+
};
|
|
683
|
+
} catch (error) {
|
|
684
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
685
|
+
throw new Error(
|
|
686
|
+
`Local CLI provider "${provider}" is unavailable or failed: ${message}`
|
|
687
|
+
);
|
|
688
|
+
}
|
|
689
|
+
},
|
|
690
|
+
};
|
|
691
|
+
}
|
|
692
|
+
|
|
518
693
|
if (shouldUsePlatformChatProvider(deps.env, agentConfig)) {
|
|
519
694
|
const providerConfig = resolvePlatformChatProviderConfig({
|
|
520
695
|
agentConfig,
|
|
@@ -541,6 +716,7 @@ export function createCliLocalRuntimeAdapter(
|
|
|
541
716
|
agentConfig,
|
|
542
717
|
});
|
|
543
718
|
const tools = buildOpenAiTools({
|
|
719
|
+
agentKey: agentConfig.key,
|
|
544
720
|
toolNames: requestedToolNames,
|
|
545
721
|
env: deps.env,
|
|
546
722
|
});
|
|
@@ -558,6 +734,8 @@ export function createCliLocalRuntimeAdapter(
|
|
|
558
734
|
model: providerConfig.model,
|
|
559
735
|
messageCount: messages.length,
|
|
560
736
|
toolCount: tools.length,
|
|
737
|
+
requestedToolNames,
|
|
738
|
+
openAiToolNames: summarizeOpenAiToolNames(tools),
|
|
561
739
|
timeoutMs: options?.timeoutMs ?? null,
|
|
562
740
|
});
|
|
563
741
|
const res = await fetchWithTransientRetry(fetchImpl, request.url, {
|
|
@@ -611,6 +789,7 @@ export function createCliLocalRuntimeAdapter(
|
|
|
611
789
|
agentConfig,
|
|
612
790
|
});
|
|
613
791
|
const tools = buildOpenAiTools({
|
|
792
|
+
agentKey: agentConfig.key,
|
|
614
793
|
toolNames: requestedToolNames,
|
|
615
794
|
env: deps.env,
|
|
616
795
|
});
|
|
@@ -627,6 +806,8 @@ export function createCliLocalRuntimeAdapter(
|
|
|
627
806
|
model: providerConfig.model,
|
|
628
807
|
messageCount: messages.length,
|
|
629
808
|
toolCount: tools.length,
|
|
809
|
+
requestedToolNames,
|
|
810
|
+
openAiToolNames: summarizeOpenAiToolNames(tools),
|
|
630
811
|
timeoutMs: options?.timeoutMs ?? null,
|
|
631
812
|
});
|
|
632
813
|
const res = await fetchWithTransientRetry(fetchImpl, request.url, {
|
|
@@ -672,8 +853,8 @@ export function createCliLocalRuntimeAdapter(
|
|
|
672
853
|
...result,
|
|
673
854
|
metadata: {
|
|
674
855
|
...(result.metadata ?? {}),
|
|
675
|
-
workspaceRoot
|
|
676
|
-
workspaceKind:
|
|
856
|
+
workspaceRoot,
|
|
857
|
+
workspaceKind: "current",
|
|
677
858
|
},
|
|
678
859
|
};
|
|
679
860
|
},
|
package/cli/commandRegistry.ts
CHANGED
|
@@ -69,8 +69,8 @@ export function renderHelpText() {
|
|
|
69
69
|
" nolo space read 01KKY77TT0DA9NY7TNW3R7255N --content-key page-user-id --brief",
|
|
70
70
|
" nolo space delete --name-prefix rn_owner_verify_0504 --yes",
|
|
71
71
|
" nolo table query --table 01ABCXYZ",
|
|
72
|
-
' nolo table query --table meta-
|
|
73
|
-
' nolo table update-row --table meta-
|
|
72
|
+
' nolo table query --table meta-0e95801d90-NOLOTASKBOARD --columns \'["title","status","owner","priority","codeStatus"]\' --no-base-fields --output items',
|
|
73
|
+
' nolo table update-row --table meta-0e95801d90-NOLOTASKBOARD --row 01ROWID --changes \'{"status":"已完成"}\'',
|
|
74
74
|
" nolo task-run read-context --row-dbkey row-user-table-row",
|
|
75
75
|
" nolo llama status",
|
|
76
76
|
];
|
|
@@ -32,7 +32,6 @@ export function resolveConnectorRunCwd(args: {
|
|
|
32
32
|
const explicit =
|
|
33
33
|
args.env?.NOLO_CONNECTOR_WORKDIR ||
|
|
34
34
|
args.env?.NOLO_AGENT_WORKDIR ||
|
|
35
|
-
args.env?.NOLO_LOCAL_WORKTREE ||
|
|
36
35
|
"";
|
|
37
36
|
const candidate = explicit || args.policy.writableRoots[0] || args.fallbackCwd || process.cwd();
|
|
38
37
|
const cwd = normalizePath(candidate);
|