@lingjingai/scriptctl 0.20.0 → 0.21.0
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/cli.js +99 -11
- package/dist/cli.js.map +1 -1
- package/dist/common.d.ts +1 -0
- package/dist/common.js.map +1 -1
- package/dist/domain/script/address.d.ts +30 -0
- package/dist/domain/script/address.js +141 -0
- package/dist/domain/script/address.js.map +1 -0
- package/dist/domain/script/lookups.d.ts +33 -0
- package/dist/domain/script/lookups.js +309 -0
- package/dist/domain/script/lookups.js.map +1 -0
- package/dist/domain/script/patch/apply.d.ts +4 -0
- package/dist/domain/script/patch/apply.js +38 -0
- package/dist/domain/script/patch/apply.js.map +1 -0
- package/dist/domain/script/patch/helpers.d.ts +11 -0
- package/dist/domain/script/patch/helpers.js +141 -0
- package/dist/domain/script/patch/helpers.js.map +1 -0
- package/dist/domain/script/patch/ops-action.d.ts +12 -0
- package/dist/domain/script/patch/ops-action.js +371 -0
- package/dist/domain/script/patch/ops-action.js.map +1 -0
- package/dist/domain/script/patch/ops-asset.d.ts +13 -0
- package/dist/domain/script/patch/ops-asset.js +363 -0
- package/dist/domain/script/patch/ops-asset.js.map +1 -0
- package/dist/domain/script/patch/ops-dialogue.d.ts +5 -0
- package/dist/domain/script/patch/ops-dialogue.js +233 -0
- package/dist/domain/script/patch/ops-dialogue.js.map +1 -0
- package/dist/domain/script/patch/ops-meta.d.ts +3 -0
- package/dist/domain/script/patch/ops-meta.js +47 -0
- package/dist/domain/script/patch/ops-meta.js.map +1 -0
- package/dist/domain/script/patch/ops-scene.d.ts +6 -0
- package/dist/domain/script/patch/ops-scene.js +345 -0
- package/dist/domain/script/patch/ops-scene.js.map +1 -0
- package/dist/domain/script/patch/ops-state.d.ts +8 -0
- package/dist/domain/script/patch/ops-state.js +146 -0
- package/dist/domain/script/patch/ops-state.js.map +1 -0
- package/dist/domain/script/patch/registry.d.ts +2 -0
- package/dist/domain/script/patch/registry.js +50 -0
- package/dist/domain/script/patch/registry.js.map +1 -0
- package/dist/domain/script/patch/types.d.ts +10 -0
- package/dist/domain/script/patch/types.js +2 -0
- package/dist/domain/script/patch/types.js.map +1 -0
- package/dist/domain/script/refs.d.ts +4 -0
- package/dist/domain/script/refs.js +152 -0
- package/dist/domain/script/refs.js.map +1 -0
- package/dist/domain/script/schema.d.ts +6 -0
- package/dist/domain/script/schema.js +53 -0
- package/dist/domain/script/schema.js.map +1 -0
- package/dist/domain/script/selector.d.ts +45 -0
- package/dist/domain/script/selector.js +187 -0
- package/dist/domain/script/selector.js.map +1 -0
- package/dist/domain/script/shared.d.ts +15 -0
- package/dist/domain/script/shared.js +37 -0
- package/dist/domain/script/shared.js.map +1 -0
- package/dist/domain/script/validate.d.ts +22 -0
- package/dist/domain/script/validate.js +844 -0
- package/dist/domain/script/validate.js.map +1 -0
- package/dist/help-text.js +21 -4
- package/dist/help-text.js.map +1 -1
- package/dist/output.d.ts +1 -1
- package/dist/output.js +11 -1
- package/dist/output.js.map +1 -1
- package/dist/usecases/direct.js +1 -1
- package/dist/usecases/direct.js.map +1 -1
- package/dist/usecases/parse.js +1 -1
- package/dist/usecases/parse.js.map +1 -1
- package/dist/usecases/script/actions.d.ts +3 -0
- package/dist/usecases/script/actions.js +71 -0
- package/dist/usecases/script/actions.js.map +1 -0
- package/dist/usecases/script/actor.d.ts +3 -0
- package/dist/usecases/script/actor.js +27 -0
- package/dist/usecases/script/actor.js.map +1 -0
- package/dist/usecases/script/actors.d.ts +3 -0
- package/dist/usecases/script/actors.js +15 -0
- package/dist/usecases/script/actors.js.map +1 -0
- package/dist/usecases/script/add-actor.d.ts +3 -0
- package/dist/usecases/script/add-actor.js +13 -0
- package/dist/usecases/script/add-actor.js.map +1 -0
- package/dist/usecases/script/add-episode.d.ts +3 -0
- package/dist/usecases/script/add-episode.js +9 -0
- package/dist/usecases/script/add-episode.js.map +1 -0
- package/dist/usecases/script/add-location.d.ts +3 -0
- package/dist/usecases/script/add-location.js +11 -0
- package/dist/usecases/script/add-location.js.map +1 -0
- package/dist/usecases/script/add-prop.d.ts +3 -0
- package/dist/usecases/script/add-prop.js +11 -0
- package/dist/usecases/script/add-prop.js.map +1 -0
- package/dist/usecases/script/add-speaker.d.ts +3 -0
- package/dist/usecases/script/add-speaker.js +22 -0
- package/dist/usecases/script/add-speaker.js.map +1 -0
- package/dist/usecases/script/alias.d.ts +3 -0
- package/dist/usecases/script/alias.js +40 -0
- package/dist/usecases/script/alias.js.map +1 -0
- package/dist/usecases/script/assets.d.ts +3 -0
- package/dist/usecases/script/assets.js +21 -0
- package/dist/usecases/script/assets.js.map +1 -0
- package/dist/usecases/script/context.d.ts +3 -0
- package/dist/usecases/script/context.js +20 -0
- package/dist/usecases/script/context.js.map +1 -0
- package/dist/usecases/script/create.d.ts +3 -0
- package/dist/usecases/script/create.js +81 -0
- package/dist/usecases/script/create.js.map +1 -0
- package/dist/usecases/script/delete.d.ts +3 -0
- package/dist/usecases/script/delete.js +79 -0
- package/dist/usecases/script/delete.js.map +1 -0
- package/dist/usecases/script/describe.d.ts +3 -0
- package/dist/usecases/script/describe.js +31 -0
- package/dist/usecases/script/describe.js.map +1 -0
- package/dist/usecases/script/dialogue.d.ts +3 -0
- package/dist/usecases/script/dialogue.js +28 -0
- package/dist/usecases/script/dialogue.js.map +1 -0
- package/dist/usecases/script/do.d.ts +3 -0
- package/dist/usecases/script/do.js +130 -0
- package/dist/usecases/script/do.js.map +1 -0
- package/dist/usecases/script/episodes.d.ts +3 -0
- package/dist/usecases/script/episodes.js +36 -0
- package/dist/usecases/script/episodes.js.map +1 -0
- package/dist/usecases/script/export.d.ts +3 -0
- package/dist/usecases/script/export.js +117 -0
- package/dist/usecases/script/export.js.map +1 -0
- package/dist/usecases/script/insert.d.ts +3 -0
- package/dist/usecases/script/insert.js +87 -0
- package/dist/usecases/script/insert.js.map +1 -0
- package/dist/usecases/script/issues.d.ts +3 -0
- package/dist/usecases/script/issues.js +27 -0
- package/dist/usecases/script/issues.js.map +1 -0
- package/dist/usecases/script/lib.d.ts +77 -0
- package/dist/usecases/script/lib.js +849 -0
- package/dist/usecases/script/lib.js.map +1 -0
- package/dist/usecases/script/locations.d.ts +3 -0
- package/dist/usecases/script/locations.js +15 -0
- package/dist/usecases/script/locations.js.map +1 -0
- package/dist/usecases/script/merge.d.ts +3 -0
- package/dist/usecases/script/merge.js +43 -0
- package/dist/usecases/script/merge.js.map +1 -0
- package/dist/usecases/script/move.d.ts +3 -0
- package/dist/usecases/script/move.js +33 -0
- package/dist/usecases/script/move.js.map +1 -0
- package/dist/usecases/script/overlap.d.ts +3 -0
- package/dist/usecases/script/overlap.js +21 -0
- package/dist/usecases/script/overlap.js.map +1 -0
- package/dist/usecases/script/props.d.ts +3 -0
- package/dist/usecases/script/props.js +15 -0
- package/dist/usecases/script/props.js.map +1 -0
- package/dist/usecases/script/refs.d.ts +3 -0
- package/dist/usecases/script/refs.js +61 -0
- package/dist/usecases/script/refs.js.map +1 -0
- package/dist/usecases/script/rename.d.ts +3 -0
- package/dist/usecases/script/rename.js +17 -0
- package/dist/usecases/script/rename.js.map +1 -0
- package/dist/usecases/script/replace.d.ts +3 -0
- package/dist/usecases/script/replace.js +35 -0
- package/dist/usecases/script/replace.js.map +1 -0
- package/dist/usecases/script/role.d.ts +3 -0
- package/dist/usecases/script/role.js +17 -0
- package/dist/usecases/script/role.js.map +1 -0
- package/dist/usecases/script/scenes.d.ts +3 -0
- package/dist/usecases/script/scenes.js +45 -0
- package/dist/usecases/script/scenes.js.map +1 -0
- package/dist/usecases/script/script-patch.d.ts +3 -0
- package/dist/usecases/script/script-patch.js +187 -0
- package/dist/usecases/script/script-patch.js.map +1 -0
- package/dist/usecases/script/script-validate.d.ts +3 -0
- package/dist/usecases/script/script-validate.js +30 -0
- package/dist/usecases/script/script-validate.js.map +1 -0
- package/dist/usecases/script/session.d.ts +44 -0
- package/dist/usecases/script/session.js +527 -0
- package/dist/usecases/script/session.js.map +1 -0
- package/dist/usecases/script/speakers.d.ts +3 -0
- package/dist/usecases/script/speakers.js +28 -0
- package/dist/usecases/script/speakers.js.map +1 -0
- package/dist/usecases/script/split.d.ts +3 -0
- package/dist/usecases/script/split.js +37 -0
- package/dist/usecases/script/split.js.map +1 -0
- package/dist/usecases/script/state-add.d.ts +3 -0
- package/dist/usecases/script/state-add.js +23 -0
- package/dist/usecases/script/state-add.js.map +1 -0
- package/dist/usecases/script/state-change.d.ts +3 -0
- package/dist/usecases/script/state-change.js +24 -0
- package/dist/usecases/script/state-change.js.map +1 -0
- package/dist/usecases/script/state-delete.d.ts +3 -0
- package/dist/usecases/script/state-delete.js +23 -0
- package/dist/usecases/script/state-delete.js.map +1 -0
- package/dist/usecases/script/state-rename.d.ts +3 -0
- package/dist/usecases/script/state-rename.js +17 -0
- package/dist/usecases/script/state-rename.js.map +1 -0
- package/dist/usecases/script/summary.d.ts +3 -0
- package/dist/usecases/script/summary.js +45 -0
- package/dist/usecases/script/summary.js.map +1 -0
- package/dist/usecases/script/transition.d.ts +3 -0
- package/dist/usecases/script/transition.js +24 -0
- package/dist/usecases/script/transition.js.map +1 -0
- package/dist/usecases/script/type.d.ts +3 -0
- package/dist/usecases/script/type.js +24 -0
- package/dist/usecases/script/type.js.map +1 -0
- package/dist/usecases/script/worldview.d.ts +3 -0
- package/dist/usecases/script/worldview.js +18 -0
- package/dist/usecases/script/worldview.js.map +1 -0
- package/package.json +1 -1
- package/dist/domain/script-core.d.ts +0 -78
- package/dist/domain/script-core.js +0 -3026
- package/dist/domain/script-core.js.map +0 -1
- package/dist/usecases/script.d.ts +0 -67
- package/dist/usecases/script.js +0 -2348
- package/dist/usecases/script.js.map +0 -1
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
import { CliError, EXIT_USAGE, } from "../../common.js";
|
|
2
|
+
import { parseAnyAddress, } from "../../domain/script/address.js";
|
|
3
|
+
import { asList, } from "../../domain/script/shared.js";
|
|
4
|
+
import { applySingleScriptOp, } from "./lib.js";
|
|
5
|
+
export async function commandDelete(opts) {
|
|
6
|
+
const args = asList(opts["_args"]);
|
|
7
|
+
if (args.length < 1) {
|
|
8
|
+
throw new CliError("VERB BLOCKED: Address missing", "Address missing.", {
|
|
9
|
+
exitCode: EXIT_USAGE,
|
|
10
|
+
required: ["address"],
|
|
11
|
+
received: ["<empty>"],
|
|
12
|
+
nextSteps: ["Pass an address (action / scene / asset / speaker)."],
|
|
13
|
+
errorCode: "ADDRESS_MISSING",
|
|
14
|
+
});
|
|
15
|
+
}
|
|
16
|
+
const addr = parseAnyAddress(args[0]);
|
|
17
|
+
// Per-kind flag whitelist — silently ignoring wrong-kind flags hid real
|
|
18
|
+
// misuse (e.g. `delete actor:X --force` did NOT bypass ref protection, but
|
|
19
|
+
// the user assumed it did). Surface the mismatch with an explicit error.
|
|
20
|
+
const flagsUsed = {
|
|
21
|
+
strategy: opts["strategy"] !== undefined,
|
|
22
|
+
replacement: opts["replacement"] !== undefined,
|
|
23
|
+
force: Boolean(opts["force"]),
|
|
24
|
+
};
|
|
25
|
+
function rejectFlags(kind, allowed) {
|
|
26
|
+
const allow = new Set(allowed);
|
|
27
|
+
const bad = [];
|
|
28
|
+
for (const f of ["strategy", "replacement", "force"]) {
|
|
29
|
+
if (flagsUsed[f] && !allow.has(f))
|
|
30
|
+
bad.push(`--${f}`);
|
|
31
|
+
}
|
|
32
|
+
if (bad.length > 0) {
|
|
33
|
+
throw new CliError("VERB BLOCKED: flag not applicable", `${bad.join(", ")} cannot be used with ${kind} delete.`, {
|
|
34
|
+
exitCode: EXIT_USAGE,
|
|
35
|
+
required: [`for ${kind} delete: ${allowed.length === 0 ? "no extra flags" : allowed.map((f) => `--${f}`).join(" / ")}`],
|
|
36
|
+
received: bad,
|
|
37
|
+
nextSteps: ["Drop the unsupported flag(s) and retry."],
|
|
38
|
+
errorCode: "DELETE_FLAG_INVALID",
|
|
39
|
+
});
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
const op = (() => {
|
|
43
|
+
if (addr.kind === "action") {
|
|
44
|
+
rejectFlags("action", []);
|
|
45
|
+
return { op: "action.delete", at: args[0] };
|
|
46
|
+
}
|
|
47
|
+
if (addr.kind === "scene") {
|
|
48
|
+
rejectFlags("scene", ["force"]);
|
|
49
|
+
return { op: "scene.delete", at: args[0], force: Boolean(opts["force"]) };
|
|
50
|
+
}
|
|
51
|
+
if (addr.kind === "asset") {
|
|
52
|
+
rejectFlags("asset", ["strategy", "replacement"]);
|
|
53
|
+
return {
|
|
54
|
+
op: "asset.delete",
|
|
55
|
+
target: args[0],
|
|
56
|
+
strategy: opts["strategy"],
|
|
57
|
+
replacement: opts["replacement"],
|
|
58
|
+
};
|
|
59
|
+
}
|
|
60
|
+
if (addr.kind === "speaker") {
|
|
61
|
+
rejectFlags("speaker", ["strategy", "replacement"]);
|
|
62
|
+
return {
|
|
63
|
+
op: "speaker.delete",
|
|
64
|
+
target: addr.speakerId,
|
|
65
|
+
strategy: opts["strategy"],
|
|
66
|
+
replacement: opts["replacement"],
|
|
67
|
+
};
|
|
68
|
+
}
|
|
69
|
+
throw new CliError("VERB BLOCKED: delete cannot operate on this address", "delete cannot operate on this address.", {
|
|
70
|
+
exitCode: EXIT_USAGE,
|
|
71
|
+
required: ["action / scene / asset / speaker address"],
|
|
72
|
+
received: [args[0]],
|
|
73
|
+
nextSteps: ["Use a supported address."],
|
|
74
|
+
errorCode: "ADDRESS_UNSUPPORTED",
|
|
75
|
+
});
|
|
76
|
+
})();
|
|
77
|
+
return applySingleScriptOp(opts, op);
|
|
78
|
+
}
|
|
79
|
+
//# sourceMappingURL=delete.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"delete.js","sourceRoot":"","sources":["../../../src/usecases/script/delete.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import { CliError, EXIT_USAGE, } from "../../common.js";
|
|
2
|
+
import { parseAnyAddress, } from "../../domain/script/address.js";
|
|
3
|
+
import { asList, } from "../../domain/script/shared.js";
|
|
4
|
+
import { applySingleScriptOp, } from "./lib.js";
|
|
5
|
+
export async function commandDescribe(opts) {
|
|
6
|
+
const args = asList(opts["_args"]);
|
|
7
|
+
if (args.length < 2) {
|
|
8
|
+
throw new CliError("VERB BLOCKED: Describe args missing", "Describe args missing.", {
|
|
9
|
+
exitCode: EXIT_USAGE,
|
|
10
|
+
required: ["<addr> <text>"],
|
|
11
|
+
received: args,
|
|
12
|
+
nextSteps: ["Example: scriptctl describe actor:act_001 \"男主\" or scriptctl describe actor:act_001/st_calm \"...\""],
|
|
13
|
+
errorCode: "ARGS_MISSING",
|
|
14
|
+
});
|
|
15
|
+
}
|
|
16
|
+
const addr = parseAnyAddress(args[0]);
|
|
17
|
+
if (addr.kind === "state") {
|
|
18
|
+
return applySingleScriptOp(opts, { op: "state.describe", target: args[0], description: args[1] });
|
|
19
|
+
}
|
|
20
|
+
if (addr.kind === "asset") {
|
|
21
|
+
return applySingleScriptOp(opts, { op: "asset.describe", target: args[0], description: args[1] });
|
|
22
|
+
}
|
|
23
|
+
throw new CliError("VERB BLOCKED: describe address invalid", "describe address invalid.", {
|
|
24
|
+
exitCode: EXIT_USAGE,
|
|
25
|
+
required: ["asset address (e.g. actor:act_001) or state address (e.g. actor:act_001/st_calm)"],
|
|
26
|
+
received: [args[0]],
|
|
27
|
+
nextSteps: ["Use a supported address."],
|
|
28
|
+
errorCode: "ADDRESS_UNSUPPORTED",
|
|
29
|
+
});
|
|
30
|
+
}
|
|
31
|
+
//# sourceMappingURL=describe.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"describe.js","sourceRoot":"","sources":["../../../src/usecases/script/describe.ts"],"names":[],"mappings":"AAKA,OAAO,EACL,QAAQ,EAKR,UAAU,GASX,MAAM,iBAAiB,CAAC;AAYzB,OAAO,EACL,eAAe,GAKhB,MAAM,gCAAgC,CAAC;AAiBxC,OAAO,EACL,MAAM,GAKP,MAAM,+BAA+B,CAAC;AAMvC,OAAO,EAC+I,mBAAmB,GACxK,MAAM,UAAU,CAAC;AAElB,MAAM,CAAC,KAAK,UAAU,eAAe,CAAC,IAAU;IAC9C,MAAM,IAAI,GAAG,MAAM,CAAS,IAAI,CAAC,OAAO,CAAC,CAAC,CAAC;IAC3C,IAAI,IAAI,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QACpB,MAAM,IAAI,QAAQ,CAAC,qCAAqC,EAAE,wBAAwB,EAAE;YAClF,QAAQ,EAAE,UAAU;YACpB,QAAQ,EAAE,CAAC,eAAe,CAAC;YAC3B,QAAQ,EAAE,IAAI;YACd,SAAS,EAAE,CAAC,sGAAsG,CAAC;YACnH,SAAS,EAAE,cAAc;SAC1B,CAAC,CAAC;IACL,CAAC;IACD,MAAM,IAAI,GAAG,eAAe,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC;IACtC,IAAI,IAAI,CAAC,IAAI,KAAK,OAAO,EAAE,CAAC;QAC1B,OAAO,mBAAmB,CAAC,IAAI,EAAE,EAAE,EAAE,EAAE,gBAAgB,EAAE,MAAM,EAAE,IAAI,CAAC,CAAC,CAAC,EAAE,WAAW,EAAE,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;IACpG,CAAC;IACD,IAAI,IAAI,CAAC,IAAI,KAAK,OAAO,EAAE,CAAC;QAC1B,OAAO,mBAAmB,CAAC,IAAI,EAAE,EAAE,EAAE,EAAE,gBAAgB,EAAE,MAAM,EAAE,IAAI,CAAC,CAAC,CAAC,EAAE,WAAW,EAAE,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;IACpG,CAAC;IACD,MAAM,IAAI,QAAQ,CAAC,wCAAwC,EAAE,2BAA2B,EAAE;QACxF,QAAQ,EAAE,UAAU;QACpB,QAAQ,EAAE,CAAC,kFAAkF,CAAC;QAC9F,QAAQ,EAAE,CAAC,IAAI,CAAC,CAAC,CAAE,CAAC;QACpB,SAAS,EAAE,CAAC,0BAA0B,CAAC;QACvC,SAAS,EAAE,qBAAqB;KACjC,CAAC,CAAC;AACL,CAAC"}
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import { CliError, EXIT_USAGE, } from "../../common.js";
|
|
2
|
+
import { asList, } from "../../domain/script/shared.js";
|
|
3
|
+
import { applySingleScriptOp, splitSpeakerList, } from "./lib.js";
|
|
4
|
+
import { dialogueTemplate } from "./lib.js";
|
|
5
|
+
export async function commandDialogue(opts) {
|
|
6
|
+
const args = asList(opts["_args"]);
|
|
7
|
+
if (args.length < 1) {
|
|
8
|
+
throw new CliError("VERB BLOCKED: dialogue action ref missing", "dialogue action ref missing.", {
|
|
9
|
+
exitCode: EXIT_USAGE,
|
|
10
|
+
required: ["<action-addr>"],
|
|
11
|
+
received: ["<empty>"],
|
|
12
|
+
nextSteps: ["Example: scriptctl dialogue ep_001/scn_001#3 --speakers spk_001"],
|
|
13
|
+
errorCode: "ARGS_MISSING",
|
|
14
|
+
});
|
|
15
|
+
}
|
|
16
|
+
const speakers = splitSpeakerList(opts["speakers"]);
|
|
17
|
+
if (speakers.length === 0) {
|
|
18
|
+
throw new CliError("VERB BLOCKED: --speakers required", "--speakers required.", {
|
|
19
|
+
exitCode: EXIT_USAGE,
|
|
20
|
+
required: ["--speakers id1[,id2,...]"],
|
|
21
|
+
received: ["<empty>"],
|
|
22
|
+
nextSteps: ["Pass one or more speaker ids."],
|
|
23
|
+
errorCode: "SPEAKERS_EMPTY",
|
|
24
|
+
});
|
|
25
|
+
}
|
|
26
|
+
return applySingleScriptOp(opts, { ...dialogueTemplate(speakers, { delivery: opts["delivery"] }), at: args[0] });
|
|
27
|
+
}
|
|
28
|
+
//# sourceMappingURL=dialogue.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"dialogue.js","sourceRoot":"","sources":["../../../src/usecases/script/dialogue.ts"],"names":[],"mappings":"AAKA,OAAO,EACL,QAAQ,EAKR,UAAU,GASX,MAAM,iBAAiB,CAAC;AAmCzB,OAAO,EACL,MAAM,GAKP,MAAM,+BAA+B,CAAC;AAMvC,OAAO,EAC+I,mBAAmB,EAAwS,gBAAgB,GAChe,MAAM,UAAU,CAAC;AAClB,OAAO,EAAE,gBAAgB,EAAE,MAAM,UAAU,CAAC;AAE5C,MAAM,CAAC,KAAK,UAAU,eAAe,CAAC,IAAU;IAC9C,MAAM,IAAI,GAAG,MAAM,CAAS,IAAI,CAAC,OAAO,CAAC,CAAC,CAAC;IAC3C,IAAI,IAAI,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QACpB,MAAM,IAAI,QAAQ,CAAC,2CAA2C,EAAE,8BAA8B,EAAE;YAC9F,QAAQ,EAAE,UAAU;YACpB,QAAQ,EAAE,CAAC,eAAe,CAAC;YAC3B,QAAQ,EAAE,CAAC,SAAS,CAAC;YACrB,SAAS,EAAE,CAAC,iEAAiE,CAAC;YAC9E,SAAS,EAAE,cAAc;SAC1B,CAAC,CAAC;IACL,CAAC;IACD,MAAM,QAAQ,GAAG,gBAAgB,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC;IACpD,IAAI,QAAQ,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QAC1B,MAAM,IAAI,QAAQ,CAAC,mCAAmC,EAAE,sBAAsB,EAAE;YAC9E,QAAQ,EAAE,UAAU;YACpB,QAAQ,EAAE,CAAC,0BAA0B,CAAC;YACtC,QAAQ,EAAE,CAAC,SAAS,CAAC;YACrB,SAAS,EAAE,CAAC,+BAA+B,CAAC;YAC5C,SAAS,EAAE,gBAAgB;SAC5B,CAAC,CAAC;IACL,CAAC;IACD,OAAO,mBAAmB,CAAC,IAAI,EAAE,EAAE,GAAG,gBAAgB,CAAC,QAAQ,EAAE,EAAE,QAAQ,EAAE,IAAI,CAAC,UAAU,CAAC,EAAE,CAAC,EAAE,EAAE,EAAE,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;AACnH,CAAC"}
|
|
@@ -0,0 +1,130 @@
|
|
|
1
|
+
import * as fs from "node:fs";
|
|
2
|
+
import * as path from "node:path";
|
|
3
|
+
import { CliError, EXIT_INPUT, EXIT_NEEDS_AGENT, EXIT_OK, EXIT_USAGE, directDir, exists, readText, } from "../../common.js";
|
|
4
|
+
import { applyPatchOperations } from "../../domain/script/patch/apply.js";
|
|
5
|
+
import { summarizeIssues, } from "../direct.js";
|
|
6
|
+
import { asList, strOf, } from "../../domain/script/shared.js";
|
|
7
|
+
import { loadScriptForEdit, validateSession, saveScriptSession, syncValidationResult, scriptSourceText, } from "./session.js";
|
|
8
|
+
import { tokenizeLine, parseDoLine, lineToOp, } from "./lib.js";
|
|
9
|
+
export async function commandDo(opts) {
|
|
10
|
+
const file = strOf(asList(opts["_args"])[0]);
|
|
11
|
+
let text;
|
|
12
|
+
if (!file || file === "-") {
|
|
13
|
+
// No pipe on an interactive terminal: reading fd 0 would block forever
|
|
14
|
+
// waiting for keyboard input. Fail fast instead.
|
|
15
|
+
if (process.stdin.isTTY) {
|
|
16
|
+
throw new CliError("DO BLOCKED: no input", "no verb script piped to stdin.", {
|
|
17
|
+
exitCode: EXIT_USAGE,
|
|
18
|
+
required: ["a file path or piped stdin"],
|
|
19
|
+
received: ["<tty, no pipe>"],
|
|
20
|
+
nextSteps: ["Pass a file (scriptctl do edits.txt) or pipe one (… | scriptctl do -)."],
|
|
21
|
+
errorCode: "DO_NO_INPUT",
|
|
22
|
+
});
|
|
23
|
+
}
|
|
24
|
+
try {
|
|
25
|
+
text = fs.readFileSync(0, "utf-8");
|
|
26
|
+
}
|
|
27
|
+
catch {
|
|
28
|
+
throw new CliError("DO BLOCKED: no input", "no verb script on stdin.", {
|
|
29
|
+
exitCode: EXIT_USAGE,
|
|
30
|
+
required: ["a file path or piped stdin"],
|
|
31
|
+
received: ["<no stdin>"],
|
|
32
|
+
nextSteps: ["Pass a file (scriptctl do edits.txt) or pipe one (… | scriptctl do -)."],
|
|
33
|
+
errorCode: "DO_NO_INPUT",
|
|
34
|
+
});
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
else {
|
|
38
|
+
if (!exists(file)) {
|
|
39
|
+
throw new CliError("DO BLOCKED: file not found", "verb-script file not found.", {
|
|
40
|
+
exitCode: EXIT_INPUT,
|
|
41
|
+
required: ["an existing file"],
|
|
42
|
+
received: [file],
|
|
43
|
+
nextSteps: ["Check the path, or pipe via stdin with `-`."],
|
|
44
|
+
errorCode: "DO_FILE_NOT_FOUND",
|
|
45
|
+
});
|
|
46
|
+
}
|
|
47
|
+
text = readText(file);
|
|
48
|
+
}
|
|
49
|
+
// Parse: one CLI verb per line; blank lines and `#` comments ignored. Line
|
|
50
|
+
// numbers are reported on parse errors so the agent can locate the bad line.
|
|
51
|
+
const ops = [];
|
|
52
|
+
const rawLines = text.split("\n");
|
|
53
|
+
for (let ln = 0; ln < rawLines.length; ln++) {
|
|
54
|
+
const trimmed = rawLines[ln].trim();
|
|
55
|
+
if (!trimmed || trimmed.startsWith("#"))
|
|
56
|
+
continue;
|
|
57
|
+
const tokens = tokenizeLine(rawLines[ln]);
|
|
58
|
+
if (tokens.length === 0)
|
|
59
|
+
continue;
|
|
60
|
+
try {
|
|
61
|
+
const { verb, args, flags } = parseDoLine(tokens);
|
|
62
|
+
ops.push(lineToOp(verb, args, flags));
|
|
63
|
+
}
|
|
64
|
+
catch (err) {
|
|
65
|
+
const detail = err instanceof CliError ? err.message : String(err);
|
|
66
|
+
throw new CliError(`DO BLOCKED: line ${ln + 1}`, `line ${ln + 1}: ${detail}`, {
|
|
67
|
+
exitCode: EXIT_USAGE,
|
|
68
|
+
required: ["a valid verb line"],
|
|
69
|
+
received: [rawLines[ln].trim()],
|
|
70
|
+
nextSteps: ["Fix this line; the whole script is one transaction (nothing is written until every line is valid)."],
|
|
71
|
+
errorCode: "DO_LINE_INVALID",
|
|
72
|
+
});
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
if (ops.length === 0) {
|
|
76
|
+
throw new CliError("DO BLOCKED: empty script", "no verb lines found.", {
|
|
77
|
+
exitCode: EXIT_USAGE,
|
|
78
|
+
required: ["at least one verb line"],
|
|
79
|
+
received: ["<empty>"],
|
|
80
|
+
nextSteps: ["Provide one CLI verb per line (without the leading `scriptctl`)."],
|
|
81
|
+
errorCode: "DO_EMPTY",
|
|
82
|
+
});
|
|
83
|
+
}
|
|
84
|
+
const apply = Boolean(opts["apply"]);
|
|
85
|
+
const workspace = strOf(opts["workspace_path"] || "workspace");
|
|
86
|
+
const session = await loadScriptForEdit(opts);
|
|
87
|
+
const script = session.script;
|
|
88
|
+
// One transaction: all ops applied in a single pass (renumber once at the
|
|
89
|
+
// end). Any op throwing aborts before any write — all-or-nothing.
|
|
90
|
+
const applied = applyPatchOperations(script, scriptSourceText(workspace), ops);
|
|
91
|
+
const head = [`lines: ${ops.length} op(s)`, `${apply ? "applied" : "would-apply"}: ${applied.length}`];
|
|
92
|
+
if (!apply) {
|
|
93
|
+
const validation = validateSession(session);
|
|
94
|
+
const passed = Boolean(validation["passed"]);
|
|
95
|
+
const report = {
|
|
96
|
+
title: "DO DRY-RUN (no write)",
|
|
97
|
+
op: "script.do.dry-run",
|
|
98
|
+
changed: false,
|
|
99
|
+
summary: `${ops.length} op(s) parsed; all apply cleanly — pass --apply to commit`,
|
|
100
|
+
result: [...head, `validation: ${passed ? "would pass" : "would need repair"}`, "dry-run: no write performed"],
|
|
101
|
+
warnings: passed ? [] : summarizeIssues(asList(validation["issues"])),
|
|
102
|
+
issues: summarizeIssues(asList(validation["issues"])),
|
|
103
|
+
artifacts: [session.artifactLabel],
|
|
104
|
+
next: [passed ? "Re-run with --apply to commit." : "Resolve validation issues before committing."],
|
|
105
|
+
};
|
|
106
|
+
return [report, passed ? EXIT_OK : EXIT_NEEDS_AGENT];
|
|
107
|
+
}
|
|
108
|
+
const [newRevision, idempotent] = await saveScriptSession(session, opts, "do");
|
|
109
|
+
const validation = validateSession(session);
|
|
110
|
+
await syncValidationResult(session, validation, newRevision);
|
|
111
|
+
const passed = Boolean(validation["passed"]);
|
|
112
|
+
const resultLines = [...head, `validation: ${passed ? "passed" : "needs repair"}`];
|
|
113
|
+
if (session.remote) {
|
|
114
|
+
resultLines.push(`revision: ${newRevision}`);
|
|
115
|
+
resultLines.push(`idempotent: ${String(idempotent).toLowerCase()}`);
|
|
116
|
+
}
|
|
117
|
+
const report = {
|
|
118
|
+
title: passed ? "DO APPLIED" : "DO APPLIED: Validation needs repair",
|
|
119
|
+
op: "script.do",
|
|
120
|
+
changed: applied.length > 0,
|
|
121
|
+
summary: `applied ${applied.length} op(s) as one transaction`,
|
|
122
|
+
result: resultLines,
|
|
123
|
+
warnings: passed ? [] : summarizeIssues(asList(validation["issues"])),
|
|
124
|
+
issues: summarizeIssues(asList(validation["issues"])),
|
|
125
|
+
artifacts: [session.artifactLabel, path.join(directDir(workspace), "validation.json")],
|
|
126
|
+
next: [passed ? "Continue editing the final script." : "Inspect issues and fix."],
|
|
127
|
+
};
|
|
128
|
+
return [report, passed ? EXIT_OK : EXIT_NEEDS_AGENT];
|
|
129
|
+
}
|
|
130
|
+
//# sourceMappingURL=do.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"do.js","sourceRoot":"","sources":["../../../src/usecases/script/do.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
import { EXIT_OK, } from "../../common.js";
|
|
2
|
+
import { parseInSelector, } from "../../domain/script/selector.js";
|
|
3
|
+
import { asList, strOf, } from "../../domain/script/shared.js";
|
|
4
|
+
import { loadScriptForEdit, parseBound, episodeCharCounts, } from "./session.js";
|
|
5
|
+
import { buildReport, synopsisPreview, episodeInSelector, } from "./lib.js";
|
|
6
|
+
export async function commandEpisodes(opts) {
|
|
7
|
+
const session = await loadScriptForEdit(opts);
|
|
8
|
+
const script = session.script;
|
|
9
|
+
const itemId = strOf(opts["id"]).trim();
|
|
10
|
+
const selector = parseInSelector(strOf(opts["in"]));
|
|
11
|
+
const minChars = parseBound(opts["min_chars"]);
|
|
12
|
+
const maxChars = parseBound(opts["max_chars"]);
|
|
13
|
+
const lines = [];
|
|
14
|
+
for (const ep of asList(script["episodes"])) {
|
|
15
|
+
const epId = strOf(ep["episode_id"]);
|
|
16
|
+
if (itemId && itemId !== epId)
|
|
17
|
+
continue;
|
|
18
|
+
const scenes = asList(ep["scenes"]);
|
|
19
|
+
if (!episodeInSelector(selector, epId, scenes))
|
|
20
|
+
continue;
|
|
21
|
+
let actionCount = 0;
|
|
22
|
+
const chars = episodeCharCounts(scenes);
|
|
23
|
+
for (const scene of scenes)
|
|
24
|
+
actionCount += asList(scene["actions"]).length;
|
|
25
|
+
if (minChars !== null && chars.total < minChars)
|
|
26
|
+
continue;
|
|
27
|
+
if (maxChars !== null && chars.total > maxChars)
|
|
28
|
+
continue;
|
|
29
|
+
const epSynopsis = strOf(ep["synopsis"]).trim();
|
|
30
|
+
const synopsisField = epSynopsis ? `, synopsis=${synopsisPreview(epSynopsis, 60)}` : "";
|
|
31
|
+
lines.push(`${ep["episode_id"]}: scenes=${scenes.length}, actions=${actionCount}, chars=${chars.total} (dialogue=${chars.dialogue}, action=${chars.action}), title=${ep["title"] || "-"}${synopsisField}`);
|
|
32
|
+
}
|
|
33
|
+
return [buildReport("query.episodes", "EPISODES", lines, session.artifactLabel, ["Use `scriptctl scenes --in <ep>` to drill in, or edit verbs to mutate."]), EXIT_OK];
|
|
34
|
+
}
|
|
35
|
+
// ----- scenes ---------------------------------------------------------------
|
|
36
|
+
//# sourceMappingURL=episodes.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"episodes.js","sourceRoot":"","sources":["../../../src/usecases/script/episodes.ts"],"names":[],"mappings":"AAKA,OAAO,EAIL,OAAO,GAWR,MAAM,iBAAiB,CAAC;AAIzB,OAAO,EAIL,eAAe,GAGhB,MAAM,iCAAiC,CAAC;AAwBzC,OAAO,EACL,MAAM,EAIN,KAAK,GACN,MAAM,+BAA+B,CAAC;AACvC,OAAO,EAEL,iBAAiB,EAC6B,UAAU,EAAE,iBAAiB,GAC5E,MAAM,cAAc,CAAC;AACtB,OAAO,EACwS,WAAW,EAAE,eAAe,EAAE,iBAAiB,GAC7V,MAAM,UAAU,CAAC;AAElB,MAAM,CAAC,KAAK,UAAU,eAAe,CAAC,IAAU;IAC9C,MAAM,OAAO,GAAG,MAAM,iBAAiB,CAAC,IAAI,CAAC,CAAC;IAC9C,MAAM,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;IAC9B,MAAM,MAAM,GAAG,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC;IACxC,MAAM,QAAQ,GAAG,eAAe,CAAC,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IACpD,MAAM,QAAQ,GAAG,UAAU,CAAC,IAAI,CAAC,WAAW,CAAC,CAAC,CAAC;IAC/C,MAAM,QAAQ,GAAG,UAAU,CAAC,IAAI,CAAC,WAAW,CAAC,CAAC,CAAC;IAC/C,MAAM,KAAK,GAAa,EAAE,CAAC;IAC3B,KAAK,MAAM,EAAE,IAAI,MAAM,CAAO,MAAM,CAAC,UAAU,CAAC,CAAC,EAAE,CAAC;QAClD,MAAM,IAAI,GAAG,KAAK,CAAC,EAAE,CAAC,YAAY,CAAC,CAAC,CAAC;QACrC,IAAI,MAAM,IAAI,MAAM,KAAK,IAAI;YAAE,SAAS;QACxC,MAAM,MAAM,GAAG,MAAM,CAAO,EAAE,CAAC,QAAQ,CAAC,CAAC,CAAC;QAC1C,IAAI,CAAC,iBAAiB,CAAC,QAAQ,EAAE,IAAI,EAAE,MAAM,CAAC;YAAE,SAAS;QACzD,IAAI,WAAW,GAAG,CAAC,CAAC;QACpB,MAAM,KAAK,GAAG,iBAAiB,CAAC,MAAM,CAAC,CAAC;QACxC,KAAK,MAAM,KAAK,IAAI,MAAM;YAAE,WAAW,IAAI,MAAM,CAAC,KAAK,CAAC,SAAS,CAAC,CAAC,CAAC,MAAM,CAAC;QAC3E,IAAI,QAAQ,KAAK,IAAI,IAAI,KAAK,CAAC,KAAK,GAAG,QAAQ;YAAE,SAAS;QAC1D,IAAI,QAAQ,KAAK,IAAI,IAAI,KAAK,CAAC,KAAK,GAAG,QAAQ;YAAE,SAAS;QAC1D,MAAM,UAAU,GAAG,KAAK,CAAC,EAAE,CAAC,UAAU,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC;QAChD,MAAM,aAAa,GAAG,UAAU,CAAC,CAAC,CAAC,cAAc,eAAe,CAAC,UAAU,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;QACxF,KAAK,CAAC,IAAI,CACR,GAAG,EAAE,CAAC,YAAY,CAAC,YAAY,MAAM,CAAC,MAAM,aAAa,WAAW,WAAW,KAAK,CAAC,KAAK,cAAc,KAAK,CAAC,QAAQ,YAAY,KAAK,CAAC,MAAM,YAAY,EAAE,CAAC,OAAO,CAAC,IAAI,GAAG,GAAG,aAAa,EAAE,CAC/L,CAAC;IACJ,CAAC;IACD,OAAO,CAAC,WAAW,CAAC,gBAAgB,EAAE,UAAU,EAAE,KAAK,EAAE,OAAO,CAAC,aAAa,EAC5E,CAAC,wEAAwE,CAAC,CAAC,EAAE,OAAO,CAAC,CAAC;AAC1F,CAAC;AAED,+EAA+E"}
|
|
@@ -0,0 +1,117 @@
|
|
|
1
|
+
import * as path from "node:path";
|
|
2
|
+
import { CliError, EXIT_INPUT, EXIT_NEEDS_AGENT, EXIT_OK, EXIT_USAGE, directDir, exists, readJson, sha256Text, } from "../../common.js";
|
|
3
|
+
import { validateScript } from "../../domain/script/validate.js";
|
|
4
|
+
import { ScriptOutputApiError, } from "../../infra/script-output-store.js";
|
|
5
|
+
import { readRunState, summarizeIssues, updateRunState, } from "../direct.js";
|
|
6
|
+
import { sortDeep } from "../../domain/direct-core.js";
|
|
7
|
+
import { asList, isDict, strOf, } from "../../domain/script/shared.js";
|
|
8
|
+
import { ScriptEditSession, scriptOutputClient, apiErrorToCli, currentRevisionOrZero, syncValidationResult, } from "./session.js";
|
|
9
|
+
export async function commandExport(opts) {
|
|
10
|
+
const workspace = strOf(opts["workspace_path"] || "workspace");
|
|
11
|
+
const force = Boolean(opts["force"]);
|
|
12
|
+
const scriptPath = path.join(directDir(workspace), "script.initial.json");
|
|
13
|
+
if (!exists(scriptPath)) {
|
|
14
|
+
throw new CliError("EXPORT BLOCKED: script.initial.json not found", "script.initial.json not found.", {
|
|
15
|
+
exitCode: EXIT_INPUT,
|
|
16
|
+
required: ["workspace/draft/scriptctl/direct/script.initial.json"],
|
|
17
|
+
received: [scriptPath],
|
|
18
|
+
nextSteps: ["Run scriptctl direct init first."],
|
|
19
|
+
});
|
|
20
|
+
}
|
|
21
|
+
const state = readRunState(workspace);
|
|
22
|
+
const provider = strOf(state["provider"]);
|
|
23
|
+
if (provider === "mock" && process.env.SCRIPTCTL_ALLOW_MOCK_EXPORT !== "1") {
|
|
24
|
+
const report = {
|
|
25
|
+
title: "EXPORT BLOCKED: Mock provider result",
|
|
26
|
+
result: ["script.initial.json was produced by --provider mock and was not exported."],
|
|
27
|
+
artifacts: [path.join(directDir(workspace), "run_state.json")],
|
|
28
|
+
next: ["Rerun init with --provider anthropic for deliverable conversion."],
|
|
29
|
+
};
|
|
30
|
+
return [report, EXIT_NEEDS_AGENT];
|
|
31
|
+
}
|
|
32
|
+
const validation = validateScript(workspace, scriptPath);
|
|
33
|
+
const blockingOrError = Boolean(validation["has_blocking"]) ||
|
|
34
|
+
asList(validation["issues"]).some((it) => isDict(it) && (it["severity"] === "blocking" || it["severity"] === "error"));
|
|
35
|
+
if (!validation["passed"] && (!force || blockingOrError)) {
|
|
36
|
+
const title = force
|
|
37
|
+
? "EXPORT BLOCKED: Validation errors require repair"
|
|
38
|
+
: "EXPORT BLOCKED: Validation needs agent repair";
|
|
39
|
+
const report = {
|
|
40
|
+
title,
|
|
41
|
+
result: ["script.initial.json was not exported."],
|
|
42
|
+
artifacts: [path.join(directDir(workspace), "validation.json")],
|
|
43
|
+
issues: summarizeIssues(asList(validation["issues"])),
|
|
44
|
+
next: ["Inspect issues and apply structured patches, then validate/export."],
|
|
45
|
+
};
|
|
46
|
+
return [report, EXIT_NEEDS_AGENT];
|
|
47
|
+
}
|
|
48
|
+
let script;
|
|
49
|
+
try {
|
|
50
|
+
script = readJson(scriptPath);
|
|
51
|
+
}
|
|
52
|
+
catch (exc) {
|
|
53
|
+
throw new CliError("EXPORT BLOCKED: script.initial.json invalid", "script.initial.json invalid.", {
|
|
54
|
+
exitCode: EXIT_INPUT,
|
|
55
|
+
required: ["valid script.initial.json"],
|
|
56
|
+
received: [`${scriptPath}: ${exc.message}`],
|
|
57
|
+
nextSteps: ["Fix script.initial.json or rerun direct init."],
|
|
58
|
+
errorCode: "SCRIPT_JSON_INVALID",
|
|
59
|
+
});
|
|
60
|
+
}
|
|
61
|
+
if (!isDict(script)) {
|
|
62
|
+
throw new CliError("EXPORT BLOCKED: script root invalid", "script root invalid.", {
|
|
63
|
+
exitCode: EXIT_USAGE,
|
|
64
|
+
required: ["script root object"],
|
|
65
|
+
received: [Array.isArray(script) ? "array" : typeof script],
|
|
66
|
+
nextSteps: ["Use a valid script document object."],
|
|
67
|
+
errorCode: "SCRIPT_ROOT_INVALID",
|
|
68
|
+
});
|
|
69
|
+
}
|
|
70
|
+
const client = scriptOutputClient(opts);
|
|
71
|
+
const baseRevision = await currentRevisionOrZero(client);
|
|
72
|
+
// Sorted-keys serialization mirrors Python json.dumps(sort_keys=True, separators=(",",":"))
|
|
73
|
+
const sortedScript = sortDeep(script);
|
|
74
|
+
const scriptHash = sha256Text(JSON.stringify(sortedScript));
|
|
75
|
+
const requestId = strOf(opts["request_id"]).trim() || `scriptctl-direct-export:${scriptHash}`;
|
|
76
|
+
let replaceRes;
|
|
77
|
+
try {
|
|
78
|
+
replaceRes = await client.replaceScript({
|
|
79
|
+
requestId,
|
|
80
|
+
baseRevision,
|
|
81
|
+
script,
|
|
82
|
+
source: "ctl",
|
|
83
|
+
});
|
|
84
|
+
}
|
|
85
|
+
catch (exc) {
|
|
86
|
+
if (exc instanceof ScriptOutputApiError) {
|
|
87
|
+
throw apiErrorToCli("SCRIPT API BLOCKED: Export write failed", exc);
|
|
88
|
+
}
|
|
89
|
+
throw exc;
|
|
90
|
+
}
|
|
91
|
+
const revision = Number(replaceRes["revision"] ?? 0);
|
|
92
|
+
const remoteSession = new ScriptEditSession({
|
|
93
|
+
workspace,
|
|
94
|
+
script,
|
|
95
|
+
client,
|
|
96
|
+
projectGroupNo: client.projectGroupNo,
|
|
97
|
+
revision,
|
|
98
|
+
});
|
|
99
|
+
await syncValidationResult(remoteSession, validation, revision);
|
|
100
|
+
const outputLabel = remoteSession.artifactLabel;
|
|
101
|
+
updateRunState(workspace, { status: "exported", output_path: outputLabel });
|
|
102
|
+
const report = {
|
|
103
|
+
title: "EXPORT COMPLETE: Final script stored in DB",
|
|
104
|
+
result: [
|
|
105
|
+
`validation: ${validation["passed"] ? "passed" : "forced"}`,
|
|
106
|
+
`base_revision: ${baseRevision}`,
|
|
107
|
+
`revision: ${revision}`,
|
|
108
|
+
`idempotent: ${String(Boolean(replaceRes["idempotent"])).toLowerCase()}`,
|
|
109
|
+
],
|
|
110
|
+
artifacts: [outputLabel, path.join(directDir(workspace), "validation.json")],
|
|
111
|
+
next: ["Proceed to downstream asset or footage stages."],
|
|
112
|
+
};
|
|
113
|
+
return [report, EXIT_OK];
|
|
114
|
+
}
|
|
115
|
+
// sortDeep is the canonical helper in domain/direct-core; re-exported here for
|
|
116
|
+
// back-compat with existing importers of `usecases/script`.
|
|
117
|
+
//# sourceMappingURL=export.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"export.js","sourceRoot":"","sources":["../../../src/usecases/script/export.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
import { CliError, EXIT_USAGE, } from "../../common.js";
|
|
2
|
+
import { parseAnyAddress, } from "../../domain/script/address.js";
|
|
3
|
+
import { asList, } from "../../domain/script/shared.js";
|
|
4
|
+
import { applySingleScriptOp, } from "./lib.js";
|
|
5
|
+
export async function commandInsert(opts) {
|
|
6
|
+
const args = asList(opts["_args"]);
|
|
7
|
+
if (args.length < 1) {
|
|
8
|
+
throw new CliError("VERB BLOCKED: Insert address missing", "Insert address missing.", {
|
|
9
|
+
exitCode: EXIT_USAGE,
|
|
10
|
+
required: ["<addr>: ep_NNN/scn_NNN (action insert) or ep_NNN (scene insert)"],
|
|
11
|
+
received: ["<empty>"],
|
|
12
|
+
nextSteps: ["Example: scriptctl insert ep_001/scn_001 --type action --content \"...\""],
|
|
13
|
+
errorCode: "ADDRESS_MISSING",
|
|
14
|
+
});
|
|
15
|
+
}
|
|
16
|
+
const addr = parseAnyAddress(args[0]);
|
|
17
|
+
// Per-kind flag whitelist. Silently dropping mismatched flags hid two
|
|
18
|
+
// real bugs:
|
|
19
|
+
// - scene insert was ignoring --scene-id (the user lost custom IDs).
|
|
20
|
+
// - mixing action + scene insert flags (`--type` with episode addr, or
|
|
21
|
+
// `--location` with scene addr) ran the wrong dispatch silently.
|
|
22
|
+
const flagsUsed = {
|
|
23
|
+
type: opts["type"] !== undefined,
|
|
24
|
+
content: opts["content"] !== undefined,
|
|
25
|
+
actor: (opts["actor_id"] ?? opts["actor"]) !== undefined,
|
|
26
|
+
speaker: (opts["speaker_id"] ?? opts["speaker"]) !== undefined,
|
|
27
|
+
location: opts["location"] !== undefined,
|
|
28
|
+
time: opts["time"] !== undefined,
|
|
29
|
+
space: opts["space"] !== undefined,
|
|
30
|
+
"scene-id": opts["scene_id"] !== undefined,
|
|
31
|
+
};
|
|
32
|
+
function rejectFlags(kind, allowed) {
|
|
33
|
+
const allow = new Set(allowed);
|
|
34
|
+
const bad = [];
|
|
35
|
+
for (const f of Object.keys(flagsUsed)) {
|
|
36
|
+
if (flagsUsed[f] && !allow.has(f))
|
|
37
|
+
bad.push(`--${f}`);
|
|
38
|
+
}
|
|
39
|
+
if (bad.length > 0) {
|
|
40
|
+
throw new CliError("VERB BLOCKED: flag not applicable", `${bad.join(", ")} cannot be used with ${kind} insert.`, {
|
|
41
|
+
exitCode: EXIT_USAGE,
|
|
42
|
+
required: [`for ${kind} insert: ${allowed.map((f) => `--${f}`).join(" / ")}`],
|
|
43
|
+
received: bad,
|
|
44
|
+
nextSteps: ["Drop the unsupported flag(s) and retry."],
|
|
45
|
+
errorCode: "INSERT_FLAG_INVALID",
|
|
46
|
+
});
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
if (addr.kind === "scene") {
|
|
50
|
+
rejectFlags("action", ["type", "content", "actor", "speaker"]);
|
|
51
|
+
return applySingleScriptOp(opts, {
|
|
52
|
+
op: "action.insert",
|
|
53
|
+
at: args[0],
|
|
54
|
+
type: opts["type"],
|
|
55
|
+
content: opts["content"],
|
|
56
|
+
at_index: opts["at_index"] ?? opts["at"],
|
|
57
|
+
before: opts["before"],
|
|
58
|
+
after: opts["after"],
|
|
59
|
+
actor_id: opts["actor_id"] ?? opts["actor"],
|
|
60
|
+
speaker_id: opts["speaker_id"] ?? opts["speaker"],
|
|
61
|
+
});
|
|
62
|
+
}
|
|
63
|
+
if (addr.kind === "episode") {
|
|
64
|
+
rejectFlags("scene", ["location", "time", "space", "scene-id"]);
|
|
65
|
+
return applySingleScriptOp(opts, {
|
|
66
|
+
op: "scene.insert",
|
|
67
|
+
at: addr.episodeId,
|
|
68
|
+
location: opts["location"],
|
|
69
|
+
time: opts["time"],
|
|
70
|
+
space: opts["space"],
|
|
71
|
+
// Forward --scene-id (was previously silently dropped — scene.insert op
|
|
72
|
+
// reads `scene_id` to honor user-supplied ids for round-trip stability).
|
|
73
|
+
scene_id: opts["scene_id"],
|
|
74
|
+
at_index: opts["at_index"] ?? opts["at"],
|
|
75
|
+
before: opts["before"],
|
|
76
|
+
after: opts["after"],
|
|
77
|
+
});
|
|
78
|
+
}
|
|
79
|
+
throw new CliError("VERB BLOCKED: insert cannot operate on this address", "insert cannot operate on this address.", {
|
|
80
|
+
exitCode: EXIT_USAGE,
|
|
81
|
+
required: ["ep_NNN (scene insert) or ep_NNN/scn_NNN (action insert)"],
|
|
82
|
+
received: [args[0]],
|
|
83
|
+
nextSteps: ["Use an episode or scene address."],
|
|
84
|
+
errorCode: "ADDRESS_UNSUPPORTED",
|
|
85
|
+
});
|
|
86
|
+
}
|
|
87
|
+
//# sourceMappingURL=insert.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"insert.js","sourceRoot":"","sources":["../../../src/usecases/script/insert.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import { EXIT_OK, } from "../../common.js";
|
|
2
|
+
import { asList, strOf, } from "../../domain/script/shared.js";
|
|
3
|
+
import { loadScriptForEdit, validateSession, } from "./session.js";
|
|
4
|
+
import { buildReport, } from "./lib.js";
|
|
5
|
+
export async function commandIssues(opts) {
|
|
6
|
+
const session = await loadScriptForEdit(opts);
|
|
7
|
+
const severityFilter = strOf(opts["severity"]).trim();
|
|
8
|
+
const codeFilter = strOf(opts["code"]).trim();
|
|
9
|
+
const validation = validateSession(session);
|
|
10
|
+
const lines = [];
|
|
11
|
+
for (const issue of asList(validation["issues"])) {
|
|
12
|
+
if (severityFilter && severityFilter !== strOf(issue["severity"]))
|
|
13
|
+
continue;
|
|
14
|
+
if (codeFilter && codeFilter !== strOf(issue["code"]))
|
|
15
|
+
continue;
|
|
16
|
+
const whereParts = [];
|
|
17
|
+
for (const k of ["episode", "scene", "action_index"]) {
|
|
18
|
+
if (issue[k] !== null && issue[k] !== undefined)
|
|
19
|
+
whereParts.push(strOf(issue[k]));
|
|
20
|
+
}
|
|
21
|
+
const where = whereParts.join(" ");
|
|
22
|
+
lines.push(`${issue["severity"]} ${issue["code"]}: ${issue["summary"]}${where ? ` [${where}]` : ""}`);
|
|
23
|
+
}
|
|
24
|
+
return [buildReport("query.issues", "ISSUES", lines, session.artifactLabel, ["Use the relevant edit verb to repair each issue."]), EXIT_OK];
|
|
25
|
+
}
|
|
26
|
+
// ----- refs (unified reverse lookup) ----------------------------------------
|
|
27
|
+
//# sourceMappingURL=issues.js.map
|