@actalk/inkos-core 1.5.0 → 1.6.1-canary.49.1
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/dist/agent/agent-session.d.ts +4 -0
- package/dist/agent/agent-session.d.ts.map +1 -1
- package/dist/agent/agent-session.js +78 -5
- package/dist/agent/agent-session.js.map +1 -1
- package/dist/agent/agent-system-prompt.d.ts +2 -0
- package/dist/agent/agent-system-prompt.d.ts.map +1 -1
- package/dist/agent/agent-system-prompt.js +181 -16
- package/dist/agent/agent-system-prompt.js.map +1 -1
- package/dist/agent/agent-tools.d.ts +97 -1
- package/dist/agent/agent-tools.d.ts.map +1 -1
- package/dist/agent/agent-tools.js +434 -3
- package/dist/agent/agent-tools.js.map +1 -1
- package/dist/agent/film-authoring-tools.d.ts +89 -0
- package/dist/agent/film-authoring-tools.d.ts.map +1 -0
- package/dist/agent/film-authoring-tools.js +336 -0
- package/dist/agent/film-authoring-tools.js.map +1 -0
- package/dist/agent/index.d.ts +2 -1
- package/dist/agent/index.d.ts.map +1 -1
- package/dist/agent/index.js +2 -1
- package/dist/agent/index.js.map +1 -1
- package/dist/agent/llm-stub.d.ts +19 -0
- package/dist/agent/llm-stub.d.ts.map +1 -0
- package/dist/agent/llm-stub.js +134 -0
- package/dist/agent/llm-stub.js.map +1 -0
- package/dist/agents/composer.d.ts.map +1 -1
- package/dist/agents/composer.js +24 -12
- package/dist/agents/composer.js.map +1 -1
- package/dist/agents/researcher.d.ts +38 -0
- package/dist/agents/researcher.d.ts.map +1 -0
- package/dist/agents/researcher.js +164 -0
- package/dist/agents/researcher.js.map +1 -0
- package/dist/agents/script-storyboard.d.ts +51 -0
- package/dist/agents/script-storyboard.d.ts.map +1 -0
- package/dist/agents/script-storyboard.js +368 -0
- package/dist/agents/script-storyboard.js.map +1 -0
- package/dist/index.d.ts +23 -2
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +24 -2
- package/dist/index.js.map +1 -1
- package/dist/interaction/action-envelope.d.ts +669 -1
- package/dist/interaction/action-envelope.d.ts.map +1 -1
- package/dist/interaction/action-envelope.js +87 -0
- package/dist/interaction/action-envelope.js.map +1 -1
- package/dist/interaction/edit-controller.d.ts.map +1 -1
- package/dist/interaction/edit-controller.js +91 -1
- package/dist/interaction/edit-controller.js.map +1 -1
- package/dist/interaction/intents.d.ts +2 -2
- package/dist/interaction/project-control.d.ts +1 -1
- package/dist/interaction/session-transcript-schema.d.ts +22 -22
- package/dist/interaction/session.d.ts +14 -14
- package/dist/interaction/session.d.ts.map +1 -1
- package/dist/interaction/session.js +1 -1
- package/dist/interaction/session.js.map +1 -1
- package/dist/interactive-film/authoring-generate.d.ts +4 -0
- package/dist/interactive-film/authoring-generate.d.ts.map +1 -0
- package/dist/interactive-film/authoring-generate.js +16 -0
- package/dist/interactive-film/authoring-generate.js.map +1 -0
- package/dist/interactive-film/authoring-store.d.ts +35 -0
- package/dist/interactive-film/authoring-store.d.ts.map +1 -0
- package/dist/interactive-film/authoring-store.js +114 -0
- package/dist/interactive-film/authoring-store.js.map +1 -0
- package/dist/interactive-film/authoring-tools.d.ts +9 -0
- package/dist/interactive-film/authoring-tools.d.ts.map +1 -0
- package/dist/interactive-film/authoring-tools.js +19 -0
- package/dist/interactive-film/authoring-tools.js.map +1 -0
- package/dist/interactive-film/delta.d.ts +591 -0
- package/dist/interactive-film/delta.d.ts.map +1 -0
- package/dist/interactive-film/delta.js +54 -0
- package/dist/interactive-film/delta.js.map +1 -0
- package/dist/interactive-film/emotion.d.ts +20 -0
- package/dist/interactive-film/emotion.d.ts.map +1 -0
- package/dist/interactive-film/emotion.js +57 -0
- package/dist/interactive-film/emotion.js.map +1 -0
- package/dist/interactive-film/evaluator.d.ts +7 -0
- package/dist/interactive-film/evaluator.d.ts.map +1 -0
- package/dist/interactive-film/evaluator.js +40 -0
- package/dist/interactive-film/evaluator.js.map +1 -0
- package/dist/interactive-film/export-html.d.ts +6 -0
- package/dist/interactive-film/export-html.d.ts.map +1 -0
- package/dist/interactive-film/export-html.js +84 -0
- package/dist/interactive-film/export-html.js.map +1 -0
- package/dist/interactive-film/export-ink.d.ts +3 -0
- package/dist/interactive-film/export-ink.d.ts.map +1 -0
- package/dist/interactive-film/export-ink.js +51 -0
- package/dist/interactive-film/export-ink.js.map +1 -0
- package/dist/interactive-film/film-context.d.ts +4 -0
- package/dist/interactive-film/film-context.d.ts.map +1 -0
- package/dist/interactive-film/film-context.js +30 -0
- package/dist/interactive-film/film-context.js.map +1 -0
- package/dist/interactive-film/generate.d.ts +13 -0
- package/dist/interactive-film/generate.d.ts.map +1 -0
- package/dist/interactive-film/generate.js +32 -0
- package/dist/interactive-film/generate.js.map +1 -0
- package/dist/interactive-film/graph-schema.d.ts +819 -0
- package/dist/interactive-film/graph-schema.d.ts.map +1 -0
- package/dist/interactive-film/graph-schema.js +84 -0
- package/dist/interactive-film/graph-schema.js.map +1 -0
- package/dist/interactive-film/graph-store.d.ts +5 -0
- package/dist/interactive-film/graph-store.d.ts.map +1 -0
- package/dist/interactive-film/graph-store.js +24 -0
- package/dist/interactive-film/graph-store.js.map +1 -0
- package/dist/interactive-film/memory-link.d.ts +9 -0
- package/dist/interactive-film/memory-link.d.ts.map +1 -0
- package/dist/interactive-film/memory-link.js +15 -0
- package/dist/interactive-film/memory-link.js.map +1 -0
- package/dist/interactive-film/node-image.d.ts +29 -0
- package/dist/interactive-film/node-image.d.ts.map +1 -0
- package/dist/interactive-film/node-image.js +52 -0
- package/dist/interactive-film/node-image.js.map +1 -0
- package/dist/interactive-film/paths.d.ts +14 -0
- package/dist/interactive-film/paths.d.ts.map +1 -0
- package/dist/interactive-film/paths.js +60 -0
- package/dist/interactive-film/paths.js.map +1 -0
- package/dist/interactive-film/validation.d.ts +14 -0
- package/dist/interactive-film/validation.d.ts.map +1 -0
- package/dist/interactive-film/validation.js +292 -0
- package/dist/interactive-film/validation.js.map +1 -0
- package/dist/llm/provider.d.ts.map +1 -1
- package/dist/llm/provider.js +53 -16
- package/dist/llm/provider.js.map +1 -1
- package/dist/models/book.d.ts +13 -0
- package/dist/models/book.d.ts.map +1 -1
- package/dist/models/book.js +3 -0
- package/dist/models/book.js.map +1 -1
- package/dist/models/input-governance.d.ts +14 -5
- package/dist/models/input-governance.d.ts.map +1 -1
- package/dist/models/input-governance.js +3 -0
- package/dist/models/input-governance.js.map +1 -1
- package/dist/models/project.d.ts +63 -10
- package/dist/models/project.d.ts.map +1 -1
- package/dist/models/project.js +11 -0
- package/dist/models/project.js.map +1 -1
- package/dist/pipeline/runner.js +1 -1
- package/dist/pipeline/runner.js.map +1 -1
- package/dist/pipeline/script-storyboard-runner.d.ts +127 -0
- package/dist/pipeline/script-storyboard-runner.d.ts.map +1 -0
- package/dist/pipeline/script-storyboard-runner.js +446 -0
- package/dist/pipeline/script-storyboard-runner.js.map +1 -0
- package/dist/play/play-agents.d.ts.map +1 -1
- package/dist/play/play-agents.js +5 -2
- package/dist/play/play-agents.js.map +1 -1
- package/dist/play/play-store.d.ts +2 -2
- package/dist/skills/builtin-prompts.d.ts +10 -0
- package/dist/skills/builtin-prompts.d.ts.map +1 -0
- package/dist/skills/builtin-prompts.js +152 -0
- package/dist/skills/builtin-prompts.js.map +1 -0
- package/dist/skills/builtin.d.ts +3 -0
- package/dist/skills/builtin.d.ts.map +1 -0
- package/dist/skills/builtin.js +252 -0
- package/dist/skills/builtin.js.map +1 -0
- package/dist/skills/context-planner.d.ts +17 -0
- package/dist/skills/context-planner.d.ts.map +1 -0
- package/dist/skills/context-planner.js +48 -0
- package/dist/skills/context-planner.js.map +1 -0
- package/dist/skills/external-loader.d.ts +20 -0
- package/dist/skills/external-loader.d.ts.map +1 -0
- package/dist/skills/external-loader.js +126 -0
- package/dist/skills/external-loader.js.map +1 -0
- package/dist/skills/index.d.ts +8 -0
- package/dist/skills/index.d.ts.map +1 -0
- package/dist/skills/index.js +8 -0
- package/dist/skills/index.js.map +1 -0
- package/dist/skills/prompt-pack.d.ts +33 -0
- package/dist/skills/prompt-pack.d.ts.map +1 -0
- package/dist/skills/prompt-pack.js +82 -0
- package/dist/skills/prompt-pack.js.map +1 -0
- package/dist/skills/registry.d.ts +6 -0
- package/dist/skills/registry.d.ts.map +1 -0
- package/dist/skills/registry.js +101 -0
- package/dist/skills/registry.js.map +1 -0
- package/dist/skills/types.d.ts +146 -0
- package/dist/skills/types.d.ts.map +1 -0
- package/dist/skills/types.js +32 -0
- package/dist/skills/types.js.map +1 -0
- package/dist/state/manager.d.ts +8 -2
- package/dist/state/manager.d.ts.map +1 -1
- package/dist/state/manager.js +58 -5
- package/dist/state/manager.js.map +1 -1
- package/dist/utils/context-assembly.d.ts +3 -0
- package/dist/utils/context-assembly.d.ts.map +1 -1
- package/dist/utils/context-assembly.js +3 -0
- package/dist/utils/context-assembly.js.map +1 -1
- package/dist/utils/web-search.d.ts +6 -1
- package/dist/utils/web-search.d.ts.map +1 -1
- package/dist/utils/web-search.js +8 -4
- package/dist/utils/web-search.js.map +1 -1
- package/package.json +14 -3
|
@@ -2,7 +2,7 @@ import { Type } from "@mariozechner/pi-ai";
|
|
|
2
2
|
import { ArchitectIncompleteFoundationError } from "../agents/architect.js";
|
|
3
3
|
import { defaultChapterLength } from "../utils/length-metrics.js";
|
|
4
4
|
import { inferLanguage } from "../utils/language.js";
|
|
5
|
-
import { readFile, writeFile, readdir, stat } from "node:fs/promises";
|
|
5
|
+
import { mkdir, readFile, writeFile, readdir, stat } from "node:fs/promises";
|
|
6
6
|
import { isAbsolute, join, resolve } from "node:path";
|
|
7
7
|
import { StateManager } from "../state/manager.js";
|
|
8
8
|
import { assertSafeTruthFileName, createInteractionToolsFromDeps } from "../interaction/project-tools.js";
|
|
@@ -11,10 +11,14 @@ import { assertSafeBookId, deriveBookIdFromTitle } from "../utils/book-id.js";
|
|
|
11
11
|
import { safeChildPath } from "../utils/path-safety.js";
|
|
12
12
|
import { normalizePlatformId, normalizePlatformOrOther } from "../models/book.js";
|
|
13
13
|
import { generateShortFictionCover, runShortFictionProduction } from "../pipeline/short-fiction-runner.js";
|
|
14
|
+
import { runInteractiveFilmCreation, runScriptCreation, runStoryboardCreation } from "../pipeline/script-storyboard-runner.js";
|
|
15
|
+
import { runResearchReport } from "../agents/researcher.js";
|
|
14
16
|
import { createPlayDB } from "../play/play-db-factory.js";
|
|
15
17
|
import { PlayRunner } from "../play/play-runner.js";
|
|
16
18
|
import { PlayStore } from "../play/play-store.js";
|
|
17
19
|
import { ActionPayloadSchema, isUsablePlayInitialScene } from "../interaction/action-envelope.js";
|
|
20
|
+
import { ResearchSearchConfigSchema } from "../models/project.js";
|
|
21
|
+
import { searchWeb } from "../utils/web-search.js";
|
|
18
22
|
function textResult(text, details) {
|
|
19
23
|
return { content: [{ type: "text", text }], details: details };
|
|
20
24
|
}
|
|
@@ -89,6 +93,12 @@ const ProposeActionParams = Type.Object({
|
|
|
89
93
|
Type.Literal("continuation_import"),
|
|
90
94
|
Type.Literal("spinoff_create"),
|
|
91
95
|
Type.Literal("style_imitation"),
|
|
96
|
+
Type.Literal("script_create"),
|
|
97
|
+
Type.Literal("storyboard_create"),
|
|
98
|
+
Type.Literal("interactive_film_create"),
|
|
99
|
+
Type.Literal("draft_structure"),
|
|
100
|
+
Type.Literal("connect_choice"),
|
|
101
|
+
Type.Literal("remove_node"),
|
|
92
102
|
], {
|
|
93
103
|
description: "The production or assisted Studio workflow the user appears to want, but which needs explicit confirmation from general chat.",
|
|
94
104
|
}),
|
|
@@ -172,12 +182,65 @@ const ProposeActionParams = Type.Object({
|
|
|
172
182
|
coverPrompt: Type.Optional(Type.String({ description: "Confirmed visual direction." })),
|
|
173
183
|
outputDir: Type.Optional(Type.String({ description: "Confirmed output directory." })),
|
|
174
184
|
}, { description: "Structured execution args for action=generate_cover." })),
|
|
185
|
+
scriptCreate: Type.Optional(Type.Object({
|
|
186
|
+
title: Type.Optional(Type.String({ description: "Confirmed script project title." })),
|
|
187
|
+
sourceKind: Type.Optional(Type.String({ description: "Source type, e.g. novel excerpt, original idea, outline, existing script." })),
|
|
188
|
+
targetFormat: Type.Optional(Type.Union([
|
|
189
|
+
Type.Literal("vertical_short_drama"),
|
|
190
|
+
Type.Literal("screenplay"),
|
|
191
|
+
Type.Literal("audio_drama"),
|
|
192
|
+
Type.Literal("interactive_script"),
|
|
193
|
+
Type.Literal("general_script"),
|
|
194
|
+
], { description: "Confirmed script output format." })),
|
|
195
|
+
sourceText: Type.Optional(Type.String({ description: "User-provided source text. For long sources, prefer sourcePath instead of summarizing." })),
|
|
196
|
+
sourcePath: Type.Optional(Type.String({ description: "Optional project-relative source file path." })),
|
|
197
|
+
requirements: Type.Optional(Type.String({ description: "Confirmed script format, production constraints, tone, episode structure, or user preferences." })),
|
|
198
|
+
episodeCount: Type.Optional(Type.Number({ description: "Optional target episode/segment count." })),
|
|
199
|
+
episodeDuration: Type.Optional(Type.String({ description: "Optional per-episode/per-segment duration." })),
|
|
200
|
+
projectId: Type.Optional(Type.String({ description: "Optional output id under dramas/." })),
|
|
201
|
+
outDir: Type.Optional(Type.String({ description: "Optional project-relative output directory. Default dramas/." })),
|
|
202
|
+
}, { description: "Structured execution args for action=script_create." })),
|
|
203
|
+
storyboardCreate: Type.Optional(Type.Object({
|
|
204
|
+
title: Type.Optional(Type.String({ description: "Confirmed storyboard project title." })),
|
|
205
|
+
sourceKind: Type.Optional(Type.String({ description: "Source type, e.g. script, novel excerpt, idea, scene list." })),
|
|
206
|
+
sourceText: Type.Optional(Type.String({ description: "User-provided source text. For long sources, prefer sourcePath instead of summarizing." })),
|
|
207
|
+
sourcePath: Type.Optional(Type.String({ description: "Optional project-relative source file path." })),
|
|
208
|
+
requirements: Type.Optional(Type.String({ description: "Confirmed shot/storyboard requirements." })),
|
|
209
|
+
visualStyle: Type.Optional(Type.String({ description: "Confirmed visual style, if the user specified one." })),
|
|
210
|
+
aspectRatio: Type.Optional(Type.String({ description: "Confirmed aspect ratio, e.g. 9:16, 16:9, 1:1." })),
|
|
211
|
+
granularity: Type.Optional(Type.String({ description: "Confirmed storyboard granularity." })),
|
|
212
|
+
maxShots: Type.Optional(Type.Number({ description: "Optional max shot count." })),
|
|
213
|
+
projectId: Type.Optional(Type.String({ description: "Optional output id under storyboards/." })),
|
|
214
|
+
outDir: Type.Optional(Type.String({ description: "Optional project-relative output directory. Default storyboards/." })),
|
|
215
|
+
}, { description: "Structured execution args for action=storyboard_create." })),
|
|
216
|
+
interactiveFilmCreate: Type.Optional(Type.Object({
|
|
217
|
+
title: Type.Optional(Type.String({ description: "Confirmed interactive-film project title." })),
|
|
218
|
+
sourceKind: Type.Optional(Type.String({ description: "Source type, e.g. novel excerpt, script, outline, original idea." })),
|
|
219
|
+
sourceText: Type.Optional(Type.String({ description: "User-provided source text. For long sources, prefer sourcePath instead of summarizing." })),
|
|
220
|
+
sourcePath: Type.Optional(Type.String({ description: "Optional project-relative source file path." })),
|
|
221
|
+
requirements: Type.Optional(Type.String({ description: "Confirmed branching, variable/flag, ending, production, visual, or market requirements." })),
|
|
222
|
+
targetAudience: Type.Optional(Type.String({ description: "Confirmed target audience or market." })),
|
|
223
|
+
episodeCount: Type.Optional(Type.Number({ description: "Optional target episode/segment count." })),
|
|
224
|
+
episodeDuration: Type.Optional(Type.String({ description: "Optional per-episode/per-segment duration." })),
|
|
225
|
+
budget: Type.Optional(Type.String({ description: "Optional budget or production constraints." })),
|
|
226
|
+
referenceMode: Type.Optional(Type.String({ description: "Optional reference mode, e.g. 盛世天下-style multi-ending interactive drama." })),
|
|
227
|
+
projectId: Type.Optional(Type.String({ description: "Optional output id under interactive-films/." })),
|
|
228
|
+
outDir: Type.Optional(Type.String({ description: "Optional project-relative output directory. Default interactive-films/." })),
|
|
229
|
+
}, { description: "Structured execution args for action=interactive_film_create." })),
|
|
175
230
|
});
|
|
176
231
|
function proposedActionSessionKind(action) {
|
|
177
232
|
if (action === "create_book")
|
|
178
233
|
return "book-create";
|
|
179
234
|
if (action === "play_start")
|
|
180
235
|
return "play";
|
|
236
|
+
if (action === "script_create")
|
|
237
|
+
return "script";
|
|
238
|
+
if (action === "storyboard_create")
|
|
239
|
+
return "storyboard";
|
|
240
|
+
if (action === "interactive_film_create")
|
|
241
|
+
return "interactive-film";
|
|
242
|
+
if (action === "draft_structure" || action === "connect_choice" || action === "remove_node")
|
|
243
|
+
return "interactive-film-authoring";
|
|
181
244
|
if (action === "fanfic_init" || action === "continuation_import" || action === "spinoff_create" || action === "style_imitation")
|
|
182
245
|
return "chat";
|
|
183
246
|
return "short";
|
|
@@ -211,6 +274,18 @@ function proposedActionFallbackTitle(action, isZh) {
|
|
|
211
274
|
return isZh ? "打开番外创作" : "Open side-story workflow";
|
|
212
275
|
case "style_imitation":
|
|
213
276
|
return isZh ? "打开仿写/文风分析" : "Open style imitation";
|
|
277
|
+
case "script_create":
|
|
278
|
+
return isZh ? "创建剧本" : "Create script";
|
|
279
|
+
case "storyboard_create":
|
|
280
|
+
return isZh ? "创建分镜" : "Create storyboard";
|
|
281
|
+
case "interactive_film_create":
|
|
282
|
+
return isZh ? "创建互动影游" : "Create interactive film";
|
|
283
|
+
case "draft_structure":
|
|
284
|
+
return isZh ? "生成故事结构" : "Draft story structure";
|
|
285
|
+
case "connect_choice":
|
|
286
|
+
return isZh ? "连接选项" : "Connect choice";
|
|
287
|
+
case "remove_node":
|
|
288
|
+
return isZh ? "删除节点" : "Remove node";
|
|
214
289
|
}
|
|
215
290
|
}
|
|
216
291
|
function proposedActionFallbackSummary(action, isZh) {
|
|
@@ -241,6 +316,11 @@ function compactObject(value) {
|
|
|
241
316
|
out[key] = items;
|
|
242
317
|
continue;
|
|
243
318
|
}
|
|
319
|
+
if (typeof raw === "number") {
|
|
320
|
+
if (Number.isFinite(raw) && raw > 0)
|
|
321
|
+
out[key] = raw;
|
|
322
|
+
continue;
|
|
323
|
+
}
|
|
244
324
|
if (raw !== undefined && raw !== null) {
|
|
245
325
|
out[key] = raw;
|
|
246
326
|
}
|
|
@@ -295,6 +375,21 @@ function proposedActionPayload(params) {
|
|
|
295
375
|
if (generateCover)
|
|
296
376
|
payload.generateCover = generateCover;
|
|
297
377
|
}
|
|
378
|
+
if (params.action === "script_create") {
|
|
379
|
+
const scriptCreate = compactObject(params.scriptCreate);
|
|
380
|
+
if (scriptCreate)
|
|
381
|
+
payload.scriptCreate = scriptCreate;
|
|
382
|
+
}
|
|
383
|
+
if (params.action === "storyboard_create") {
|
|
384
|
+
const storyboardCreate = compactObject(params.storyboardCreate);
|
|
385
|
+
if (storyboardCreate)
|
|
386
|
+
payload.storyboardCreate = storyboardCreate;
|
|
387
|
+
}
|
|
388
|
+
if (params.action === "interactive_film_create") {
|
|
389
|
+
const interactiveFilmCreate = compactObject(params.interactiveFilmCreate);
|
|
390
|
+
if (interactiveFilmCreate)
|
|
391
|
+
payload.interactiveFilmCreate = interactiveFilmCreate;
|
|
392
|
+
}
|
|
298
393
|
return Object.keys(payload).length > 0 ? payload : undefined;
|
|
299
394
|
}
|
|
300
395
|
function validateProposedActionPayload(payload) {
|
|
@@ -323,6 +418,18 @@ function assertExecutableProposedAction(params, payload) {
|
|
|
323
418
|
}
|
|
324
419
|
if (params.action === "generate_cover") {
|
|
325
420
|
requireProposedText(payload?.generateCover?.title, "generateCover.title");
|
|
421
|
+
return;
|
|
422
|
+
}
|
|
423
|
+
if (params.action === "script_create") {
|
|
424
|
+
requireProposedText(payload?.scriptCreate?.title, "scriptCreate.title");
|
|
425
|
+
return;
|
|
426
|
+
}
|
|
427
|
+
if (params.action === "storyboard_create") {
|
|
428
|
+
requireProposedText(payload?.storyboardCreate?.title, "storyboardCreate.title");
|
|
429
|
+
return;
|
|
430
|
+
}
|
|
431
|
+
if (params.action === "interactive_film_create") {
|
|
432
|
+
requireProposedText(payload?.interactiveFilmCreate?.title, "interactiveFilmCreate.title");
|
|
326
433
|
}
|
|
327
434
|
}
|
|
328
435
|
export function createProposeActionTool(language = "zh", options = {}) {
|
|
@@ -620,7 +727,97 @@ export function createSubAgentTool(pipeline, activeBookId, projectRoot, options
|
|
|
620
727
|
};
|
|
621
728
|
}
|
|
622
729
|
// ---------------------------------------------------------------------------
|
|
623
|
-
// 2.
|
|
730
|
+
// 2. Research Tool (research_web)
|
|
731
|
+
// ---------------------------------------------------------------------------
|
|
732
|
+
const ResearchWebParams = Type.Object({
|
|
733
|
+
topic: Type.String({
|
|
734
|
+
description: "Research question or topic, e.g. 1990s county cold-storage accounting workflow or Tang dynasty courier stations.",
|
|
735
|
+
}),
|
|
736
|
+
purpose: Type.Union([
|
|
737
|
+
Type.Literal("worldbuilding"),
|
|
738
|
+
Type.Literal("era"),
|
|
739
|
+
Type.Literal("profession"),
|
|
740
|
+
Type.Literal("market"),
|
|
741
|
+
Type.Literal("fact-check"),
|
|
742
|
+
Type.Literal("general"),
|
|
743
|
+
], {
|
|
744
|
+
description: "Why this research is needed. Research reports are references only and must not directly mutate story state.",
|
|
745
|
+
}),
|
|
746
|
+
depth: Type.Optional(Type.Union([
|
|
747
|
+
Type.Literal("quick"),
|
|
748
|
+
Type.Literal("standard"),
|
|
749
|
+
Type.Literal("deep"),
|
|
750
|
+
], {
|
|
751
|
+
description: "Research depth. Default standard.",
|
|
752
|
+
})),
|
|
753
|
+
});
|
|
754
|
+
export function createResearchWebTool(projectRoot) {
|
|
755
|
+
return {
|
|
756
|
+
name: "research_web",
|
|
757
|
+
description: "Collect traceable web research for worldbuilding, era, profession, market, or fact-check questions. " +
|
|
758
|
+
"Saves a Markdown report under .inkos/research/. It is reference material only; it must not modify books, chapters, or truth files.",
|
|
759
|
+
label: "Research Web",
|
|
760
|
+
parameters: ResearchWebParams,
|
|
761
|
+
async execute(_toolCallId, params, _signal, onUpdate) {
|
|
762
|
+
onUpdate?.(textResult(`Researching: ${params.topic}`));
|
|
763
|
+
const searchConfig = await readResearchSearchConfig(projectRoot);
|
|
764
|
+
const searchOptions = searchConfig.enabled
|
|
765
|
+
? {
|
|
766
|
+
apiKey: searchConfig.apiKey,
|
|
767
|
+
apiKeyEnv: searchConfig.apiKeyEnv,
|
|
768
|
+
baseUrl: searchConfig.baseUrl,
|
|
769
|
+
}
|
|
770
|
+
: {};
|
|
771
|
+
const report = await runResearchReport({
|
|
772
|
+
topic: params.topic,
|
|
773
|
+
purpose: params.purpose,
|
|
774
|
+
depth: params.depth ?? "standard",
|
|
775
|
+
}, {
|
|
776
|
+
search: (query, maxResults) => searchWeb(query, maxResults, searchOptions),
|
|
777
|
+
});
|
|
778
|
+
const reportDir = join(projectRoot, ".inkos", "research");
|
|
779
|
+
await mkdir(reportDir, { recursive: true });
|
|
780
|
+
const fileName = `${new Date().toISOString().replace(/[:.]/g, "-")}-${slugResearchTopic(params.topic)}.md`;
|
|
781
|
+
const reportPath = join(reportDir, fileName);
|
|
782
|
+
await writeFile(reportPath, report.markdown, "utf-8");
|
|
783
|
+
return textResult([
|
|
784
|
+
`Research report saved: ${reportPath}`,
|
|
785
|
+
`Sources: ${report.sources.length}; confidence: ${report.confidence}.`,
|
|
786
|
+
report.partialFailures.length > 0 ? `Partial failures: ${report.partialFailures.length}.` : "Partial failures: none.",
|
|
787
|
+
].join("\n"), {
|
|
788
|
+
kind: "research_report",
|
|
789
|
+
reportPath,
|
|
790
|
+
topic: params.topic,
|
|
791
|
+
purpose: params.purpose,
|
|
792
|
+
depth: params.depth ?? "standard",
|
|
793
|
+
sources: report.sources,
|
|
794
|
+
claims: report.claims,
|
|
795
|
+
confidence: report.confidence,
|
|
796
|
+
partialFailures: report.partialFailures,
|
|
797
|
+
});
|
|
798
|
+
},
|
|
799
|
+
};
|
|
800
|
+
}
|
|
801
|
+
function slugResearchTopic(topic) {
|
|
802
|
+
const slug = topic
|
|
803
|
+
.normalize("NFKC")
|
|
804
|
+
.toLowerCase()
|
|
805
|
+
.replace(/[^a-z0-9\u4e00-\u9fff]+/g, "-")
|
|
806
|
+
.replace(/^-+|-+$/g, "")
|
|
807
|
+
.slice(0, 60);
|
|
808
|
+
return slug || "research";
|
|
809
|
+
}
|
|
810
|
+
async function readResearchSearchConfig(projectRoot) {
|
|
811
|
+
try {
|
|
812
|
+
const raw = JSON.parse(await readFile(join(projectRoot, "inkos.json"), "utf-8"));
|
|
813
|
+
return ResearchSearchConfigSchema.parse(raw.researchSearch ?? {});
|
|
814
|
+
}
|
|
815
|
+
catch {
|
|
816
|
+
return ResearchSearchConfigSchema.parse({});
|
|
817
|
+
}
|
|
818
|
+
}
|
|
819
|
+
// ---------------------------------------------------------------------------
|
|
820
|
+
// 3. Standalone Short Fiction Tool
|
|
624
821
|
// ---------------------------------------------------------------------------
|
|
625
822
|
const ShortFictionRunParams = Type.Object({
|
|
626
823
|
direction: Type.String({
|
|
@@ -721,7 +918,241 @@ function summarizeCoverGenerationError(error) {
|
|
|
721
918
|
return text.slice(0, 300);
|
|
722
919
|
}
|
|
723
920
|
// ---------------------------------------------------------------------------
|
|
724
|
-
// 3.
|
|
921
|
+
// 3. Script and Storyboard tools
|
|
922
|
+
// ---------------------------------------------------------------------------
|
|
923
|
+
const ScriptCreateParams = Type.Object({
|
|
924
|
+
title: Type.String({
|
|
925
|
+
description: "Required script project title.",
|
|
926
|
+
}),
|
|
927
|
+
instruction: Type.String({
|
|
928
|
+
description: "Confirmed script creation instruction, including format, source, and user preferences.",
|
|
929
|
+
}),
|
|
930
|
+
sourceKind: Type.Optional(Type.String({
|
|
931
|
+
description: "Source type, e.g. novel excerpt, original idea, outline, existing script.",
|
|
932
|
+
})),
|
|
933
|
+
targetFormat: Type.Optional(Type.Union([
|
|
934
|
+
Type.Literal("vertical_short_drama"),
|
|
935
|
+
Type.Literal("screenplay"),
|
|
936
|
+
Type.Literal("audio_drama"),
|
|
937
|
+
Type.Literal("interactive_script"),
|
|
938
|
+
Type.Literal("general_script"),
|
|
939
|
+
], { description: "Confirmed script output format." })),
|
|
940
|
+
sourceText: Type.Optional(Type.String({
|
|
941
|
+
description: "User-provided source text. For long sources, prefer sourcePath instead of summarizing.",
|
|
942
|
+
})),
|
|
943
|
+
sourcePath: Type.Optional(Type.String({
|
|
944
|
+
description: "Optional project-relative source file path.",
|
|
945
|
+
})),
|
|
946
|
+
requirements: Type.Optional(Type.String({
|
|
947
|
+
description: "Confirmed script format, production constraints, tone, episode structure, or user preferences.",
|
|
948
|
+
})),
|
|
949
|
+
episodeCount: Type.Optional(Type.Number({
|
|
950
|
+
description: "Optional target episode/segment count.",
|
|
951
|
+
})),
|
|
952
|
+
episodeDuration: Type.Optional(Type.String({
|
|
953
|
+
description: "Optional per-episode/per-segment duration.",
|
|
954
|
+
})),
|
|
955
|
+
projectId: Type.Optional(Type.String({
|
|
956
|
+
description: "Optional output id under dramas/.",
|
|
957
|
+
})),
|
|
958
|
+
outDir: Type.Optional(Type.String({
|
|
959
|
+
description: "Optional project-relative output directory. Default dramas/.",
|
|
960
|
+
})),
|
|
961
|
+
});
|
|
962
|
+
export function createScriptCreationTool(pipeline, projectRoot, options = {}) {
|
|
963
|
+
return {
|
|
964
|
+
name: "script_create",
|
|
965
|
+
description: "Create a script project from a novel excerpt, idea, outline, or existing script. " +
|
|
966
|
+
"Writes human-readable Markdown spec and script files under dramas/.",
|
|
967
|
+
label: "Script Creation",
|
|
968
|
+
parameters: ScriptCreateParams,
|
|
969
|
+
async execute(_toolCallId, params, _signal, onUpdate) {
|
|
970
|
+
const progress = (message) => onUpdate?.(textResult(message));
|
|
971
|
+
const payload = options.actionPayload?.scriptCreate;
|
|
972
|
+
const result = await runScriptCreation({
|
|
973
|
+
projectRoot,
|
|
974
|
+
runtime: pipeline.createAgentContext("script-creation"),
|
|
975
|
+
title: payload?.title ?? params.title,
|
|
976
|
+
instruction: params.instruction,
|
|
977
|
+
sourceKind: payload?.sourceKind ?? params.sourceKind,
|
|
978
|
+
targetFormat: (payload?.targetFormat ?? params.targetFormat),
|
|
979
|
+
sourceText: payload?.sourceText ?? params.sourceText,
|
|
980
|
+
sourcePath: payload?.sourcePath ?? params.sourcePath,
|
|
981
|
+
requirements: payload?.requirements ?? params.requirements,
|
|
982
|
+
episodeCount: payload?.episodeCount ?? params.episodeCount,
|
|
983
|
+
episodeDuration: payload?.episodeDuration ?? params.episodeDuration,
|
|
984
|
+
projectId: payload?.projectId ?? params.projectId,
|
|
985
|
+
outDir: payload?.outDir ?? params.outDir,
|
|
986
|
+
onProgress: progress,
|
|
987
|
+
});
|
|
988
|
+
return textResult([
|
|
989
|
+
`Script "${result.projectId}" completed.`,
|
|
990
|
+
`Spec: ${result.specPath}`,
|
|
991
|
+
`Script: ${result.scriptPath}`,
|
|
992
|
+
].join("\n"), { kind: "script_created", ...result });
|
|
993
|
+
},
|
|
994
|
+
};
|
|
995
|
+
}
|
|
996
|
+
const StoryboardCreateParams = Type.Object({
|
|
997
|
+
title: Type.String({
|
|
998
|
+
description: "Required storyboard project title.",
|
|
999
|
+
}),
|
|
1000
|
+
instruction: Type.String({
|
|
1001
|
+
description: "Confirmed storyboard creation instruction, including source, style, aspect ratio, and shot granularity.",
|
|
1002
|
+
}),
|
|
1003
|
+
sourceKind: Type.Optional(Type.String({
|
|
1004
|
+
description: "Source type, e.g. script, novel excerpt, idea, scene list.",
|
|
1005
|
+
})),
|
|
1006
|
+
sourceText: Type.Optional(Type.String({
|
|
1007
|
+
description: "User-provided source text. For long sources, prefer sourcePath instead of summarizing.",
|
|
1008
|
+
})),
|
|
1009
|
+
sourcePath: Type.Optional(Type.String({
|
|
1010
|
+
description: "Optional project-relative source file path.",
|
|
1011
|
+
})),
|
|
1012
|
+
requirements: Type.Optional(Type.String({
|
|
1013
|
+
description: "Confirmed shot/storyboard requirements.",
|
|
1014
|
+
})),
|
|
1015
|
+
visualStyle: Type.Optional(Type.String({
|
|
1016
|
+
description: "Confirmed visual style, if the user specified one.",
|
|
1017
|
+
})),
|
|
1018
|
+
aspectRatio: Type.Optional(Type.String({
|
|
1019
|
+
description: "Confirmed aspect ratio, e.g. 9:16, 16:9, 1:1.",
|
|
1020
|
+
})),
|
|
1021
|
+
granularity: Type.Optional(Type.String({
|
|
1022
|
+
description: "Confirmed storyboard granularity.",
|
|
1023
|
+
})),
|
|
1024
|
+
maxShots: Type.Optional(Type.Number({
|
|
1025
|
+
description: "Optional max shot count.",
|
|
1026
|
+
})),
|
|
1027
|
+
projectId: Type.Optional(Type.String({
|
|
1028
|
+
description: "Optional output id under storyboards/.",
|
|
1029
|
+
})),
|
|
1030
|
+
outDir: Type.Optional(Type.String({
|
|
1031
|
+
description: "Optional project-relative output directory. Default storyboards/.",
|
|
1032
|
+
})),
|
|
1033
|
+
});
|
|
1034
|
+
export function createStoryboardCreationTool(pipeline, projectRoot, options = {}) {
|
|
1035
|
+
return {
|
|
1036
|
+
name: "storyboard_create",
|
|
1037
|
+
description: "Create a storyboard project and image prompts from a script, novel excerpt, idea, or scene list. " +
|
|
1038
|
+
"Writes human-readable Markdown spec, storyboard, and image prompt files under storyboards/.",
|
|
1039
|
+
label: "Storyboard Creation",
|
|
1040
|
+
parameters: StoryboardCreateParams,
|
|
1041
|
+
async execute(_toolCallId, params, _signal, onUpdate) {
|
|
1042
|
+
const progress = (message) => onUpdate?.(textResult(message));
|
|
1043
|
+
const payload = options.actionPayload?.storyboardCreate;
|
|
1044
|
+
const result = await runStoryboardCreation({
|
|
1045
|
+
projectRoot,
|
|
1046
|
+
runtime: pipeline.createAgentContext("storyboard-creation"),
|
|
1047
|
+
title: payload?.title ?? params.title,
|
|
1048
|
+
instruction: params.instruction,
|
|
1049
|
+
sourceKind: payload?.sourceKind ?? params.sourceKind,
|
|
1050
|
+
sourceText: payload?.sourceText ?? params.sourceText,
|
|
1051
|
+
sourcePath: payload?.sourcePath ?? params.sourcePath,
|
|
1052
|
+
requirements: payload?.requirements ?? params.requirements,
|
|
1053
|
+
visualStyle: payload?.visualStyle ?? params.visualStyle,
|
|
1054
|
+
aspectRatio: payload?.aspectRatio ?? params.aspectRatio,
|
|
1055
|
+
granularity: payload?.granularity ?? params.granularity,
|
|
1056
|
+
maxShots: payload?.maxShots ?? params.maxShots,
|
|
1057
|
+
projectId: payload?.projectId ?? params.projectId,
|
|
1058
|
+
outDir: payload?.outDir ?? params.outDir,
|
|
1059
|
+
onProgress: progress,
|
|
1060
|
+
});
|
|
1061
|
+
return textResult([
|
|
1062
|
+
`Storyboard "${result.projectId}" completed.`,
|
|
1063
|
+
`Spec: ${result.specPath}`,
|
|
1064
|
+
`Storyboard: ${result.storyboardPath}`,
|
|
1065
|
+
`Image prompts: ${result.imagePromptsPath}`,
|
|
1066
|
+
`Image assets: ${result.assetsManifestPath}`,
|
|
1067
|
+
].join("\n"), { kind: "storyboard_created", ...result });
|
|
1068
|
+
},
|
|
1069
|
+
};
|
|
1070
|
+
}
|
|
1071
|
+
const InteractiveFilmCreateParams = Type.Object({
|
|
1072
|
+
title: Type.String({
|
|
1073
|
+
description: "Required interactive-film project title.",
|
|
1074
|
+
}),
|
|
1075
|
+
instruction: Type.String({
|
|
1076
|
+
description: "Confirmed interactive-film creation instruction, including branching, variables/flags, endings, source, and user preferences.",
|
|
1077
|
+
}),
|
|
1078
|
+
sourceKind: Type.Optional(Type.String({
|
|
1079
|
+
description: "Source type, e.g. novel excerpt, script, outline, original idea.",
|
|
1080
|
+
})),
|
|
1081
|
+
sourceText: Type.Optional(Type.String({
|
|
1082
|
+
description: "User-provided source text. For long sources, prefer sourcePath instead of summarizing.",
|
|
1083
|
+
})),
|
|
1084
|
+
sourcePath: Type.Optional(Type.String({
|
|
1085
|
+
description: "Optional project-relative source file path.",
|
|
1086
|
+
})),
|
|
1087
|
+
requirements: Type.Optional(Type.String({
|
|
1088
|
+
description: "Confirmed branching, variable/flag, ending, production, visual, or market requirements.",
|
|
1089
|
+
})),
|
|
1090
|
+
targetAudience: Type.Optional(Type.String({
|
|
1091
|
+
description: "Optional confirmed target audience or market.",
|
|
1092
|
+
})),
|
|
1093
|
+
episodeCount: Type.Optional(Type.Number({
|
|
1094
|
+
description: "Optional target episode/segment count.",
|
|
1095
|
+
})),
|
|
1096
|
+
episodeDuration: Type.Optional(Type.String({
|
|
1097
|
+
description: "Optional per-episode/per-segment duration.",
|
|
1098
|
+
})),
|
|
1099
|
+
budget: Type.Optional(Type.String({
|
|
1100
|
+
description: "Optional budget or production constraints.",
|
|
1101
|
+
})),
|
|
1102
|
+
referenceMode: Type.Optional(Type.String({
|
|
1103
|
+
description: "Optional reference mode, e.g. 盛世天下-style multi-ending interactive drama.",
|
|
1104
|
+
})),
|
|
1105
|
+
projectId: Type.Optional(Type.String({
|
|
1106
|
+
description: "Optional output id under interactive-films/.",
|
|
1107
|
+
})),
|
|
1108
|
+
outDir: Type.Optional(Type.String({
|
|
1109
|
+
description: "Optional project-relative output directory. Default interactive-films/.",
|
|
1110
|
+
})),
|
|
1111
|
+
});
|
|
1112
|
+
export function createInteractiveFilmCreationTool(pipeline, projectRoot, options = {}) {
|
|
1113
|
+
return {
|
|
1114
|
+
name: "interactive_film_create",
|
|
1115
|
+
description: "Create an interactive film/game script package with story tree, variables/flags, endings, script, storyboard, and image prompts. " +
|
|
1116
|
+
"Writes human-readable Markdown files under interactive-films/.",
|
|
1117
|
+
label: "Interactive Film Creation",
|
|
1118
|
+
parameters: InteractiveFilmCreateParams,
|
|
1119
|
+
async execute(_toolCallId, params, _signal, onUpdate) {
|
|
1120
|
+
const progress = (message) => onUpdate?.(textResult(message));
|
|
1121
|
+
const payload = options.actionPayload?.interactiveFilmCreate;
|
|
1122
|
+
const result = await runInteractiveFilmCreation({
|
|
1123
|
+
projectRoot,
|
|
1124
|
+
runtime: pipeline.createAgentContext("interactive-film-creation"),
|
|
1125
|
+
title: payload?.title ?? params.title,
|
|
1126
|
+
instruction: params.instruction,
|
|
1127
|
+
sourceKind: payload?.sourceKind ?? params.sourceKind,
|
|
1128
|
+
sourceText: payload?.sourceText ?? params.sourceText,
|
|
1129
|
+
sourcePath: payload?.sourcePath ?? params.sourcePath,
|
|
1130
|
+
requirements: payload?.requirements ?? params.requirements,
|
|
1131
|
+
targetAudience: payload?.targetAudience ?? params.targetAudience,
|
|
1132
|
+
episodeCount: payload?.episodeCount ?? params.episodeCount,
|
|
1133
|
+
episodeDuration: payload?.episodeDuration ?? params.episodeDuration,
|
|
1134
|
+
budget: payload?.budget ?? params.budget,
|
|
1135
|
+
referenceMode: payload?.referenceMode ?? params.referenceMode,
|
|
1136
|
+
projectId: payload?.projectId ?? params.projectId,
|
|
1137
|
+
outDir: payload?.outDir ?? params.outDir,
|
|
1138
|
+
onProgress: progress,
|
|
1139
|
+
});
|
|
1140
|
+
return textResult([
|
|
1141
|
+
`Interactive film "${result.projectId}" completed.`,
|
|
1142
|
+
`Spec: ${result.specPath}`,
|
|
1143
|
+
`Story graph: ${result.storyGraphPath}`,
|
|
1144
|
+
`Story tree: ${result.storyTreePath}`,
|
|
1145
|
+
`Flags: ${result.flagsPath}`,
|
|
1146
|
+
`Script: ${result.scriptPath}`,
|
|
1147
|
+
`Storyboard: ${result.storyboardPath}`,
|
|
1148
|
+
`Image prompts: ${result.imagePromptsPath}`,
|
|
1149
|
+
`Image assets: ${result.assetsManifestPath}`,
|
|
1150
|
+
].join("\n"), { kind: "interactive_film_created", ...result });
|
|
1151
|
+
},
|
|
1152
|
+
};
|
|
1153
|
+
}
|
|
1154
|
+
// ---------------------------------------------------------------------------
|
|
1155
|
+
// 4. Standalone Cover Tool
|
|
725
1156
|
// ---------------------------------------------------------------------------
|
|
726
1157
|
const GenerateCoverParams = Type.Object({
|
|
727
1158
|
title: Type.String({
|