@thanh01.pmt/curriculum-kit 1.4.20 → 1.4.21
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/index.cjs +126 -46
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +36 -2
- package/dist/index.d.ts +36 -2
- package/dist/index.mjs +124 -47
- package/dist/index.mjs.map +1 -1
- package/dist/storage/index.cjs +21 -9
- package/dist/storage/index.cjs.map +1 -1
- package/dist/storage/index.d.cts +11 -1
- package/dist/storage/index.d.ts +11 -1
- package/dist/storage/index.mjs +21 -10
- package/dist/storage/index.mjs.map +1 -1
- package/dist/workflow/index.cjs.map +1 -1
- package/dist/workflow/index.mjs.map +1 -1
- package/package.json +1 -1
package/dist/index.cjs
CHANGED
|
@@ -1513,7 +1513,8 @@ function buildSlideBatchPrompt(params) {
|
|
|
1513
1513
|
skillPrompt,
|
|
1514
1514
|
language = "Vietnamese",
|
|
1515
1515
|
languageDirective = "",
|
|
1516
|
-
headingDirective = ""
|
|
1516
|
+
headingDirective = "",
|
|
1517
|
+
groundContext = ""
|
|
1517
1518
|
} = params;
|
|
1518
1519
|
const slidesSpec = clusterSlides.map((s) => `
|
|
1519
1520
|
- Slide ${s.slideIndex} [Phase: ${s.lessonPhase}] -> Layout: "${s.layoutId}"
|
|
@@ -1526,7 +1527,11 @@ function buildSlideBatchPrompt(params) {
|
|
|
1526
1527
|
const systemPrompt = `
|
|
1527
1528
|
${skillPrompt}
|
|
1528
1529
|
|
|
1529
|
-
|
|
1530
|
+
${groundContext ? `---
|
|
1531
|
+
### PROJECT GROUND CONTEXT (framework, style guide, glossary, canonical knowledge \u2014 author from these):
|
|
1532
|
+
${groundContext}
|
|
1533
|
+
|
|
1534
|
+
---` : ""}
|
|
1530
1535
|
### OPERATIONAL GROUND RULES FOR CHUNK GENERATION:
|
|
1531
1536
|
${languageDirective}
|
|
1532
1537
|
${headingDirective}
|
|
@@ -1604,6 +1609,7 @@ __export(slideProductionWorkflow_exports, {
|
|
|
1604
1609
|
HybridPipelineError: () => exports.HybridPipelineError,
|
|
1605
1610
|
SlideBlueprintArraySchema: () => exports.SlideBlueprintArraySchema,
|
|
1606
1611
|
SlideBlueprintItemSchema: () => exports.SlideBlueprintItemSchema,
|
|
1612
|
+
emitUsage: () => emitUsage,
|
|
1607
1613
|
executeSlideProductionWorkflow: () => executeSlideProductionWorkflow,
|
|
1608
1614
|
extractJsonArray: () => extractJsonArray,
|
|
1609
1615
|
validateHybridDeckSlides: () => validateHybridDeckSlides
|
|
@@ -1656,15 +1662,28 @@ function validateHybridDeckSlides(slides, blueprint) {
|
|
|
1656
1662
|
});
|
|
1657
1663
|
return v.slice(0, 10);
|
|
1658
1664
|
}
|
|
1665
|
+
function emitUsage(usage, onProgress) {
|
|
1666
|
+
if (!onProgress || !usage) return;
|
|
1667
|
+
const promptTokens = usage.promptTokens ?? usage.inputTokens ?? 0;
|
|
1668
|
+
const completionTokens = usage.completionTokens ?? usage.outputTokens ?? 0;
|
|
1669
|
+
if (promptTokens === 0 && completionTokens === 0) return;
|
|
1670
|
+
onProgress("@illustrator", JSON.stringify({
|
|
1671
|
+
promptTokens,
|
|
1672
|
+
completionTokens,
|
|
1673
|
+
totalTokens: usage.totalTokens ?? promptTokens + completionTokens,
|
|
1674
|
+
reasoningTokens: usage.reasoningTokens ?? 0
|
|
1675
|
+
}), { type: "usage" });
|
|
1676
|
+
}
|
|
1659
1677
|
async function inferTextJson(schema, systemPrompt, userPrompt, options, label) {
|
|
1660
1678
|
const model = getAIModel(options.modelOptions);
|
|
1661
1679
|
try {
|
|
1662
|
-
const { text, finishReason } = await ai.generateText({
|
|
1680
|
+
const { text, finishReason, usage } = await ai.generateText({
|
|
1663
1681
|
model,
|
|
1664
1682
|
system: systemPrompt || void 0,
|
|
1665
1683
|
prompt: userPrompt,
|
|
1666
1684
|
maxOutputTokens: options.maxOutputTokens ?? 65536
|
|
1667
1685
|
});
|
|
1686
|
+
emitUsage(usage, options.onProgress);
|
|
1668
1687
|
const extracted = extractJsonArray(text);
|
|
1669
1688
|
if (!("value" in extracted) || extracted.value === void 0) {
|
|
1670
1689
|
console.warn(
|
|
@@ -1685,12 +1704,13 @@ async function inferTextJson(schema, systemPrompt, userPrompt, options, label) {
|
|
|
1685
1704
|
async function inferStructured(schema, systemPrompt, userPrompt, options, label) {
|
|
1686
1705
|
try {
|
|
1687
1706
|
const model = getAIModel(options.modelOptions);
|
|
1688
|
-
const { object } = await ai.generateObject({
|
|
1707
|
+
const { object, usage } = await ai.generateObject({
|
|
1689
1708
|
model,
|
|
1690
1709
|
schema,
|
|
1691
1710
|
system: systemPrompt || void 0,
|
|
1692
1711
|
prompt: userPrompt
|
|
1693
1712
|
});
|
|
1713
|
+
emitUsage(usage, options.onProgress);
|
|
1694
1714
|
const validated = schema.safeParse(object);
|
|
1695
1715
|
if (validated.success) return validated.data;
|
|
1696
1716
|
console.warn(
|
|
@@ -1705,7 +1725,9 @@ async function inferStructured(schema, systemPrompt, userPrompt, options, label)
|
|
|
1705
1725
|
const messages = [
|
|
1706
1726
|
{ role: "user", content: [systemPrompt, userPrompt].filter(Boolean).join("\n\n") }
|
|
1707
1727
|
];
|
|
1708
|
-
const raw = await runCurriculumAIInference(messages, options.satelliteContext || "", options.runnerOptions)
|
|
1728
|
+
const raw = await runCurriculumAIInference(messages, options.satelliteContext || "", options.runnerOptions, (token, type) => {
|
|
1729
|
+
if (type === "usage") options.onProgress?.("@illustrator", token, { type: "usage" });
|
|
1730
|
+
});
|
|
1709
1731
|
const fenceMatch = raw.match(/```(?:json)?\s*([\s\S]*?)\s*```/i);
|
|
1710
1732
|
const candidate = (fenceMatch ? fenceMatch[1] : raw).trim();
|
|
1711
1733
|
let parsed;
|
|
@@ -1738,7 +1760,7 @@ function normalizeBlueprintItems(items) {
|
|
|
1738
1760
|
}));
|
|
1739
1761
|
}
|
|
1740
1762
|
function buildHybridDeckPrompts(params) {
|
|
1741
|
-
const { lessonFlow, blueprint, skillPrompt, language, languageDirective, headingDirective } = params;
|
|
1763
|
+
const { lessonFlow, blueprint, skillPrompt, language, languageDirective, headingDirective, groundContext } = params;
|
|
1742
1764
|
const blueprintText = JSON.stringify(
|
|
1743
1765
|
blueprint.map((s) => ({
|
|
1744
1766
|
slideIndex: s.slideIndex,
|
|
@@ -1757,6 +1779,7 @@ function buildHybridDeckPrompts(params) {
|
|
|
1757
1779
|
${p.content}`).join("\n\n") : lessonFlow.rawContent;
|
|
1758
1780
|
const systemPrompt = [
|
|
1759
1781
|
skillPrompt,
|
|
1782
|
+
groundContext || "",
|
|
1760
1783
|
languageDirective,
|
|
1761
1784
|
headingDirective,
|
|
1762
1785
|
`
|
|
@@ -1821,7 +1844,8 @@ async function runHybridPipeline(ctx) {
|
|
|
1821
1844
|
skillPrompt,
|
|
1822
1845
|
language,
|
|
1823
1846
|
languageDirective,
|
|
1824
|
-
headingDirective
|
|
1847
|
+
headingDirective,
|
|
1848
|
+
groundContext: options.groundContext
|
|
1825
1849
|
});
|
|
1826
1850
|
let slides = null;
|
|
1827
1851
|
let lastViolations = [];
|
|
@@ -1970,7 +1994,8 @@ ${p.content}`).join("\n\n") : lessonFlow.rawContent.slice(0, 3500);
|
|
|
1970
1994
|
skillPrompt,
|
|
1971
1995
|
language,
|
|
1972
1996
|
languageDirective,
|
|
1973
|
-
headingDirective
|
|
1997
|
+
headingDirective,
|
|
1998
|
+
groundContext: options.groundContext
|
|
1974
1999
|
});
|
|
1975
2000
|
try {
|
|
1976
2001
|
const batchSlides = await pRetry__default.default(
|
|
@@ -9312,6 +9337,21 @@ var STANDARD_SOT_FILES = [
|
|
|
9312
9337
|
"ART_DIRECTION.md",
|
|
9313
9338
|
"ALIGNMENT_MATRIX.md"
|
|
9314
9339
|
];
|
|
9340
|
+
function atomicWriteFileSync(targetPath, content) {
|
|
9341
|
+
const dir = path3__default.default.dirname(targetPath);
|
|
9342
|
+
if (!fs2__default.default.existsSync(dir)) fs2__default.default.mkdirSync(dir, { recursive: true });
|
|
9343
|
+
const tmpPath = path3__default.default.join(dir, `.${path3__default.default.basename(targetPath)}.${process.pid}.${Date.now()}.${crypto__default.default.randomBytes(4).toString("hex")}.tmp`);
|
|
9344
|
+
try {
|
|
9345
|
+
fs2__default.default.writeFileSync(tmpPath, content, "utf-8");
|
|
9346
|
+
fs2__default.default.renameSync(tmpPath, targetPath);
|
|
9347
|
+
} catch (err) {
|
|
9348
|
+
try {
|
|
9349
|
+
if (fs2__default.default.existsSync(tmpPath)) fs2__default.default.unlinkSync(tmpPath);
|
|
9350
|
+
} catch {
|
|
9351
|
+
}
|
|
9352
|
+
throw err;
|
|
9353
|
+
}
|
|
9354
|
+
}
|
|
9315
9355
|
var FileSystemCurriculumAdapter = class {
|
|
9316
9356
|
baseDir;
|
|
9317
9357
|
constructor(options = {}) {
|
|
@@ -9450,7 +9490,7 @@ var FileSystemCurriculumAdapter = class {
|
|
|
9450
9490
|
if (oldContent !== content) {
|
|
9451
9491
|
const historyDir = path3__default.default.join(projectDir, ".history", relPath);
|
|
9452
9492
|
fs2__default.default.mkdirSync(historyDir, { recursive: true });
|
|
9453
|
-
|
|
9493
|
+
atomicWriteFileSync(path3__default.default.join(historyDir, `${Date.now()}.md`), oldContent);
|
|
9454
9494
|
const versions = fs2__default.default.readdirSync(historyDir).filter((f) => f.endsWith(".md")).sort();
|
|
9455
9495
|
while (versions.length > 10) {
|
|
9456
9496
|
fs2__default.default.unlinkSync(path3__default.default.join(historyDir, versions.shift()));
|
|
@@ -9460,19 +9500,15 @@ var FileSystemCurriculumAdapter = class {
|
|
|
9460
9500
|
console.warn("[FileSystemCurriculumAdapter] version history snapshot failed:", histErr?.message || histErr);
|
|
9461
9501
|
}
|
|
9462
9502
|
}
|
|
9463
|
-
|
|
9503
|
+
atomicWriteFileSync(targetPath, content);
|
|
9464
9504
|
const filename = path3__default.default.basename(relPath);
|
|
9465
9505
|
const match = filename.match(/(LESSON|ACT|QUIZ|SLIDE|GUIDE|HANDOUT|WKS|EXT)_(U\d+_M\d+_L\d+)\.md/i);
|
|
9466
9506
|
if (match) {
|
|
9467
9507
|
const lessonId = match[2].toUpperCase();
|
|
9468
|
-
|
|
9469
|
-
if (!fs2__default.default.existsSync(lessonsDir)) {
|
|
9470
|
-
fs2__default.default.mkdirSync(lessonsDir, { recursive: true });
|
|
9471
|
-
}
|
|
9472
|
-
fs2__default.default.writeFileSync(path3__default.default.join(lessonsDir, filename), content, "utf-8");
|
|
9508
|
+
atomicWriteFileSync(path3__default.default.join(projectDir, "lessons", lessonId, filename), content);
|
|
9473
9509
|
const legacyContentDir = path3__default.default.join(projectDir, "_content", lessonId);
|
|
9474
9510
|
if (fs2__default.default.existsSync(legacyContentDir)) {
|
|
9475
|
-
|
|
9511
|
+
atomicWriteFileSync(path3__default.default.join(legacyContentDir, filename), content);
|
|
9476
9512
|
}
|
|
9477
9513
|
}
|
|
9478
9514
|
}
|
|
@@ -9563,7 +9599,7 @@ ${lessonTable}
|
|
|
9563
9599
|
}
|
|
9564
9600
|
const stateFile = path3__default.default.join(pipelineDir, "state.json");
|
|
9565
9601
|
state.updatedAt = (/* @__PURE__ */ new Date()).toISOString();
|
|
9566
|
-
|
|
9602
|
+
atomicWriteFileSync(stateFile, JSON.stringify(state, null, 2));
|
|
9567
9603
|
}
|
|
9568
9604
|
async updateArtifactState(projectId, taskId, artifactType, update) {
|
|
9569
9605
|
const current = await this.getPipelineState(projectId);
|
|
@@ -11263,6 +11299,13 @@ var DEFAULT_LESSON_PRIORITIES = [
|
|
|
11263
11299
|
"Learning Objectives & Evidence",
|
|
11264
11300
|
"Activity Sequence"
|
|
11265
11301
|
];
|
|
11302
|
+
var SATELLITE_LESSON_PRIORITIES = [
|
|
11303
|
+
"Artifact Contract",
|
|
11304
|
+
"A. Lesson Design Plan",
|
|
11305
|
+
"B. Lesson Flow",
|
|
11306
|
+
"Learning Objectives & Evidence",
|
|
11307
|
+
"Activity Sequence"
|
|
11308
|
+
];
|
|
11266
11309
|
var DEFAULT_KX_PRIORITIES = [
|
|
11267
11310
|
"Key Terms",
|
|
11268
11311
|
"Concept Narratives",
|
|
@@ -26094,6 +26137,21 @@ ${renderHorizonPromptBlock(horizon)}`;
|
|
|
26094
26137
|
} catch (hErr) {
|
|
26095
26138
|
console.warn(`[produceSingleLesson] Notice: Curriculum Horizon extraction:`, hErr?.message || hErr);
|
|
26096
26139
|
}
|
|
26140
|
+
const buildGroundTruthBlock = () => {
|
|
26141
|
+
const parts = [];
|
|
26142
|
+
if (expositionContext) {
|
|
26143
|
+
parts.push(`### KNOWLEDGE_EXPOSITION (CANONICAL KNOWLEDGE \u2014 teach from this, do not contradict)
|
|
26144
|
+
${expositionContext}`);
|
|
26145
|
+
}
|
|
26146
|
+
if (effectiveRefPack) {
|
|
26147
|
+
parts.push(`### REFERENCE PACK GROUND TRUTH
|
|
26148
|
+
${effectiveRefPack}`);
|
|
26149
|
+
}
|
|
26150
|
+
return parts.length > 0 ? `
|
|
26151
|
+
|
|
26152
|
+
[GROUND TRUTH]:
|
|
26153
|
+
${parts.join("\n\n")}` : "";
|
|
26154
|
+
};
|
|
26097
26155
|
const glossaryBlock = glossaryContext ? `
|
|
26098
26156
|
|
|
26099
26157
|
[GLOSSARY TERMS (use these exact definitions)]:
|
|
@@ -26101,21 +26159,14 @@ ${glossaryContext}` : "";
|
|
|
26101
26159
|
const standardsBlock = standardsContext ? `
|
|
26102
26160
|
|
|
26103
26161
|
${standardsContext}` : "";
|
|
26104
|
-
const expositionBlock = expositionContext ? `
|
|
26105
|
-
|
|
26106
|
-
[KNOWLEDGE_EXPOSITION (CANONICAL KNOWLEDGE \u2014 teach from this, do not contradict)]:
|
|
26107
|
-
${expositionContext}` : "";
|
|
26108
26162
|
const sessionSliceBlock = sessionSliceContext ? `
|
|
26109
26163
|
|
|
26110
26164
|
${sessionSliceContext}` : "";
|
|
26111
|
-
const assembleCommonContext = (
|
|
26165
|
+
const assembleCommonContext = (sg) => `${baseContextPrefix}
|
|
26112
26166
|
|
|
26113
26167
|
[CONTENT STYLE GUIDE EXCERPT]:
|
|
26114
|
-
${sg}
|
|
26115
|
-
|
|
26116
|
-
[REFERENCE PACK GROUND TRUTH]:
|
|
26117
|
-
${ref}${standardsBlock}${glossaryBlock}${expositionBlock}${sessionSliceBlock}${horizonBlock}`;
|
|
26118
|
-
let commonContext = assembleCommonContext(effectiveRefPack, effectiveStyleGuide);
|
|
26168
|
+
${sg}${standardsBlock}${glossaryBlock}${buildGroundTruthBlock()}${sessionSliceBlock}${horizonBlock}`;
|
|
26169
|
+
let commonContext = assembleCommonContext(effectiveStyleGuide);
|
|
26119
26170
|
const MAX_COMPOSITE_PROMPT_CHARS = 3e4;
|
|
26120
26171
|
const runnerOptions = options.customInference ? { customInference: options.customInference } : {};
|
|
26121
26172
|
if (commonContext.length > MAX_COMPOSITE_PROMPT_CHARS && effectiveRefPack.length > 1e3) {
|
|
@@ -26126,14 +26177,14 @@ ${ref}${standardsBlock}${glossaryBlock}${expositionBlock}${sessionSliceBlock}${h
|
|
|
26126
26177
|
],
|
|
26127
26178
|
budget: 1e3
|
|
26128
26179
|
}).excerpt;
|
|
26129
|
-
commonContext = assembleCommonContext(
|
|
26180
|
+
commonContext = assembleCommonContext(effectiveStyleGuide);
|
|
26130
26181
|
}
|
|
26131
26182
|
if (commonContext.length > MAX_COMPOSITE_PROMPT_CHARS && effectiveStyleGuide.length > 1e3) {
|
|
26132
26183
|
effectiveStyleGuide = buildSectionAwareExcerpt(styleGuide, {
|
|
26133
26184
|
priorities: ["Voice & Tone", "Standard Terminology (Glossary)"],
|
|
26134
26185
|
budget: 1e3
|
|
26135
26186
|
}).excerpt;
|
|
26136
|
-
commonContext = assembleCommonContext(
|
|
26187
|
+
commonContext = assembleCommonContext(effectiveStyleGuide);
|
|
26137
26188
|
}
|
|
26138
26189
|
onProgress?.("@content", `[CONTEXT] Composite prompt ready (${commonContext.length} chars, adaptive budget <= ${MAX_COMPOSITE_PROMPT_CHARS})`, {
|
|
26139
26190
|
type: "progress",
|
|
@@ -26484,7 +26535,7 @@ ${currentContent}` }],
|
|
|
26484
26535
|
});
|
|
26485
26536
|
}
|
|
26486
26537
|
const lessonExcerptResult = buildSectionAwareExcerpt(lessonContent, {
|
|
26487
|
-
priorities:
|
|
26538
|
+
priorities: SATELLITE_LESSON_PRIORITIES,
|
|
26488
26539
|
budget: 12e3,
|
|
26489
26540
|
sectionLanguageContract: slcMarkdown,
|
|
26490
26541
|
artifactType: "LESSON"
|
|
@@ -26674,6 +26725,7 @@ ${buildHeadingDirective("QUIZ", slcMarkdown, targetLang)}`;
|
|
|
26674
26725
|
} catch {
|
|
26675
26726
|
}
|
|
26676
26727
|
const { executeSlideProductionWorkflow: executeSlideProductionWorkflow2 } = await Promise.resolve().then(() => (init_slideProductionWorkflow(), slideProductionWorkflow_exports));
|
|
26728
|
+
const slideGroundContext = `${commonContext}${symbolLedgerBlock}`;
|
|
26677
26729
|
const workflowResult = await executeSlideProductionWorkflow2({
|
|
26678
26730
|
lessonMarkdown: lessonContent || "",
|
|
26679
26731
|
lessonCode,
|
|
@@ -26682,6 +26734,7 @@ ${buildHeadingDirective("QUIZ", slcMarkdown, targetLang)}`;
|
|
|
26682
26734
|
language: targetLang || "Vietnamese",
|
|
26683
26735
|
languageDirective,
|
|
26684
26736
|
headingDirective: buildHeadingDirective("SLIDE", slcMarkdown, targetLang),
|
|
26737
|
+
groundContext: slideGroundContext,
|
|
26685
26738
|
satelliteContext,
|
|
26686
26739
|
runnerOptions,
|
|
26687
26740
|
onProgress: (agent, msg, meta) => {
|
|
@@ -26690,7 +26743,7 @@ ${buildHeadingDirective("QUIZ", slcMarkdown, targetLang)}`;
|
|
|
26690
26743
|
});
|
|
26691
26744
|
let deckJson = workflowResult.deckJson;
|
|
26692
26745
|
const markdownWrapper = workflowResult.markdownWrapper;
|
|
26693
|
-
let validation = presentationKitAi?.validateHtmlSlideDeck ? presentationKitAi.validateHtmlSlideDeck(deckJson, true) : deckJson && Array.isArray(deckJson.slides) ? { valid: true, score: 95, issues: [], slideCount: deckJson.slides.length} : { valid: false, score: 0, issues: [{ message: "Malformed JSON slide deck" }]
|
|
26746
|
+
let validation = presentationKitAi?.validateHtmlSlideDeck ? presentationKitAi.validateHtmlSlideDeck(deckJson, true) : deckJson && Array.isArray(deckJson.slides) ? { valid: true, score: 95, issues: [], slideCount: deckJson.slides.length} : { valid: false, score: 0, issues: [{ message: "Malformed JSON slide deck" }]};
|
|
26694
26747
|
await storage.saveArtifact(projectId, slideRelPath, markdownWrapper);
|
|
26695
26748
|
producedArtifacts.push(`SLIDE_${lessonCode}.md`);
|
|
26696
26749
|
if (deckJson) {
|
|
@@ -26710,21 +26763,45 @@ ${buildHeadingDirective("QUIZ", slcMarkdown, targetLang)}`;
|
|
|
26710
26763
|
}
|
|
26711
26764
|
}
|
|
26712
26765
|
}
|
|
26713
|
-
const
|
|
26714
|
-
const
|
|
26715
|
-
|
|
26716
|
-
|
|
26717
|
-
|
|
26718
|
-
|
|
26719
|
-
|
|
26720
|
-
|
|
26721
|
-
|
|
26722
|
-
|
|
26723
|
-
|
|
26724
|
-
|
|
26725
|
-
|
|
26726
|
-
|
|
26727
|
-
|
|
26766
|
+
const structuralOk = Boolean(validation.valid && (validation.score ?? 100) >= 80);
|
|
26767
|
+
const structuralScore = validation.score ?? (structuralOk ? 95 : 50);
|
|
26768
|
+
const gateMode = gateModeFor(gates, "SLIDE");
|
|
26769
|
+
if (!structuralOk) {
|
|
26770
|
+
await storage.updateArtifactState(projectId, lessonCode, "SLIDE", {
|
|
26771
|
+
state: "rejected",
|
|
26772
|
+
generatedAt: (/* @__PURE__ */ new Date()).toISOString(),
|
|
26773
|
+
contentHash: computeContentHash(markdownWrapper),
|
|
26774
|
+
review: {
|
|
26775
|
+
decision: "NEEDS_REVISION",
|
|
26776
|
+
reviewedBy: "@heuristic-linter",
|
|
26777
|
+
reviewedAt: (/* @__PURE__ */ new Date()).toISOString(),
|
|
26778
|
+
score: structuralScore,
|
|
26779
|
+
critique: `HTML Slide Deck failed schema validation: ${(validation.issues || []).map((i) => i.message).join("; ")}`
|
|
26780
|
+
}
|
|
26781
|
+
});
|
|
26782
|
+
onProgress?.("@reviewer", `\u26A0\uFE0F SLIDE structural pre-check FAILED (${structuralScore}/100) [html-deck schema issues]`);
|
|
26783
|
+
} else {
|
|
26784
|
+
await storage.updateArtifactState(projectId, lessonCode, "SLIDE", {
|
|
26785
|
+
state: gateMode === "LLM_JUDGE" ? "pending" : "completed",
|
|
26786
|
+
generatedAt: (/* @__PURE__ */ new Date()).toISOString(),
|
|
26787
|
+
contentHash: computeContentHash(markdownWrapper)
|
|
26788
|
+
});
|
|
26789
|
+
onProgress?.("@reviewer", gateMode === "LLM_JUDGE" ? `\u2705 SLIDE structural pre-check PASS (${structuralScore}/100) \u2014 handing content review to LLM-as-Judge gate` : `\u2705 SLIDE structural pre-check PASS (${structuralScore}/100) [gate=${gateMode}, no LLM judge]`);
|
|
26790
|
+
const deckTextForJudge = Array.isArray(deckJson?.slides) ? deckJson.slides.map((s, i) => {
|
|
26791
|
+
const slotLines = Object.entries(s.slots || {}).map(([k, v]) => {
|
|
26792
|
+
if (Array.isArray(v)) return `- ${k}:
|
|
26793
|
+
${v.map((item) => typeof item === "object" ? ` - ${JSON.stringify(item)}` : ` - ${item}`).join("\n")}`;
|
|
26794
|
+
if (v && typeof v === "object") return `- ${k}: ${JSON.stringify(v, null, 1)}`;
|
|
26795
|
+
return `- ${k}: ${v}`;
|
|
26796
|
+
}).join("\n");
|
|
26797
|
+
return `## Slide ${i + 1} [${s.layoutId}]
|
|
26798
|
+
${slotLines}
|
|
26799
|
+
|
|
26800
|
+
Presenter Notes:
|
|
26801
|
+
${s.notes || "(none)"}`;
|
|
26802
|
+
}).join("\n\n") : String(markdownWrapper);
|
|
26803
|
+
await judgeSat("SLIDE", deckTextForJudge);
|
|
26804
|
+
}
|
|
26728
26805
|
} else {
|
|
26729
26806
|
const canonicalSlideTemplate = loadCurriculumTemplate("SLIDE_template.md");
|
|
26730
26807
|
const templateScaffold = canonicalSlideTemplate || `---
|
|
@@ -31873,6 +31950,7 @@ exports.RoadmapInputSchema = RoadmapInputSchema;
|
|
|
31873
31950
|
exports.RotationStationSchema = RotationStationSchema;
|
|
31874
31951
|
exports.RubricCriteriaSchema = RubricCriteriaSchema;
|
|
31875
31952
|
exports.RubricSchema = RubricSchema;
|
|
31953
|
+
exports.SATELLITE_LESSON_PRIORITIES = SATELLITE_LESSON_PRIORITIES;
|
|
31876
31954
|
exports.SCIENCE_LAB_TEMPLATE = SCIENCE_LAB_TEMPLATE;
|
|
31877
31955
|
exports.SELF_LAB_TEMPLATE = SELF_LAB_TEMPLATE;
|
|
31878
31956
|
exports.SLIDE_CANONICAL_METHODOLOGY = SLIDE_CANONICAL_METHODOLOGY;
|
|
@@ -31922,6 +32000,7 @@ exports.analystTools = analystTools;
|
|
|
31922
32000
|
exports.analyzeProjectCreationIntent = analyzeProjectCreationIntent;
|
|
31923
32001
|
exports.assertAcyclic = assertAcyclic;
|
|
31924
32002
|
exports.assessorTools = assessorTools;
|
|
32003
|
+
exports.atomicWriteFileSync = atomicWriteFileSync;
|
|
31925
32004
|
exports.auditCurriculumQualityFlow = auditCurriculumQualityFlow;
|
|
31926
32005
|
exports.auditQualityReport = auditQualityReport;
|
|
31927
32006
|
exports.buildActivityPrompt = buildActivityPrompt;
|
|
@@ -31969,6 +32048,7 @@ exports.createStreamChunkExtractor = createStreamChunkExtractor;
|
|
|
31969
32048
|
exports.curateMediaLedger = curateMediaLedger;
|
|
31970
32049
|
exports.designerTools = designerTools;
|
|
31971
32050
|
exports.detectProjectPedagogy = detectProjectPedagogy;
|
|
32051
|
+
exports.emitUsage = emitUsage;
|
|
31972
32052
|
exports.ensureExpositionForLesson = ensureExpositionForLesson;
|
|
31973
32053
|
exports.ensureKnowledgeExposition = ensureKnowledgeExposition;
|
|
31974
32054
|
exports.evaluateStandardsCoverage = evaluateStandardsCoverage;
|