@ai-react-markdown/engine 2.5.2 → 2.5.4

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 CHANGED
@@ -270,6 +270,26 @@ var import_micromark_util_html_tag_name = require("micromark-util-html-tag-name"
270
270
  var import_micromark_util_normalize_identifier = require("micromark-util-normalize-identifier");
271
271
  var TYPE6_NAMES = new Set(import_micromark_util_html_tag_name.htmlBlockNames);
272
272
  var TABLE_PART_NAMES = /* @__PURE__ */ new Set(["td", "th", "tr", "tbody", "thead", "tfoot", "caption", "col", "colgroup"]);
273
+ var DOCUMENT_STRUCTURE_NAMES = /* @__PURE__ */ new Set(["html", "head", "body", "frameset"]);
274
+ var RETROACTIVE_OPENERS = [
275
+ "<!doctype",
276
+ "<html",
277
+ "<head",
278
+ "<body",
279
+ "<frameset",
280
+ "</html",
281
+ "</head",
282
+ "</body",
283
+ "</frameset"
284
+ ];
285
+ function tailCarriesRetroactive(text) {
286
+ const lower = text.toLowerCase();
287
+ for (let i = lower.indexOf("<"); i !== -1; i = lower.indexOf("<", i + 1)) {
288
+ const rest = lower.slice(i);
289
+ for (const op of RETROACTIVE_OPENERS) if (rest.startsWith(op)) return true;
290
+ }
291
+ return false;
292
+ }
273
293
  var HTML_BREAKOUT_TAGS = /* @__PURE__ */ new Set([
274
294
  "b",
275
295
  "big",
@@ -316,7 +336,8 @@ var HTML_BREAKOUT_TAGS = /* @__PURE__ */ new Set([
316
336
  "ul",
317
337
  "var"
318
338
  ]);
319
- var HTML_INTEGRATION_POINTS = ["foreignobject", "desc", "mi", "mo", "mn", "ms", "mtext", "annotation-xml"];
339
+ var HTML_INTEGRATION_POINTS = ["foreignobject", "desc", "title", "mi", "mo", "mn", "ms", "mtext", "annotation-xml"];
340
+ var FOREIGN_ROOT_NAMES = ["svg", "math"];
320
341
  var TYPE1_NAMES = /* @__PURE__ */ new Set(["script", "pre", "style", "textarea"]);
321
342
  var RAW_TEXT_ELEMENTS = /* @__PURE__ */ new Set([
322
343
  "script",
@@ -335,6 +356,7 @@ var RAW_TEXT_ELEMENTS = /* @__PURE__ */ new Set([
335
356
  ]);
336
357
  var TYPE6_START_RE = /^<\/?([A-Za-z][A-Za-z0-9-]*)(?:[ \t\r]|\/?>|$)/;
337
358
  var TYPE1_START_RE = /^<(script|pre|style|textarea)(?:[ \t\r]|>|$)/i;
359
+ var TYPE1_CLOSE_RE = /<\/(?:script|pre|style|textarea)>/i;
338
360
  var TYPE7_LINE_RE = /^(?:<[A-Za-z][A-Za-z0-9-]*(?:[ \t\r][^>]*|\/)?>|<\/[A-Za-z][A-Za-z0-9-]*[ \t\r]*>)[ \t\r]*$/;
339
361
  var t7Name = (line) => /^<\/?([A-Za-z][A-Za-z0-9-]*)/.exec(line)[1];
340
362
  var VOID_TAGS = /* @__PURE__ */ new Set([
@@ -485,6 +507,7 @@ function freshCheckpoint(defListEnabled, mathFlow, referenceTaint) {
485
507
  piOpen: false,
486
508
  bogusOpen: false,
487
509
  rawTextOpen: null,
510
+ scriptDataEscaped: false,
488
511
  declOpen: false,
489
512
  cdataOpen: false,
490
513
  inFence: false,
@@ -510,7 +533,9 @@ function freshCheckpoint(defListEnabled, mathFlow, referenceTaint) {
510
533
  tagAcrossLines: false,
511
534
  tagAcrossLinesIndent: 0,
512
535
  tagAcrossLinesState: "outside",
513
- htmlFlowReal: false
536
+ htmlFlowReal: false,
537
+ type1FlowOpen: false,
538
+ rawTextInline: false
514
539
  };
515
540
  }
516
541
  function isPlausibleLinkDefRest(rest) {
@@ -655,8 +680,9 @@ function computeFreezeBoundary(text, options, resume) {
655
680
  if (tailLine) return !canBecomeDdLine(tailLine.text, false);
656
681
  return false;
657
682
  };
683
+ const tailRetroactive = tailLine !== null && tailCarriesRetroactive(tailLine.text);
658
684
  let boundary = 0;
659
- for (let i = cp.candidates.length - 1; i >= 0; i--) {
685
+ for (let i = cp.candidates.length - 1; i >= 0 && !tailRetroactive; i--) {
660
686
  const c = cp.candidates[i];
661
687
  if (!c.htmlBalanced || c.hazard || c.seamRisk) continue;
662
688
  if (c.offset > cp.phasePoisonedAt) continue;
@@ -722,7 +748,7 @@ function processConfirmedLine(cp, ln, text) {
722
748
  cp.htmlSeamPending = false;
723
749
  }
724
750
  }
725
- const inForeignContent = () => (cp.tagBalance.get("svg") ?? 0) > 0 || (cp.tagBalance.get("math") ?? 0) > 0;
751
+ const inForeignContent = () => FOREIGN_ROOT_NAMES.some((name) => (cp.tagBalance.get(name) ?? 0) > 0);
726
752
  const honoursSelfClosing = (tag) => {
727
753
  if (tag === "svg" || tag === "math") return true;
728
754
  if (!inForeignContent() || HTML_BREAKOUT_TAGS.has(tag)) return false;
@@ -734,14 +760,37 @@ function processConfirmedLine(cp, ln, text) {
734
760
  for (const ip of HTML_INTEGRATION_POINTS) if ((cp.tagBalance.get(ip) ?? 0) > 0) return true;
735
761
  return false;
736
762
  };
763
+ const popForeignRoots = () => {
764
+ for (const name of FOREIGN_ROOT_NAMES) {
765
+ const count = cp.tagBalance.get(name) ?? 0;
766
+ if (count > 0) {
767
+ cp.tagBalance.set(name, 0);
768
+ cp.openTotal -= count;
769
+ }
770
+ }
771
+ };
772
+ const noteBreakout = (tag, closing) => {
773
+ if (closing || cp.rawTextOpen !== null) return;
774
+ if (HTML_BREAKOUT_TAGS.has(tag) && !htmlRulesApply()) popForeignRoots();
775
+ };
737
776
  const applyTag = (tag, closing) => {
738
777
  if (cp.rawTextOpen !== null) {
778
+ if (cp.scriptDataEscaped && !closing && tag === "script") {
779
+ cp.phasePoisonedAt = Math.min(cp.phasePoisonedAt, ln.start);
780
+ }
739
781
  if (!(closing && tag === cp.rawTextOpen)) return;
740
782
  cp.rawTextOpen = null;
741
- } else if (!closing && RAW_TEXT_ELEMENTS.has(tag) && htmlRulesApply()) {
742
- cp.rawTextOpen = tag;
743
- if (tag === "plaintext") cp.phasePoisonedAt = Math.min(cp.phasePoisonedAt, ln.start);
783
+ cp.scriptDataEscaped = false;
784
+ } else {
785
+ noteBreakout(tag, closing);
786
+ if (!closing && RAW_TEXT_ELEMENTS.has(tag) && htmlRulesApply()) {
787
+ cp.rawTextOpen = tag;
788
+ cp.scriptDataEscaped = false;
789
+ cp.rawTextInline = !cp.htmlFlowReal;
790
+ if (tag === "plaintext") cp.phasePoisonedAt = Math.min(cp.phasePoisonedAt, ln.start);
791
+ }
744
792
  }
793
+ if (DOCUMENT_STRUCTURE_NAMES.has(tag)) cp.phasePoisonedAt = 0;
745
794
  if (closing) {
746
795
  const count = cp.tagBalance.get(tag) ?? 0;
747
796
  if (count > 0) {
@@ -852,15 +901,22 @@ function processConfirmedLine(cp, ln, text) {
852
901
  cp.candidates.push({
853
902
  offset: Math.min(ln.end + 1, text.length),
854
903
  blankRun: cp.blankRun,
855
- htmlBalanced: cp.openTotal === 0 && !cp.commentOpen && !cp.piOpen && !cp.declOpen && !cp.cdataOpen && !cp.bogusOpen,
904
+ // `type1FlowOpen`: an unterminated type-1 block swallows this blank
905
+ // and everything after it as RAW content, so nothing here is a block
906
+ // boundary at all. Its tags are invisible to the balance scan
907
+ // (`rawTextOpen` suppresses them), which is exactly why `openTotal`
908
+ // reads 0 and the candidate looked safe.
909
+ htmlBalanced: cp.openTotal === 0 && !cp.commentOpen && !cp.piOpen && !cp.declOpen && !cp.cdataOpen && !cp.bogusOpen && !cp.type1FlowOpen,
856
910
  hazard: cp.hazardVerdict,
857
911
  seamRisk: cp.htmlSeamPending,
858
912
  defListSettled: null
859
913
  });
860
914
  cp.paragraphHasUnpairedRun = false;
861
915
  cp.openBracket = null;
862
- cp.htmlFlowSinceBlank = false;
863
- cp.htmlFlowReal = false;
916
+ if (!cp.type1FlowOpen) {
917
+ cp.htmlFlowSinceBlank = false;
918
+ cp.htmlFlowReal = false;
919
+ }
864
920
  cp.prevLineBlank = true;
865
921
  cp.prevLineWasText = false;
866
922
  cp.prevLineWasValidDef = false;
@@ -874,7 +930,9 @@ function processConfirmedLine(cp, ln, text) {
874
930
  }
875
931
  const tagStart = ln.indent <= 3 ? /^<\/?([A-Za-z][A-Za-z0-9-]*)/.exec(mdTrimStart(ln.text)) : null;
876
932
  if (tagStart) {
933
+ const noRealBlockOpen = !cp.htmlFlowReal;
877
934
  cp.htmlFlowSinceBlank = true;
935
+ if (noRealBlockOpen && TYPE1_START_RE.test(mdTrimStart(ln.text))) cp.type1FlowOpen = true;
878
936
  if (!TYPE6_NAMES.has(tagStart[1].toLowerCase())) cp.hazardVerdict = true;
879
937
  if (!cp.htmlFlowReal) {
880
938
  const t = mdTrimStart(ln.text);
@@ -1025,6 +1083,7 @@ ${cont(scanText)}` };
1025
1083
  pos = pi + 2;
1026
1084
  } else {
1027
1085
  rawSpans.push([decl, decl + 2]);
1086
+ if (ln.indent <= 3 && /^doctype/i.test(scanText.slice(decl + 2))) cp.phasePoisonedAt = 0;
1028
1087
  cp.declOpen = true;
1029
1088
  pos = decl + 2;
1030
1089
  }
@@ -1056,7 +1115,10 @@ ${cont(scanText)}` };
1056
1115
  let m;
1057
1116
  let lastCommentOpenerIdx = -1;
1058
1117
  while ((m = TAG_OR_COMMENT_RE.exec(tagText)) !== null) {
1059
- if (cp.rawTextOpen !== null && (m[0] === "<!--" || m[0] === "-->" || m[0] === "--!>")) continue;
1118
+ if (cp.rawTextOpen !== null && (m[0] === "<!--" || m[0] === "-->" || m[0] === "--!>")) {
1119
+ if (cp.rawTextOpen === "script" && m[0] === "<!--") cp.scriptDataEscaped = true;
1120
+ continue;
1121
+ }
1060
1122
  if (m[0] === "<!--") {
1061
1123
  const next = tagText.slice(m.index + 4, m.index + 6);
1062
1124
  if (cp.commentOpen) {
@@ -1105,8 +1167,12 @@ ${cont(scanText)}` };
1105
1167
  TAG_OR_COMMENT_RE.lastIndex = gt + 1;
1106
1168
  }
1107
1169
  }
1108
- if (closing && !cp.htmlFlowReal && !/^\s*$/.test(attrs)) continue;
1170
+ if (closing && !cp.htmlFlowReal && !/^\s*$/.test(attrs)) {
1171
+ TAG_OR_COMMENT_RE.lastIndex = m.index + 2 + m[2].length;
1172
+ continue;
1173
+ }
1109
1174
  const selfClosing = /\/\s*$/.test(attrs);
1175
+ noteBreakout(tag, closing);
1110
1176
  if (VOID_TAGS.has(tag) || selfClosing && honoursSelfClosing(tag)) continue;
1111
1177
  applyTag(tag, closing);
1112
1178
  }
@@ -1129,6 +1195,7 @@ ${cont(scanText)}` };
1129
1195
  if (strayTablePart(tag)) cp.phasePoisonedAt = Math.min(cp.phasePoisonedAt, ln.start + mr.index);
1130
1196
  if (closing && mr[3] !== void 0 && !/^\s*$/.test(mr[3])) continue;
1131
1197
  const selfClosing = mr[3] !== void 0 && /\/\s*$/.test(mr[3]);
1198
+ noteBreakout(tag, closing);
1132
1199
  if (VOID_TAGS.has(tag) || selfClosing && honoursSelfClosing(tag)) continue;
1133
1200
  applyTag(tag, closing);
1134
1201
  }
@@ -1186,6 +1253,14 @@ ${cont(scanText)}` };
1186
1253
  cp.htmlSeamPending = true;
1187
1254
  }
1188
1255
  }
1256
+ if (cp.rawTextOpen !== null && cp.rawTextInline) {
1257
+ cp.phasePoisonedAt = Math.min(cp.phasePoisonedAt, ln.start);
1258
+ }
1259
+ if (cp.type1FlowOpen && TYPE1_CLOSE_RE.test(ln.text)) {
1260
+ cp.type1FlowOpen = false;
1261
+ cp.htmlFlowSinceBlank = false;
1262
+ cp.htmlFlowReal = false;
1263
+ }
1189
1264
  cp.blankRun = 0;
1190
1265
  cp.prevLineBlank = false;
1191
1266
  cp.prevLineWasText = true;