@claritylabs/cl-sdk 3.0.10 → 3.0.11

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.js CHANGED
@@ -3017,14 +3017,24 @@ function normalizeDocumentSourceTreePaths(nodes) {
3017
3017
  group.sort((left, right) => left.order - right.order || left.id.localeCompare(right.id));
3018
3018
  }
3019
3019
  const result = [];
3020
- const visit = (node, path) => {
3021
- const next = { ...node, path };
3020
+ const visited = /* @__PURE__ */ new Set();
3021
+ const visit = (node, path, ancestors, parentId) => {
3022
+ if (visited.has(node.id) || ancestors.has(node.id)) return;
3023
+ visited.add(node.id);
3024
+ const next = { ...node, parentId, path };
3022
3025
  result.push(next);
3023
3026
  const children = byParent.get(node.id) ?? [];
3024
- children.forEach((child, index) => visit(child, `${path}.${index + 1}`));
3027
+ const nextAncestors = new Set(ancestors);
3028
+ nextAncestors.add(node.id);
3029
+ children.forEach((child, index) => visit(child, `${path}.${index + 1}`, nextAncestors, node.id));
3025
3030
  };
3026
3031
  const roots = byParent.get(void 0) ?? [];
3027
- roots.forEach((root, index) => visit(root, String(index + 1)));
3032
+ roots.forEach((root, index) => visit(root, String(index + 1), /* @__PURE__ */ new Set(), void 0));
3033
+ for (const node of nodes) {
3034
+ if (!visited.has(node.id)) {
3035
+ visit(node, String(result.length + 1), /* @__PURE__ */ new Set(), void 0);
3036
+ }
3037
+ }
3028
3038
  return result;
3029
3039
  }
3030
3040
  function buildDocumentSourceTree(sourceSpans, documentId) {
@@ -9347,6 +9357,8 @@ var ORGANIZABLE_KINDS = [
9347
9357
  ];
9348
9358
  var ORGANIZATION_TOP_LEVEL_BATCH_SIZE = 80;
9349
9359
  var ORGANIZATION_CHILD_CONTEXT_LIMIT = 4;
9360
+ var ORGANIZER_MAX_SOURCE_SPANS = 400;
9361
+ var ORGANIZER_MAX_TOP_LEVEL_NODES = 18;
9350
9362
  var SourceTreeOrganizationSchema = import_zod41.z.object({
9351
9363
  labels: import_zod41.z.array(import_zod41.z.object({
9352
9364
  nodeId: import_zod41.z.string(),
@@ -9473,7 +9485,7 @@ function semanticGroupNodeId(documentId, kind, title, childNodeIds) {
9473
9485
  ].join(":");
9474
9486
  }
9475
9487
  function looksLikeDeclarationsStart(node) {
9476
- return /\bdeclarations?\s+(page|schedule)\b/i.test(sourceNodeText(node));
9488
+ return /(^|\b)declarations?\b/i.test(sourceNodeText(node)) && !/\bforms?\s+and\s+endorsements?\b/i.test(sourceNodeText(node));
9477
9489
  }
9478
9490
  function looksLikeDeclarationsContinuation(node) {
9479
9491
  const text = sourceNodeText(node);
@@ -9481,7 +9493,8 @@ function looksLikeDeclarationsContinuation(node) {
9481
9493
  }
9482
9494
  function looksLikePolicyFormStart(node) {
9483
9495
  const text = sourceNodeText(node);
9484
- return /\bpolicy form\b/i.test(node.title) || /\btechnology errors?\s*&?\s*omissions\b/i.test(text) && /\bplease read this entire policy carefully\b/i.test(text) || /\bform\s+[A-Z]{2,}-[A-Z0-9-]+\s+\d{2}\s+\d{2}\b/i.test(text);
9496
+ const excerpt = cleanText(node.textExcerpt, "");
9497
+ return /\bpolicy form\b/i.test(node.title) || /^policy\s+form\b/i.test(excerpt) || /\btechnology errors?\s*&?\s*omissions\b/i.test(text) && /\bplease read this entire policy carefully\b/i.test(text) || /\bform\s+[A-Z]{2,}-[A-Z0-9-]+\s+\d{2}\s+\d{2}\b/i.test(text);
9485
9498
  }
9486
9499
  function looksLikePolicyFormContinuation(node) {
9487
9500
  const text = sourceNodeText(node);
@@ -9885,6 +9898,24 @@ function nodesByParent(sourceTree) {
9885
9898
  function sourceTreeRootId(sourceTree) {
9886
9899
  return sourceTree.find((node) => node.kind === "document")?.id;
9887
9900
  }
9901
+ function rootChildren(sourceTree) {
9902
+ const byParent = nodesByParent(sourceTree);
9903
+ const rootId = sourceTreeRootId(sourceTree);
9904
+ return (byParent.get(rootId) ?? []).filter((node) => node.kind !== "document");
9905
+ }
9906
+ function hasDeterministicSemanticOutline(sourceTree) {
9907
+ const children = rootChildren(sourceTree);
9908
+ const semanticCount = children.filter(
9909
+ (node) => node.kind === "page_group" || node.kind === "form" || node.kind === "endorsement" || node.kind === "section" || node.kind === "schedule"
9910
+ ).length;
9911
+ return semanticCount >= 2 || children.some((node) => node.title === "Declarations") || children.some((node) => node.title === "Policy Form") || children.some((node) => node.title === "Endorsements");
9912
+ }
9913
+ function shouldRunSourceTreeOrganizer(sourceTree, sourceSpans) {
9914
+ const topLevelCount = rootChildren(sourceTree).length;
9915
+ if (sourceSpans.length > ORGANIZER_MAX_SOURCE_SPANS) return false;
9916
+ if (topLevelCount > ORGANIZER_MAX_TOP_LEVEL_NODES) return false;
9917
+ return !hasDeterministicSemanticOutline(sourceTree);
9918
+ }
9888
9919
  function organizationBatches(sourceTree) {
9889
9920
  const byParent = nodesByParent(sourceTree);
9890
9921
  const rootId = sourceTreeRootId(sourceTree);
@@ -10166,7 +10197,7 @@ function materializeDocument(params) {
10166
10197
  }
10167
10198
  async function runSourceTreeExtraction(params) {
10168
10199
  const sourceSpans = normalizeSourceSpans(params.sourceSpans);
10169
- let sourceTree = buildDocumentSourceTree(sourceSpans, params.id);
10200
+ let sourceTree = applySemanticPageGrouping(buildDocumentSourceTree(sourceSpans, params.id));
10170
10201
  const warnings = [];
10171
10202
  let modelCalls = 0;
10172
10203
  let callsWithUsage = 0;
@@ -10188,40 +10219,43 @@ async function runSourceTreeExtraction(params) {
10188
10219
  }
10189
10220
  params.trackUsage(usage, report);
10190
10221
  };
10191
- try {
10192
- const organizations = [];
10193
- const batches = organizationBatches(sourceTree);
10194
- for (const [batchIndex, batch] of batches.entries()) {
10195
- const budget = params.resolveBudget("extraction_source_tree", 4096);
10196
- const startedAt = Date.now();
10197
- const response = await safeGenerateObject(
10198
- params.generateObject,
10199
- {
10200
- prompt: buildOrganizationPrompt(batch),
10201
- schema: SourceTreeOrganizationSchema,
10202
- maxTokens: budget.maxTokens,
10222
+ if (shouldRunSourceTreeOrganizer(sourceTree, sourceSpans)) {
10223
+ try {
10224
+ const organizations = [];
10225
+ const batches = organizationBatches(sourceTree);
10226
+ for (const [batchIndex, batch] of batches.entries()) {
10227
+ const budget = params.resolveBudget("extraction_source_tree", 4096);
10228
+ const startedAt = Date.now();
10229
+ const response = await safeGenerateObject(
10230
+ params.generateObject,
10231
+ {
10232
+ prompt: buildOrganizationPrompt(batch),
10233
+ schema: SourceTreeOrganizationSchema,
10234
+ maxTokens: budget.maxTokens,
10235
+ taskKind: "extraction_source_tree",
10236
+ budgetDiagnostics: budget,
10237
+ providerOptions: params.providerOptions
10238
+ },
10239
+ {
10240
+ fallback: { labels: [], groups: [] },
10241
+ log: params.log
10242
+ }
10243
+ );
10244
+ localTrack(response.usage, {
10203
10245
  taskKind: "extraction_source_tree",
10204
- budgetDiagnostics: budget,
10205
- providerOptions: { ...params.providerOptions, sourceSpans }
10206
- },
10207
- {
10208
- fallback: { labels: [], groups: [] },
10209
- log: params.log
10210
- }
10211
- );
10212
- localTrack(response.usage, {
10213
- taskKind: "extraction_source_tree",
10214
- label: batches.length > 1 ? `source_tree_organizer_${batchIndex + 1}` : "source_tree_organizer",
10215
- maxTokens: budget.maxTokens,
10216
- durationMs: Date.now() - startedAt
10217
- });
10218
- organizations.push(response.object);
10246
+ label: batches.length > 1 ? `source_tree_organizer_${batchIndex + 1}` : "source_tree_organizer",
10247
+ maxTokens: budget.maxTokens,
10248
+ durationMs: Date.now() - startedAt
10249
+ });
10250
+ organizations.push(response.object);
10251
+ }
10252
+ sourceTree = applyOrganization(sourceTree, mergeOrganizationResults(organizations));
10253
+ } catch (error) {
10254
+ warnings.push(`Source-tree organizer failed; deterministic tree used (${error instanceof Error ? error.message : String(error)})`);
10219
10255
  }
10220
- sourceTree = applyOrganization(sourceTree, mergeOrganizationResults(organizations));
10221
- } catch (error) {
10222
- warnings.push(`Source-tree organizer failed; deterministic tree used (${error instanceof Error ? error.message : String(error)})`);
10256
+ } else {
10257
+ await params.log?.("Deterministic source tree ready; skipped model organizer");
10223
10258
  }
10224
- sourceTree = applySemanticPageGrouping(sourceTree);
10225
10259
  const deterministicProfile = buildDeterministicOperationalProfile({
10226
10260
  sourceTree,
10227
10261
  sourceSpans