@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.mjs CHANGED
@@ -2662,14 +2662,24 @@ function normalizeDocumentSourceTreePaths(nodes) {
2662
2662
  group.sort((left, right) => left.order - right.order || left.id.localeCompare(right.id));
2663
2663
  }
2664
2664
  const result = [];
2665
- const visit = (node, path) => {
2666
- const next = { ...node, path };
2665
+ const visited = /* @__PURE__ */ new Set();
2666
+ const visit = (node, path, ancestors, parentId) => {
2667
+ if (visited.has(node.id) || ancestors.has(node.id)) return;
2668
+ visited.add(node.id);
2669
+ const next = { ...node, parentId, path };
2667
2670
  result.push(next);
2668
2671
  const children = byParent.get(node.id) ?? [];
2669
- children.forEach((child, index) => visit(child, `${path}.${index + 1}`));
2672
+ const nextAncestors = new Set(ancestors);
2673
+ nextAncestors.add(node.id);
2674
+ children.forEach((child, index) => visit(child, `${path}.${index + 1}`, nextAncestors, node.id));
2670
2675
  };
2671
2676
  const roots = byParent.get(void 0) ?? [];
2672
- roots.forEach((root, index) => visit(root, String(index + 1)));
2677
+ roots.forEach((root, index) => visit(root, String(index + 1), /* @__PURE__ */ new Set(), void 0));
2678
+ for (const node of nodes) {
2679
+ if (!visited.has(node.id)) {
2680
+ visit(node, String(result.length + 1), /* @__PURE__ */ new Set(), void 0);
2681
+ }
2682
+ }
2673
2683
  return result;
2674
2684
  }
2675
2685
  function buildDocumentSourceTree(sourceSpans, documentId) {
@@ -9000,6 +9010,8 @@ var ORGANIZABLE_KINDS = [
9000
9010
  ];
9001
9011
  var ORGANIZATION_TOP_LEVEL_BATCH_SIZE = 80;
9002
9012
  var ORGANIZATION_CHILD_CONTEXT_LIMIT = 4;
9013
+ var ORGANIZER_MAX_SOURCE_SPANS = 400;
9014
+ var ORGANIZER_MAX_TOP_LEVEL_NODES = 18;
9003
9015
  var SourceTreeOrganizationSchema = z41.object({
9004
9016
  labels: z41.array(z41.object({
9005
9017
  nodeId: z41.string(),
@@ -9126,7 +9138,7 @@ function semanticGroupNodeId(documentId, kind, title, childNodeIds) {
9126
9138
  ].join(":");
9127
9139
  }
9128
9140
  function looksLikeDeclarationsStart(node) {
9129
- return /\bdeclarations?\s+(page|schedule)\b/i.test(sourceNodeText(node));
9141
+ return /(^|\b)declarations?\b/i.test(sourceNodeText(node)) && !/\bforms?\s+and\s+endorsements?\b/i.test(sourceNodeText(node));
9130
9142
  }
9131
9143
  function looksLikeDeclarationsContinuation(node) {
9132
9144
  const text = sourceNodeText(node);
@@ -9134,7 +9146,8 @@ function looksLikeDeclarationsContinuation(node) {
9134
9146
  }
9135
9147
  function looksLikePolicyFormStart(node) {
9136
9148
  const text = sourceNodeText(node);
9137
- 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);
9149
+ const excerpt = cleanText(node.textExcerpt, "");
9150
+ 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);
9138
9151
  }
9139
9152
  function looksLikePolicyFormContinuation(node) {
9140
9153
  const text = sourceNodeText(node);
@@ -9538,6 +9551,24 @@ function nodesByParent(sourceTree) {
9538
9551
  function sourceTreeRootId(sourceTree) {
9539
9552
  return sourceTree.find((node) => node.kind === "document")?.id;
9540
9553
  }
9554
+ function rootChildren(sourceTree) {
9555
+ const byParent = nodesByParent(sourceTree);
9556
+ const rootId = sourceTreeRootId(sourceTree);
9557
+ return (byParent.get(rootId) ?? []).filter((node) => node.kind !== "document");
9558
+ }
9559
+ function hasDeterministicSemanticOutline(sourceTree) {
9560
+ const children = rootChildren(sourceTree);
9561
+ const semanticCount = children.filter(
9562
+ (node) => node.kind === "page_group" || node.kind === "form" || node.kind === "endorsement" || node.kind === "section" || node.kind === "schedule"
9563
+ ).length;
9564
+ return semanticCount >= 2 || children.some((node) => node.title === "Declarations") || children.some((node) => node.title === "Policy Form") || children.some((node) => node.title === "Endorsements");
9565
+ }
9566
+ function shouldRunSourceTreeOrganizer(sourceTree, sourceSpans) {
9567
+ const topLevelCount = rootChildren(sourceTree).length;
9568
+ if (sourceSpans.length > ORGANIZER_MAX_SOURCE_SPANS) return false;
9569
+ if (topLevelCount > ORGANIZER_MAX_TOP_LEVEL_NODES) return false;
9570
+ return !hasDeterministicSemanticOutline(sourceTree);
9571
+ }
9541
9572
  function organizationBatches(sourceTree) {
9542
9573
  const byParent = nodesByParent(sourceTree);
9543
9574
  const rootId = sourceTreeRootId(sourceTree);
@@ -9819,7 +9850,7 @@ function materializeDocument(params) {
9819
9850
  }
9820
9851
  async function runSourceTreeExtraction(params) {
9821
9852
  const sourceSpans = normalizeSourceSpans(params.sourceSpans);
9822
- let sourceTree = buildDocumentSourceTree(sourceSpans, params.id);
9853
+ let sourceTree = applySemanticPageGrouping(buildDocumentSourceTree(sourceSpans, params.id));
9823
9854
  const warnings = [];
9824
9855
  let modelCalls = 0;
9825
9856
  let callsWithUsage = 0;
@@ -9841,40 +9872,43 @@ async function runSourceTreeExtraction(params) {
9841
9872
  }
9842
9873
  params.trackUsage(usage, report);
9843
9874
  };
9844
- try {
9845
- const organizations = [];
9846
- const batches = organizationBatches(sourceTree);
9847
- for (const [batchIndex, batch] of batches.entries()) {
9848
- const budget = params.resolveBudget("extraction_source_tree", 4096);
9849
- const startedAt = Date.now();
9850
- const response = await safeGenerateObject(
9851
- params.generateObject,
9852
- {
9853
- prompt: buildOrganizationPrompt(batch),
9854
- schema: SourceTreeOrganizationSchema,
9855
- maxTokens: budget.maxTokens,
9875
+ if (shouldRunSourceTreeOrganizer(sourceTree, sourceSpans)) {
9876
+ try {
9877
+ const organizations = [];
9878
+ const batches = organizationBatches(sourceTree);
9879
+ for (const [batchIndex, batch] of batches.entries()) {
9880
+ const budget = params.resolveBudget("extraction_source_tree", 4096);
9881
+ const startedAt = Date.now();
9882
+ const response = await safeGenerateObject(
9883
+ params.generateObject,
9884
+ {
9885
+ prompt: buildOrganizationPrompt(batch),
9886
+ schema: SourceTreeOrganizationSchema,
9887
+ maxTokens: budget.maxTokens,
9888
+ taskKind: "extraction_source_tree",
9889
+ budgetDiagnostics: budget,
9890
+ providerOptions: params.providerOptions
9891
+ },
9892
+ {
9893
+ fallback: { labels: [], groups: [] },
9894
+ log: params.log
9895
+ }
9896
+ );
9897
+ localTrack(response.usage, {
9856
9898
  taskKind: "extraction_source_tree",
9857
- budgetDiagnostics: budget,
9858
- providerOptions: { ...params.providerOptions, sourceSpans }
9859
- },
9860
- {
9861
- fallback: { labels: [], groups: [] },
9862
- log: params.log
9863
- }
9864
- );
9865
- localTrack(response.usage, {
9866
- taskKind: "extraction_source_tree",
9867
- label: batches.length > 1 ? `source_tree_organizer_${batchIndex + 1}` : "source_tree_organizer",
9868
- maxTokens: budget.maxTokens,
9869
- durationMs: Date.now() - startedAt
9870
- });
9871
- organizations.push(response.object);
9899
+ label: batches.length > 1 ? `source_tree_organizer_${batchIndex + 1}` : "source_tree_organizer",
9900
+ maxTokens: budget.maxTokens,
9901
+ durationMs: Date.now() - startedAt
9902
+ });
9903
+ organizations.push(response.object);
9904
+ }
9905
+ sourceTree = applyOrganization(sourceTree, mergeOrganizationResults(organizations));
9906
+ } catch (error) {
9907
+ warnings.push(`Source-tree organizer failed; deterministic tree used (${error instanceof Error ? error.message : String(error)})`);
9872
9908
  }
9873
- sourceTree = applyOrganization(sourceTree, mergeOrganizationResults(organizations));
9874
- } catch (error) {
9875
- warnings.push(`Source-tree organizer failed; deterministic tree used (${error instanceof Error ? error.message : String(error)})`);
9909
+ } else {
9910
+ await params.log?.("Deterministic source tree ready; skipped model organizer");
9876
9911
  }
9877
- sourceTree = applySemanticPageGrouping(sourceTree);
9878
9912
  const deterministicProfile = buildDeterministicOperationalProfile({
9879
9913
  sourceTree,
9880
9914
  sourceSpans