@ai-matrx/content-ir 0.18.5 → 0.19.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/CHANGELOG.md +83 -4
- package/README.md +4 -2
- package/dist/index.cjs +168 -48
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +168 -49
- package/dist/index.js.map +1 -1
- package/dist/registry.cjs +88 -0
- package/dist/registry.cjs.map +1 -1
- package/dist/registry.d.cts +104 -1
- package/dist/registry.d.ts +104 -1
- package/dist/registry.js +88 -1
- package/dist/registry.js.map +1 -1
- package/dist/source.cjs +80 -48
- package/dist/source.cjs.map +1 -1
- package/dist/source.js +80 -48
- package/dist/source.js.map +1 -1
- package/package.json +1 -1
package/dist/source.cjs
CHANGED
|
@@ -270,12 +270,6 @@ function fenceOpenerOf(content) {
|
|
|
270
270
|
return null;
|
|
271
271
|
}
|
|
272
272
|
var FenceReader = class {
|
|
273
|
-
constructor(opener, options = {}) {
|
|
274
|
-
this.opener = opener;
|
|
275
|
-
this.isJson = opener.char === "`" && opener.lang === "json";
|
|
276
|
-
this.nesting = opener.char === "`" && (options.nesting ?? fenceNestsInnerFences(opener.lang));
|
|
277
|
-
this.tildeCloser = opener.char === "~" ? new RegExp(`^ {0,3}~{${opener.ticks},}[ \\t]*$`) : null;
|
|
278
|
-
}
|
|
279
273
|
opener;
|
|
280
274
|
state = { inString: false, escaped: false };
|
|
281
275
|
depth = 0;
|
|
@@ -284,6 +278,12 @@ var FenceReader = class {
|
|
|
284
278
|
isJson;
|
|
285
279
|
nesting;
|
|
286
280
|
tildeCloser;
|
|
281
|
+
constructor(opener, options = {}) {
|
|
282
|
+
this.opener = opener;
|
|
283
|
+
this.isJson = opener.char === "`" && opener.lang === "json";
|
|
284
|
+
this.nesting = opener.char === "`" && (options.nesting ?? fenceNestsInnerFences(opener.lang));
|
|
285
|
+
this.tildeCloser = opener.char === "~" ? new RegExp(`^ {0,3}~{${opener.ticks},}[ \\t]*$`) : null;
|
|
286
|
+
}
|
|
287
287
|
/** How many nested fences are open right now. */
|
|
288
288
|
get nestedDepth() {
|
|
289
289
|
return this.depth;
|
|
@@ -901,9 +901,6 @@ function isEscapedBacktick(line, offset) {
|
|
|
901
901
|
return slashes % 2 === 1;
|
|
902
902
|
}
|
|
903
903
|
var XmlContainerTracker = class {
|
|
904
|
-
constructor(rootTag) {
|
|
905
|
-
this.rootTag = rootTag;
|
|
906
|
-
}
|
|
907
904
|
rootTag;
|
|
908
905
|
depth = 0;
|
|
909
906
|
inComment = false;
|
|
@@ -911,6 +908,9 @@ var XmlContainerTracker = class {
|
|
|
911
908
|
inlineTicks = 0;
|
|
912
909
|
/** The open fence, read by THE one closer (source/code-ranges.ts). */
|
|
913
910
|
fence = null;
|
|
911
|
+
constructor(rootTag) {
|
|
912
|
+
this.rootTag = rootTag;
|
|
913
|
+
}
|
|
914
914
|
consumeLine(line, startOffset = 0) {
|
|
915
915
|
if (this.fence) {
|
|
916
916
|
if (this.fence.feed(line)) this.fence = null;
|
|
@@ -1122,6 +1122,23 @@ function isSplitterTreeLine(line) {
|
|
|
1122
1122
|
}
|
|
1123
1123
|
var MEDIA_REF_PREFIXES = ["[Image URL:", "[Video URL:", "[Audio URL:"];
|
|
1124
1124
|
var Tokenizer = class {
|
|
1125
|
+
text;
|
|
1126
|
+
streaming;
|
|
1127
|
+
meter;
|
|
1128
|
+
n;
|
|
1129
|
+
lineStarts = [];
|
|
1130
|
+
contentEnds = [];
|
|
1131
|
+
lineEnds = [];
|
|
1132
|
+
blocks = [];
|
|
1133
|
+
blockCache = /* @__PURE__ */ new Map();
|
|
1134
|
+
/** Lazily built: for line i, first line j >= i where brace net from i drops to <= 0. */
|
|
1135
|
+
braceStop = null;
|
|
1136
|
+
braceNet = null;
|
|
1137
|
+
/** Every occurrence offset of each needle searched so far (overlapping, like indexOf). */
|
|
1138
|
+
occurrences = /* @__PURE__ */ new Map();
|
|
1139
|
+
/** `$$` opener → closer for the pairs the core renders as math. */
|
|
1140
|
+
mathPairs;
|
|
1141
|
+
finder = (needle, from) => this.next(needle, from);
|
|
1125
1142
|
constructor(text, streaming = false, meter = void 0) {
|
|
1126
1143
|
this.text = text;
|
|
1127
1144
|
this.streaming = streaming;
|
|
@@ -1168,23 +1185,6 @@ var Tokenizer = class {
|
|
|
1168
1185
|
this.lineEnds.push(text.length);
|
|
1169
1186
|
}
|
|
1170
1187
|
}
|
|
1171
|
-
text;
|
|
1172
|
-
streaming;
|
|
1173
|
-
meter;
|
|
1174
|
-
n;
|
|
1175
|
-
lineStarts = [];
|
|
1176
|
-
contentEnds = [];
|
|
1177
|
-
lineEnds = [];
|
|
1178
|
-
blocks = [];
|
|
1179
|
-
blockCache = /* @__PURE__ */ new Map();
|
|
1180
|
-
/** Lazily built: for line i, first line j >= i where brace net from i drops to <= 0. */
|
|
1181
|
-
braceStop = null;
|
|
1182
|
-
braceNet = null;
|
|
1183
|
-
/** Every occurrence offset of each needle searched so far (overlapping, like indexOf). */
|
|
1184
|
-
occurrences = /* @__PURE__ */ new Map();
|
|
1185
|
-
/** `$$` opener → closer for the pairs the core renders as math. */
|
|
1186
|
-
mathPairs;
|
|
1187
|
-
finder = (needle, from) => this.next(needle, from);
|
|
1188
1188
|
/** Streaming: where provisional text starts (a pending `$$`), or +∞. */
|
|
1189
1189
|
provisionalFrom = Number.POSITIVE_INFINITY;
|
|
1190
1190
|
/** Streaming: the text ends in a lone CR whose LF has not arrived yet. */
|
|
@@ -1241,10 +1241,13 @@ var Tokenizer = class {
|
|
|
1241
1241
|
/**
|
|
1242
1242
|
* Streaming: an open block that may still turn back into prose — a `$$`
|
|
1243
1243
|
* pair whose closer is on the open last line (prose after it makes it
|
|
1244
|
-
* inline),
|
|
1244
|
+
* inline), a JSON head whose braces have not balanced (it may never parse),
|
|
1245
|
+
* or any opener that is itself still arriving on the open last line.
|
|
1245
1246
|
*/
|
|
1246
1247
|
mayDissolve(block) {
|
|
1247
|
-
|
|
1248
|
+
if (!this.streaming || block.complete) return false;
|
|
1249
|
+
if (block.type === "math_block" || block.type === "json") return true;
|
|
1250
|
+
return this.isOpenTail(this.lineOf(block.start));
|
|
1248
1251
|
}
|
|
1249
1252
|
/** Streaming: paragraph ends where an undecided, dissolvable block cut them short. */
|
|
1250
1253
|
undecidedBreaks = /* @__PURE__ */ new Set();
|
|
@@ -1265,6 +1268,12 @@ var Tokenizer = class {
|
|
|
1265
1268
|
}
|
|
1266
1269
|
return lo;
|
|
1267
1270
|
}
|
|
1271
|
+
/** How many whitespace characters open the text at `from` (up to `to`). */
|
|
1272
|
+
leadingSpace(from, to) {
|
|
1273
|
+
let k = from;
|
|
1274
|
+
while (k < to && /\s/.test(this.text[k])) k++;
|
|
1275
|
+
return k - from;
|
|
1276
|
+
}
|
|
1268
1277
|
isBlank(from, to) {
|
|
1269
1278
|
return !NOT_WHITESPACE.test(this.text.slice(from, to));
|
|
1270
1279
|
}
|
|
@@ -1289,6 +1298,10 @@ var Tokenizer = class {
|
|
|
1289
1298
|
break;
|
|
1290
1299
|
}
|
|
1291
1300
|
const island = this.detectBlock(pos, li, true);
|
|
1301
|
+
if (island && pos + this.leadingSpace(pos, this.contentEnds[li]) >= this.provisionalFrom) {
|
|
1302
|
+
this.push({ kind: "prose", start: pos, end: this.n, island: null, inlines: [] });
|
|
1303
|
+
break;
|
|
1304
|
+
}
|
|
1292
1305
|
if (island) {
|
|
1293
1306
|
this.push({ kind: "island", start: island.start, end: island.end, island, inlines: [] });
|
|
1294
1307
|
pos = island.end;
|
|
@@ -1318,12 +1331,6 @@ var Tokenizer = class {
|
|
|
1318
1331
|
const last = this.lineStarts.length - 1;
|
|
1319
1332
|
if (last < 0) return;
|
|
1320
1333
|
if (this.isOpenTail(last)) {
|
|
1321
|
-
const lineStart = this.lineStarts[last];
|
|
1322
|
-
for (const block2 of this.blocks) {
|
|
1323
|
-
if (block2.kind === "prose" && block2.end > lineStart) {
|
|
1324
|
-
block2.inlines = block2.inlines.filter((inline) => inline.end <= lineStart);
|
|
1325
|
-
}
|
|
1326
|
-
}
|
|
1327
1334
|
let b = this.blocks.length - 1;
|
|
1328
1335
|
while (b >= 0 && this.blocks[b].kind === "gap") b--;
|
|
1329
1336
|
const block = this.blocks[b];
|
|
@@ -1349,36 +1356,55 @@ var Tokenizer = class {
|
|
|
1349
1356
|
* region…) is never a tree line nor a root label, so it stops the walk.
|
|
1350
1357
|
*/
|
|
1351
1358
|
treeRootHoldFrom() {
|
|
1352
|
-
const
|
|
1359
|
+
const claimFrom = (k2) => {
|
|
1360
|
+
const lineStart = this.lineStarts[k2];
|
|
1361
|
+
const lineEnd = this.contentEnds[k2];
|
|
1362
|
+
let pos = lineStart;
|
|
1353
1363
|
for (; ; ) {
|
|
1354
|
-
const block = this.blockAt(
|
|
1355
|
-
if (!block || block.kind !== "island" || block.island
|
|
1356
|
-
|
|
1357
|
-
if (
|
|
1358
|
-
|
|
1364
|
+
const block = this.blockAt(pos);
|
|
1365
|
+
if (!block || block.kind !== "island" || !block.island) return pos;
|
|
1366
|
+
if (block.island.fromParagraph === true || this.mayDissolve(block.island)) return pos;
|
|
1367
|
+
if (block.start < lineStart) {
|
|
1368
|
+
const opened = this.lineOf(block.start);
|
|
1369
|
+
if (this.lineStarts[opened] !== block.start && claimFrom(opened) !== -1) return pos;
|
|
1370
|
+
if (block.end >= lineEnd) return -1;
|
|
1371
|
+
pos = block.end;
|
|
1372
|
+
continue;
|
|
1373
|
+
}
|
|
1374
|
+
if (block.end >= lineEnd) return -1;
|
|
1375
|
+
pos = block.end;
|
|
1359
1376
|
}
|
|
1360
1377
|
};
|
|
1361
1378
|
let k = this.lineCount - 1;
|
|
1362
1379
|
let start = this.lineCount;
|
|
1380
|
+
let startPos = this.n;
|
|
1363
1381
|
if (k >= 0 && this.isOpenTail(k)) {
|
|
1364
|
-
|
|
1382
|
+
const at = claimFrom(k);
|
|
1383
|
+
if (at === -1) return this.n;
|
|
1365
1384
|
start = k;
|
|
1385
|
+
startPos = at;
|
|
1366
1386
|
k--;
|
|
1367
1387
|
}
|
|
1368
|
-
for (; k >= 0
|
|
1388
|
+
for (; k >= 0; k--) {
|
|
1369
1389
|
this.tick(1);
|
|
1390
|
+
const at = claimFrom(k);
|
|
1391
|
+
if (at === -1) break;
|
|
1370
1392
|
if (this.lineIsBlank(k)) continue;
|
|
1371
1393
|
if (!TREE_GLYPHS.test(this.lineText(k))) break;
|
|
1372
1394
|
start = k;
|
|
1395
|
+
startPos = at;
|
|
1373
1396
|
}
|
|
1374
|
-
let
|
|
1375
|
-
for (let j = start - 1; j >= 0
|
|
1397
|
+
let rootPos = startPos;
|
|
1398
|
+
for (let j = start - 1; j >= 0; j--) {
|
|
1399
|
+
const at = claimFrom(j);
|
|
1400
|
+
if (at === -1) break;
|
|
1376
1401
|
const trimmed = this.lineText(j).trim();
|
|
1377
1402
|
this.tick(trimmed.length + 1);
|
|
1378
1403
|
if (!trimmed || isSplitterTreeLine(trimmed) || /^#{1,6}\s/.test(trimmed)) break;
|
|
1379
|
-
|
|
1404
|
+
rootPos = at;
|
|
1405
|
+
if (at > this.lineStarts[j]) break;
|
|
1380
1406
|
}
|
|
1381
|
-
return
|
|
1407
|
+
return rootPos;
|
|
1382
1408
|
}
|
|
1383
1409
|
/** The block (so far) containing offset `pos`, or null. */
|
|
1384
1410
|
blockAt(pos) {
|
|
@@ -1910,7 +1936,9 @@ var Tokenizer = class {
|
|
|
1910
1936
|
const block = this.detectBlock(this.lineStarts[k], k, false);
|
|
1911
1937
|
if (block) {
|
|
1912
1938
|
breakLine = k;
|
|
1913
|
-
if (this.mayDissolve(block)
|
|
1939
|
+
if (this.mayDissolve(block) || this.streaming && block.start >= this.provisionalFrom) {
|
|
1940
|
+
this.undecidedBreaks.add(end);
|
|
1941
|
+
}
|
|
1914
1942
|
break;
|
|
1915
1943
|
}
|
|
1916
1944
|
end = this.contentEnds[k];
|
|
@@ -2148,6 +2176,10 @@ var Tokenizer = class {
|
|
|
2148
2176
|
const closer = `</${name}>`;
|
|
2149
2177
|
const close = this.next(closer, tagEnd);
|
|
2150
2178
|
const blockType = isAttr ? "xml_attr" : "xml_region";
|
|
2179
|
+
if (close === -1 && isThinking && !this.streaming) {
|
|
2180
|
+
i = tagEnd;
|
|
2181
|
+
continue;
|
|
2182
|
+
}
|
|
2151
2183
|
if (close === -1) return stop(this.island(blockType, i, this.n, false, { tag: name }));
|
|
2152
2184
|
const end = close + closer.length;
|
|
2153
2185
|
if (end > pe) return stop(this.spill(blockType, i, end, pe, { tag: name }));
|
|
@@ -2251,12 +2283,12 @@ function blockAt(blocks, offset) {
|
|
|
2251
2283
|
|
|
2252
2284
|
// source/splice.ts
|
|
2253
2285
|
var SourceSpliceError = class extends Error {
|
|
2286
|
+
code;
|
|
2254
2287
|
constructor(code, message) {
|
|
2255
2288
|
super(message);
|
|
2256
2289
|
this.code = code;
|
|
2257
2290
|
this.name = "SourceSpliceError";
|
|
2258
2291
|
}
|
|
2259
|
-
code;
|
|
2260
2292
|
};
|
|
2261
2293
|
function blockEdit(block, text) {
|
|
2262
2294
|
return { start: block.start, end: block.end, text };
|