la-machina-engine 0.7.0 → 0.7.2

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
@@ -1974,6 +1974,10 @@ function toAISdkTools(tools) {
1974
1974
  }
1975
1975
 
1976
1976
  // src/model/aiSdkAdapter.ts
1977
+ var import_anthropic = require("@ai-sdk/anthropic");
1978
+ var import_openai = require("@ai-sdk/openai");
1979
+ var import_google = require("@ai-sdk/google");
1980
+ var import_openai_compatible = require("@ai-sdk/openai-compatible");
1977
1981
  var AISdkAdapter = class {
1978
1982
  options;
1979
1983
  model = null;
@@ -2034,23 +2038,18 @@ var AISdkAdapter = class {
2034
2038
  async getModel() {
2035
2039
  if (this.model !== null) return this.model;
2036
2040
  const { provider, modelId, apiKey, baseURL } = this.options;
2037
- let mod;
2038
2041
  switch (provider) {
2039
2042
  case "anthropic":
2040
- mod = await importOrThrow("@ai-sdk/anthropic", provider);
2041
- this.model = mod.createAnthropic({ apiKey })(modelId);
2043
+ this.model = (0, import_anthropic.createAnthropic)({ apiKey })(modelId);
2042
2044
  break;
2043
2045
  case "openai":
2044
- mod = await importOrThrow("@ai-sdk/openai", provider);
2045
- this.model = mod.createOpenAI({ apiKey, ...baseURL ? { baseURL } : {} })(modelId);
2046
+ this.model = (0, import_openai.createOpenAI)({ apiKey, ...baseURL ? { baseURL } : {} })(modelId);
2046
2047
  break;
2047
2048
  case "google":
2048
- mod = await importOrThrow("@ai-sdk/google", provider);
2049
- this.model = mod.createGoogleGenerativeAI({ apiKey })(modelId);
2049
+ this.model = (0, import_google.createGoogleGenerativeAI)({ apiKey })(modelId);
2050
2050
  break;
2051
2051
  case "openai-compatible":
2052
- mod = await importOrThrow("@ai-sdk/openai-compatible", provider);
2053
- this.model = mod.createOpenAICompatible({ name: "custom", apiKey, baseURL: baseURL ?? "" })(
2052
+ this.model = (0, import_openai_compatible.createOpenAICompatible)({ name: "custom", apiKey, baseURL: baseURL ?? "" })(
2054
2053
  modelId
2055
2054
  );
2056
2055
  break;
@@ -2072,13 +2071,6 @@ function mapFinishReason(reason) {
2072
2071
  return "end_turn";
2073
2072
  }
2074
2073
  }
2075
- async function importOrThrow(pkg, provider) {
2076
- try {
2077
- return await import(pkg);
2078
- } catch {
2079
- throw new Error(`Provider "${provider}" requires "${pkg}". Install: npm i ${pkg}`);
2080
- }
2081
- }
2082
2074
 
2083
2075
  // src/model/factory.ts
2084
2076
  function createModelAdapter(config, options = {}) {
@@ -8201,75 +8193,8 @@ init_cjs_shims();
8201
8193
  var import_zod26 = require("zod");
8202
8194
  init_contract();
8203
8195
 
8204
- // src/knowledge/scope.ts
8196
+ // src/knowledge/indexer.ts
8205
8197
  init_cjs_shims();
8206
- var SAFE_PATH_RE = /^[a-zA-Z0-9_\-./]+$/;
8207
- function parseFolderRef(raw) {
8208
- if (typeof raw !== "string" || raw.length === 0) {
8209
- throw new Error(`invalid knowledge folder ref: empty`);
8210
- }
8211
- if (raw.startsWith("/")) {
8212
- throw new Error(`invalid knowledge folder ref: absolute paths not allowed ("${raw}")`);
8213
- }
8214
- const trimmed = raw.replace(/\/+$/g, "");
8215
- if (trimmed.length === 0) {
8216
- throw new Error(`invalid knowledge folder ref: "${raw}"`);
8217
- }
8218
- if (!SAFE_PATH_RE.test(trimmed)) {
8219
- throw new Error(`invalid knowledge folder ref: unsafe characters in "${raw}"`);
8220
- }
8221
- if (trimmed.split("/").some((seg) => seg === ".." || seg === "." || seg === "")) {
8222
- throw new Error(`invalid knowledge folder ref: traversal in "${raw}"`);
8223
- }
8224
- const segs = trimmed.split("/");
8225
- const base = segs[0];
8226
- const subPath = segs.slice(1).join("/");
8227
- return { path: trimmed, base, subPath };
8228
- }
8229
- function relPathInScope(folder, relPath) {
8230
- if (folder.subPath === "") return true;
8231
- return relPath === folder.subPath || relPath.startsWith(`${folder.subPath}/`);
8232
- }
8233
- function parseKnowledgeRef(raw) {
8234
- if (typeof raw !== "string" || raw.length === 0) {
8235
- throw new Error("invalid knowledge ref: empty");
8236
- }
8237
- if (raw.startsWith("ext:")) {
8238
- const name = raw.slice("ext:".length);
8239
- if (!/^[a-zA-Z0-9_-]+$/.test(name) || name.length === 0) {
8240
- throw new Error(`invalid knowledge ref: external name "${name}" has unsafe characters`);
8241
- }
8242
- return { kind: "ext", target: name };
8243
- }
8244
- if (raw.startsWith("/")) {
8245
- throw new Error(`invalid knowledge ref: absolute paths not allowed ("${raw}")`);
8246
- }
8247
- const hashAt = raw.indexOf("#");
8248
- const filePath = hashAt === -1 ? raw : raw.slice(0, hashAt);
8249
- const section = hashAt === -1 ? void 0 : raw.slice(hashAt + 1);
8250
- if (!SAFE_PATH_RE.test(filePath)) {
8251
- throw new Error(`invalid knowledge ref: unsafe characters in "${filePath}"`);
8252
- }
8253
- if (filePath.split("/").some((seg) => seg === ".." || seg === "." || seg === "")) {
8254
- throw new Error(`invalid knowledge ref: traversal in "${filePath}"`);
8255
- }
8256
- if (section !== void 0) {
8257
- if (section.length > 0 && !/^[a-zA-Z0-9_-]+$/.test(section)) {
8258
- throw new Error(`invalid knowledge ref: unsafe characters in section "${section}"`);
8259
- }
8260
- return { kind: "section", target: filePath, section };
8261
- }
8262
- return { kind: "file", target: filePath };
8263
- }
8264
- function refInScope(folders, filePath) {
8265
- return folders.some((f) => {
8266
- if (filePath === f.base || filePath.startsWith(`${f.base}/`)) {
8267
- const relInBase = filePath === f.base ? "" : filePath.slice(f.base.length + 1);
8268
- return relPathInScope(f, relInBase);
8269
- }
8270
- return false;
8271
- });
8272
- }
8273
8198
 
8274
8199
  // src/knowledge/tokenize.ts
8275
8200
  init_cjs_shims();
@@ -8346,6 +8271,220 @@ function scoreOverlap(sectionWords, queryTokens) {
8346
8271
  return n;
8347
8272
  }
8348
8273
 
8274
+ // src/knowledge/indexer.ts
8275
+ var HEADING_RE = /^(#{1,6})[ \t]+(.+?)\s*$/;
8276
+ var WIKI_LINK_RE = /\[\[([^\]|#]+)(?:[#|][^\]]*)?\]\]/g;
8277
+ var FORMAT_BY_EXT = {
8278
+ md: "md",
8279
+ markdown: "md",
8280
+ txt: "txt",
8281
+ json: "json",
8282
+ csv: "csv",
8283
+ html: "html",
8284
+ htm: "html",
8285
+ pdf: "pdf",
8286
+ docx: "docx"
8287
+ };
8288
+ var PREVIEW_CHARS = 200;
8289
+ async function buildKnowledgeIndex(options) {
8290
+ const { adapter, base } = options;
8291
+ const safeBase = base.replace(/^\/+|\/+$/g, "");
8292
+ if (safeBase.length === 0 || safeBase.includes("..")) {
8293
+ throw new Error(`buildKnowledgeIndex: invalid base "${base}"`);
8294
+ }
8295
+ const files = await listFilesRecursive(adapter, safeBase);
8296
+ const sections = [];
8297
+ const filesMeta = {};
8298
+ for (const fileRel of files) {
8299
+ if (fileRel === "_index.json") continue;
8300
+ const fullPath = `${safeBase}/${fileRel}`;
8301
+ const ext = (fileRel.split(".").pop() ?? "").toLowerCase();
8302
+ const format = FORMAT_BY_EXT[ext];
8303
+ if (format === void 0) continue;
8304
+ const raw = await adapter.readFile(fullPath);
8305
+ if (raw === null) continue;
8306
+ const sizeBytes = byteLength3(raw);
8307
+ const meta = { format, size: sizeBytes };
8308
+ if (format === "md" || format === "txt") {
8309
+ const fileSections = splitSections(raw, fileRel);
8310
+ sections.push(...fileSections);
8311
+ const wikiLinks = extractWikiLinks(raw);
8312
+ if (wikiLinks.length > 0) meta.wikiLinks = wikiLinks;
8313
+ }
8314
+ filesMeta[fileRel] = meta;
8315
+ }
8316
+ return {
8317
+ schema: "v1",
8318
+ base: safeBase,
8319
+ builtAt: options.nowIso ?? (/* @__PURE__ */ new Date()).toISOString(),
8320
+ fileCount: Object.keys(filesMeta).length,
8321
+ sections,
8322
+ files: filesMeta
8323
+ };
8324
+ }
8325
+ async function writeKnowledgeIndex(options) {
8326
+ const index = await buildKnowledgeIndex(options);
8327
+ await options.adapter.writeFile(`${index.base}/_index.json`, JSON.stringify(index, null, 2));
8328
+ return index;
8329
+ }
8330
+ async function listFilesRecursive(adapter, dir) {
8331
+ const out = [];
8332
+ const stack = [""];
8333
+ while (stack.length > 0) {
8334
+ const sub = stack.pop();
8335
+ const fullDir = sub === "" ? dir : `${dir}/${sub}`;
8336
+ let entries = [];
8337
+ try {
8338
+ entries = await adapter.listDir(fullDir);
8339
+ } catch {
8340
+ continue;
8341
+ }
8342
+ for (const name of entries) {
8343
+ const childRel = sub === "" ? name : `${sub}/${name}`;
8344
+ const childFull = `${dir}/${childRel}`;
8345
+ const isDir = await adapter.isDirectory(childFull).catch(() => false);
8346
+ if (isDir) {
8347
+ stack.push(childRel);
8348
+ } else {
8349
+ out.push(childRel);
8350
+ }
8351
+ }
8352
+ }
8353
+ return out.sort();
8354
+ }
8355
+ function splitSections(content, relPath) {
8356
+ const lines = content.split(/\r?\n/);
8357
+ const out = [];
8358
+ const heads = [];
8359
+ for (let i = 0; i < lines.length; i++) {
8360
+ const line = lines[i];
8361
+ const m = HEADING_RE.exec(line);
8362
+ if (m) heads.push({ line: i + 1, depth: m[1].length, heading: m[2].trim() });
8363
+ }
8364
+ const leadInEndLine = heads.length > 0 ? heads[0].line - 1 : lines.length;
8365
+ const leadInBody = lines.slice(0, leadInEndLine).join("\n").trim();
8366
+ if (leadInBody.length > 0) {
8367
+ out.push({
8368
+ relPath,
8369
+ heading: "",
8370
+ slug: `${relPath}#`,
8371
+ depth: 0,
8372
+ words: tokenize(leadInBody),
8373
+ preview: makePreview(leadInBody),
8374
+ startLine: 1,
8375
+ endLine: leadInEndLine
8376
+ });
8377
+ }
8378
+ for (let i = 0; i < heads.length; i++) {
8379
+ const h = heads[i];
8380
+ const startLine = h.line;
8381
+ const endLine = i + 1 < heads.length ? heads[i + 1].line - 1 : lines.length;
8382
+ const body = lines.slice(startLine - 1, endLine).join("\n");
8383
+ out.push({
8384
+ relPath,
8385
+ heading: h.heading,
8386
+ slug: `${relPath}#${slugify(h.heading)}`,
8387
+ depth: h.depth,
8388
+ words: tokenize(body),
8389
+ preview: makePreview(body),
8390
+ startLine,
8391
+ endLine
8392
+ });
8393
+ }
8394
+ return out;
8395
+ }
8396
+ function makePreview(body) {
8397
+ const trimmed = body.replace(/^#{1,6}\s+.+$\r?\n?/m, "").trim();
8398
+ if (trimmed.length <= PREVIEW_CHARS) return trimmed;
8399
+ return trimmed.slice(0, PREVIEW_CHARS) + "\u2026";
8400
+ }
8401
+ function slugify(text2) {
8402
+ return text2.toLowerCase().trim().replace(/[^a-z0-9]+/g, "-").replace(/^-+|-+$/g, "");
8403
+ }
8404
+ function extractWikiLinks(text2) {
8405
+ const seen = /* @__PURE__ */ new Set();
8406
+ let m;
8407
+ WIKI_LINK_RE.lastIndex = 0;
8408
+ while ((m = WIKI_LINK_RE.exec(text2)) !== null) {
8409
+ const target = m[1].trim();
8410
+ if (target.length > 0) seen.add(target);
8411
+ }
8412
+ return [...seen].sort();
8413
+ }
8414
+ function byteLength3(s) {
8415
+ return new TextEncoder().encode(s).byteLength;
8416
+ }
8417
+
8418
+ // src/knowledge/scope.ts
8419
+ init_cjs_shims();
8420
+ var SAFE_PATH_RE = /^[a-zA-Z0-9_\-./]+$/;
8421
+ function parseFolderRef(raw) {
8422
+ if (typeof raw !== "string" || raw.length === 0) {
8423
+ throw new Error(`invalid knowledge folder ref: empty`);
8424
+ }
8425
+ if (raw.startsWith("/")) {
8426
+ throw new Error(`invalid knowledge folder ref: absolute paths not allowed ("${raw}")`);
8427
+ }
8428
+ const trimmed = raw.replace(/\/+$/g, "");
8429
+ if (trimmed.length === 0) {
8430
+ throw new Error(`invalid knowledge folder ref: "${raw}"`);
8431
+ }
8432
+ if (!SAFE_PATH_RE.test(trimmed)) {
8433
+ throw new Error(`invalid knowledge folder ref: unsafe characters in "${raw}"`);
8434
+ }
8435
+ if (trimmed.split("/").some((seg) => seg === ".." || seg === "." || seg === "")) {
8436
+ throw new Error(`invalid knowledge folder ref: traversal in "${raw}"`);
8437
+ }
8438
+ const segs = trimmed.split("/");
8439
+ const base = segs[0];
8440
+ const subPath = segs.slice(1).join("/");
8441
+ return { path: trimmed, base, subPath };
8442
+ }
8443
+ function relPathInScope(folder, relPath) {
8444
+ if (folder.subPath === "") return true;
8445
+ return relPath === folder.subPath || relPath.startsWith(`${folder.subPath}/`);
8446
+ }
8447
+ function parseKnowledgeRef(raw) {
8448
+ if (typeof raw !== "string" || raw.length === 0) {
8449
+ throw new Error("invalid knowledge ref: empty");
8450
+ }
8451
+ if (raw.startsWith("ext:")) {
8452
+ const name = raw.slice("ext:".length);
8453
+ if (!/^[a-zA-Z0-9_-]+$/.test(name) || name.length === 0) {
8454
+ throw new Error(`invalid knowledge ref: external name "${name}" has unsafe characters`);
8455
+ }
8456
+ return { kind: "ext", target: name };
8457
+ }
8458
+ if (raw.startsWith("/")) {
8459
+ throw new Error(`invalid knowledge ref: absolute paths not allowed ("${raw}")`);
8460
+ }
8461
+ const hashAt = raw.indexOf("#");
8462
+ const filePath = hashAt === -1 ? raw : raw.slice(0, hashAt);
8463
+ const section = hashAt === -1 ? void 0 : raw.slice(hashAt + 1);
8464
+ if (!SAFE_PATH_RE.test(filePath)) {
8465
+ throw new Error(`invalid knowledge ref: unsafe characters in "${filePath}"`);
8466
+ }
8467
+ if (filePath.split("/").some((seg) => seg === ".." || seg === "." || seg === "")) {
8468
+ throw new Error(`invalid knowledge ref: traversal in "${filePath}"`);
8469
+ }
8470
+ if (section !== void 0) {
8471
+ if (section.length > 0 && !/^[a-zA-Z0-9_-]+$/.test(section)) {
8472
+ throw new Error(`invalid knowledge ref: unsafe characters in section "${section}"`);
8473
+ }
8474
+ return { kind: "section", target: filePath, section };
8475
+ }
8476
+ return { kind: "file", target: filePath };
8477
+ }
8478
+ function refInScope(folders, filePath) {
8479
+ return folders.some((f) => {
8480
+ if (filePath === f.base || filePath.startsWith(`${f.base}/`)) {
8481
+ const relInBase = filePath === f.base ? "" : filePath.slice(f.base.length + 1);
8482
+ return relPathInScope(f, relInBase);
8483
+ }
8484
+ return false;
8485
+ });
8486
+ }
8487
+
8349
8488
  // src/tools/searchKnowledge.ts
8350
8489
  var DEFAULT_MAX_RESULTS = 5;
8351
8490
  var inputSchema18 = import_zod26.z.object({
@@ -8430,17 +8569,24 @@ function truncatePreview(s) {
8430
8569
  async function loadIndex(adapter, base, cache) {
8431
8570
  const cached2 = cache.get(base);
8432
8571
  if (cached2 !== void 0) return cached2;
8433
- let raw;
8572
+ let raw = null;
8434
8573
  try {
8435
8574
  raw = await adapter.readFile(`${base}/_index.json`);
8436
8575
  } catch {
8437
- return null;
8576
+ raw = null;
8577
+ }
8578
+ if (raw !== null) {
8579
+ try {
8580
+ const parsed = JSON.parse(raw);
8581
+ cache.set(base, parsed);
8582
+ return parsed;
8583
+ } catch {
8584
+ }
8438
8585
  }
8439
- if (raw === null) return null;
8440
8586
  try {
8441
- const parsed = JSON.parse(raw);
8442
- cache.set(base, parsed);
8443
- return parsed;
8587
+ const built = await buildKnowledgeIndex({ adapter, base });
8588
+ cache.set(base, built);
8589
+ return built;
8444
8590
  } catch {
8445
8591
  return null;
8446
8592
  }
@@ -8599,7 +8745,7 @@ function createReadKnowledgeTool(opts) {
8599
8745
  const idx = await loadIndex2(opts.adapter, base, indexCache);
8600
8746
  if (idx === null) {
8601
8747
  return {
8602
- content: `ERR_KNOWLEDGE_INDEX_MISSING: no _index.json for base "${base}"`,
8748
+ content: `ERR_KNOWLEDGE_REF_NOT_FOUND: base "${base}" has no readable files`,
8603
8749
  isError: true
8604
8750
  };
8605
8751
  }
@@ -8705,17 +8851,24 @@ ${payload}`,
8705
8851
  async function loadIndex2(adapter, base, cache) {
8706
8852
  const cached2 = cache.get(base);
8707
8853
  if (cached2 !== void 0) return cached2;
8708
- let raw;
8854
+ let raw = null;
8709
8855
  try {
8710
8856
  raw = await adapter.readFile(`${base}/_index.json`);
8711
8857
  } catch {
8712
- return null;
8858
+ raw = null;
8859
+ }
8860
+ if (raw !== null) {
8861
+ try {
8862
+ const idx = JSON.parse(raw);
8863
+ cache.set(base, idx);
8864
+ return idx;
8865
+ } catch {
8866
+ }
8713
8867
  }
8714
- if (raw === null) return null;
8715
8868
  try {
8716
- const idx = JSON.parse(raw);
8717
- cache.set(base, idx);
8718
- return idx;
8869
+ const built = await buildKnowledgeIndex({ adapter, base });
8870
+ cache.set(base, built);
8871
+ return built;
8719
8872
  } catch {
8720
8873
  return null;
8721
8874
  }
@@ -11239,153 +11392,6 @@ function buildToolRegistry(options) {
11239
11392
  // src/index.ts
11240
11393
  init_contract();
11241
11394
  init_fetchData();
11242
-
11243
- // src/knowledge/indexer.ts
11244
- init_cjs_shims();
11245
- var HEADING_RE = /^(#{1,6})[ \t]+(.+?)\s*$/;
11246
- var WIKI_LINK_RE = /\[\[([^\]|#]+)(?:[#|][^\]]*)?\]\]/g;
11247
- var FORMAT_BY_EXT = {
11248
- md: "md",
11249
- markdown: "md",
11250
- txt: "txt",
11251
- json: "json",
11252
- csv: "csv",
11253
- html: "html",
11254
- htm: "html",
11255
- pdf: "pdf",
11256
- docx: "docx"
11257
- };
11258
- var PREVIEW_CHARS = 200;
11259
- async function buildKnowledgeIndex(options) {
11260
- const { adapter, base } = options;
11261
- const safeBase = base.replace(/^\/+|\/+$/g, "");
11262
- if (safeBase.length === 0 || safeBase.includes("..")) {
11263
- throw new Error(`buildKnowledgeIndex: invalid base "${base}"`);
11264
- }
11265
- const files = await listFilesRecursive(adapter, safeBase);
11266
- const sections = [];
11267
- const filesMeta = {};
11268
- for (const fileRel of files) {
11269
- if (fileRel === "_index.json") continue;
11270
- const fullPath = `${safeBase}/${fileRel}`;
11271
- const ext = (fileRel.split(".").pop() ?? "").toLowerCase();
11272
- const format = FORMAT_BY_EXT[ext];
11273
- if (format === void 0) continue;
11274
- const raw = await adapter.readFile(fullPath);
11275
- if (raw === null) continue;
11276
- const sizeBytes = byteLength3(raw);
11277
- const meta = { format, size: sizeBytes };
11278
- if (format === "md" || format === "txt") {
11279
- const fileSections = splitSections(raw, fileRel);
11280
- sections.push(...fileSections);
11281
- const wikiLinks = extractWikiLinks(raw);
11282
- if (wikiLinks.length > 0) meta.wikiLinks = wikiLinks;
11283
- }
11284
- filesMeta[fileRel] = meta;
11285
- }
11286
- return {
11287
- schema: "v1",
11288
- base: safeBase,
11289
- builtAt: options.nowIso ?? (/* @__PURE__ */ new Date()).toISOString(),
11290
- fileCount: Object.keys(filesMeta).length,
11291
- sections,
11292
- files: filesMeta
11293
- };
11294
- }
11295
- async function writeKnowledgeIndex(options) {
11296
- const index = await buildKnowledgeIndex(options);
11297
- await options.adapter.writeFile(`${index.base}/_index.json`, JSON.stringify(index, null, 2));
11298
- return index;
11299
- }
11300
- async function listFilesRecursive(adapter, dir) {
11301
- const out = [];
11302
- const stack = [""];
11303
- while (stack.length > 0) {
11304
- const sub = stack.pop();
11305
- const fullDir = sub === "" ? dir : `${dir}/${sub}`;
11306
- let entries = [];
11307
- try {
11308
- entries = await adapter.listDir(fullDir);
11309
- } catch {
11310
- continue;
11311
- }
11312
- for (const name of entries) {
11313
- const childRel = sub === "" ? name : `${sub}/${name}`;
11314
- const childFull = `${dir}/${childRel}`;
11315
- const isDir = await adapter.isDirectory(childFull).catch(() => false);
11316
- if (isDir) {
11317
- stack.push(childRel);
11318
- } else {
11319
- out.push(childRel);
11320
- }
11321
- }
11322
- }
11323
- return out.sort();
11324
- }
11325
- function splitSections(content, relPath) {
11326
- const lines = content.split(/\r?\n/);
11327
- const out = [];
11328
- const heads = [];
11329
- for (let i = 0; i < lines.length; i++) {
11330
- const line = lines[i];
11331
- const m = HEADING_RE.exec(line);
11332
- if (m) heads.push({ line: i + 1, depth: m[1].length, heading: m[2].trim() });
11333
- }
11334
- const leadInEndLine = heads.length > 0 ? heads[0].line - 1 : lines.length;
11335
- const leadInBody = lines.slice(0, leadInEndLine).join("\n").trim();
11336
- if (leadInBody.length > 0) {
11337
- out.push({
11338
- relPath,
11339
- heading: "",
11340
- slug: `${relPath}#`,
11341
- depth: 0,
11342
- words: tokenize(leadInBody),
11343
- preview: makePreview(leadInBody),
11344
- startLine: 1,
11345
- endLine: leadInEndLine
11346
- });
11347
- }
11348
- for (let i = 0; i < heads.length; i++) {
11349
- const h = heads[i];
11350
- const startLine = h.line;
11351
- const endLine = i + 1 < heads.length ? heads[i + 1].line - 1 : lines.length;
11352
- const body = lines.slice(startLine - 1, endLine).join("\n");
11353
- out.push({
11354
- relPath,
11355
- heading: h.heading,
11356
- slug: `${relPath}#${slugify(h.heading)}`,
11357
- depth: h.depth,
11358
- words: tokenize(body),
11359
- preview: makePreview(body),
11360
- startLine,
11361
- endLine
11362
- });
11363
- }
11364
- return out;
11365
- }
11366
- function makePreview(body) {
11367
- const trimmed = body.replace(/^#{1,6}\s+.+$\r?\n?/m, "").trim();
11368
- if (trimmed.length <= PREVIEW_CHARS) return trimmed;
11369
- return trimmed.slice(0, PREVIEW_CHARS) + "\u2026";
11370
- }
11371
- function slugify(text2) {
11372
- return text2.toLowerCase().trim().replace(/[^a-z0-9]+/g, "-").replace(/^-+|-+$/g, "");
11373
- }
11374
- function extractWikiLinks(text2) {
11375
- const seen = /* @__PURE__ */ new Set();
11376
- let m;
11377
- WIKI_LINK_RE.lastIndex = 0;
11378
- while ((m = WIKI_LINK_RE.exec(text2)) !== null) {
11379
- const target = m[1].trim();
11380
- if (target.length > 0) seen.add(target);
11381
- }
11382
- return [...seen].sort();
11383
- }
11384
- function byteLength3(s) {
11385
- return new TextEncoder().encode(s).byteLength;
11386
- }
11387
-
11388
- // src/index.ts
11389
11395
  init_orchestrate();
11390
11396
  init_planParser();
11391
11397
  init_retry();