billion-context 0.1.67-pr.415.252 → 0.1.67-pr.415.253

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
@@ -47005,6 +47005,18 @@ var DEFAULT_ROLE_WEIGHTS = {
47005
47005
  block: 1
47006
47006
  };
47007
47007
  var DEFAULT_ALGORITHM = "hybrid";
47008
+ function messageDocs(msgs) {
47009
+ return msgs.map((m2) => ({
47010
+ kind: "message",
47011
+ ref: m2.ref,
47012
+ text: m2.text,
47013
+ title: `${m2.role}: ${m2.text.slice(0, 60)}`,
47014
+ role: m2.role,
47015
+ blockId: m2.blockId,
47016
+ tier: m2.tier,
47017
+ tokens: m2.tokens
47018
+ }));
47019
+ }
47008
47020
  function applyRoleWeight(scored, docs, rw) {
47009
47021
  if (docs.length === 0) return scored;
47010
47022
  const docByRef = new Map(docs.map((d) => [d.ref, d]));
@@ -50177,7 +50189,7 @@ async function flushAllSessions() {
50177
50189
  }
50178
50190
 
50179
50191
  // src/compress-tool.ts
50180
- var SEARCH_CONTEXT_DESCRIPTION = "Searches the FOLDED ORIGINAL CONTENT of compressed blocks \u2014 error text, file paths, and variable names that summaries drop \u2014 plus each block's summary as a secondary signal (English + Chinese/CJK). Use BEFORE decompressing to find the right block; every hit is a decompressable blockId. Hits marked [summary-only] mean the block's originals are gone from every payload and only its summary was searched.";
50192
+ var SEARCH_CONTEXT_DESCRIPTION = "Searches the ORIGINAL text of folded-away messages across ALL compressed blocks (any tier, active or archived) plus block summaries as a secondary signal (English + Chinese/CJK). Visible messages are not indexed \u2014 they are already in context. Use to locate which block holds a detail (an exact error string, a path, a value); message hits name the owning block, then decompress it. Hits marked summary-only mean the block's originals are gone from every payload and only its summary was searched.";
50181
50193
  var SEARCH_CONTEXT_TOOL2 = { ...SEARCH_CONTEXT_TOOL, description: SEARCH_CONTEXT_DESCRIPTION };
50182
50194
  var SEARCH_CONTEXT_TOOL_OPENAI2 = {
50183
50195
  ...SEARCH_CONTEXT_TOOL_OPENAI,
@@ -50289,59 +50301,108 @@ function parseSearchContextArgs(args) {
50289
50301
  const limit = typeof args.limit === "number" && args.limit > 0 ? Math.floor(args.limit) : 5;
50290
50302
  return { query, limit };
50291
50303
  }
50304
+ function ownerOf(state, rawId) {
50305
+ let best;
50306
+ for (const b2 of state.blocks) {
50307
+ if (!b2.effectiveMessageIds.includes(rawId)) continue;
50308
+ if (!best || b2.tier < best.tier || b2.tier === best.tier && b2.effectiveMessageIds.length < best.effectiveMessageIds.length) {
50309
+ best = b2;
50310
+ }
50311
+ }
50312
+ return best;
50313
+ }
50314
+ function foldedMessageInputs(state, log2) {
50315
+ const byRaw = state.messageRefs.byRaw;
50316
+ const foldedRaw = /* @__PURE__ */ new Set();
50317
+ for (const b2 of state.blocks) {
50318
+ for (const id of b2.effectiveMessageIds) foldedRaw.add(id);
50319
+ }
50320
+ const out = [];
50321
+ const seen = /* @__PURE__ */ new Set();
50322
+ for (const m2 of log2) {
50323
+ if (seen.has(m2.id)) continue;
50324
+ seen.add(m2.id);
50325
+ if (!foldedRaw.has(m2.id)) continue;
50326
+ if (m2.role === "system") continue;
50327
+ const text = m2.text ?? "";
50328
+ if (text.length === 0) continue;
50329
+ const ref = byRaw[m2.id];
50330
+ if (typeof ref !== "string" || ref.length === 0) continue;
50331
+ const owner = ownerOf(state, m2.id);
50332
+ const role = m2.role === "tool" || m2.contentType === "tool-call" || m2.contentType === "tool-result" ? "tool" : m2.role;
50333
+ out.push({ ref, role, text, blockId: owner?.blockId, tier: owner?.tier });
50334
+ }
50335
+ return out;
50336
+ }
50292
50337
  function hasSubstance(text) {
50293
50338
  return text.replace(/^\[[^\]]*\]\s*$/gm, "").trim().length > 0;
50294
50339
  }
50295
- function collectFromSource(state, block, source) {
50296
- if (!source || source.length === 0) return "";
50297
- const collected = collectBlockContent(state, block, source, { full: true });
50298
- if (collected.count === 0 || !hasSubstance(collected.text)) return "";
50299
- return collected.text;
50300
- }
50301
- function blockOriginals(state, block, session, messages) {
50302
- const cached = session.blockContents.get(block.blockId)?.full.text;
50303
- if (cached && hasSubstance(cached)) return cached;
50304
- return collectFromSource(state, block, session.lastMessages) || collectFromSource(state, block, messages);
50340
+ function blockHasOriginals(blockId, byId, owners) {
50341
+ const b2 = byId.get(blockId);
50342
+ if (!b2) return false;
50343
+ if (owners.has(blockId)) return true;
50344
+ return b2.directBlockIds.some((id) => blockHasOriginals(id, byId, owners));
50305
50345
  }
50306
50346
  function handleSearchContext(args, session, messages) {
50307
50347
  const { query, limit } = parseSearchContextArgs(args);
50308
50348
  if (query.length === 0) return "[search_context FAILED: query is required]";
50309
50349
  const state = session.state;
50310
- const docs = [];
50350
+ const log2 = session.lastMessages && session.lastMessages.length > 0 ? session.lastMessages : messages;
50351
+ const messageInputs = foldedMessageInputs(state, log2);
50352
+ const owners = new Set(
50353
+ messageInputs.map((m2) => m2.blockId).filter((b2) => typeof b2 === "string")
50354
+ );
50355
+ const byId = new Map(state.blocks.map((b2) => [b2.blockId, b2]));
50356
+ const docs = [...messageDocs(messageInputs)];
50311
50357
  const summaryOnly = /* @__PURE__ */ new Set();
50312
- let withOriginals = 0;
50358
+ let cachedBlocks = 0;
50313
50359
  for (const b2 of state.blocks) {
50314
- if (!b2.active) continue;
50315
50360
  const base = {
50316
50361
  kind: "block",
50317
50362
  ref: b2.blockId,
50318
50363
  title: b2.topic ?? b2.blockId,
50319
50364
  blockId: b2.blockId,
50320
- tier: b2.tier ?? 1,
50365
+ tier: b2.tier,
50321
50366
  tokens: b2.compressedTokens
50322
50367
  };
50323
- const originals = blockOriginals(state, b2, session, messages);
50324
- if (originals) {
50325
- withOriginals++;
50326
- docs.push({ ...base, text: `${originals}
50368
+ const summaryText = `${b2.topic ?? ""} ${b2.summary ?? ""}`.trim();
50369
+ if (blockHasOriginals(b2.blockId, byId, owners)) {
50370
+ docs.push({ ...base, text: summaryText });
50371
+ continue;
50372
+ }
50373
+ const cached = session.blockContents.get(b2.blockId)?.full;
50374
+ if (cached && hasSubstance(cached.text)) {
50375
+ cachedBlocks++;
50376
+ docs.push({ ...base, text: `${cached.text}
50327
50377
 
50328
- ${b2.topic ?? ""} ${b2.summary ?? ""}`.trim() });
50378
+ ${summaryText}`.trim() });
50329
50379
  } else {
50330
50380
  summaryOnly.add(b2.blockId);
50331
- docs.push({ ...base, text: `${b2.topic ?? ""} ${b2.summary ?? ""}`.trim() });
50381
+ docs.push({ ...base, text: summaryText });
50332
50382
  }
50333
50383
  }
50334
50384
  const results = searchBlocks(docs, query, { limit });
50335
50385
  if (results.length === 0) {
50336
- return `[No matches for "${query}" \u2014 searched ${docs.length} active block(s) (${withOriginals} with folded originals, ${summaryOnly.size} summary-only). Try a broader term, or decompress the block you suspect holds it.]`;
50386
+ return `[No matches for "${query}" \u2014 searched ${state.blocks.length} block(s) (${owners.size + cachedBlocks} with folded originals, ${summaryOnly.size} summary-only) and ${messageInputs.length} folded-away message(s). Folded originals are matched on full text. Try a broader term, or decompress the block you suspect holds it.]`;
50337
50387
  }
50338
50388
  const lines = results.map((r) => {
50339
- const topic = r.title === r.ref ? "(no topic)" : r.title;
50340
- const marker = summaryOnly.has(r.ref) ? " [summary-only]" : "";
50341
- return `${r.ref} (T${r.tier}) "${topic}"${marker}
50389
+ if (r.kind === "block") {
50390
+ const topic = r.title === r.ref ? "(no topic)" : r.title;
50391
+ const mark = summaryOnly.has(r.ref) ? ", summary only" : "";
50392
+ return `${r.ref} (T${r.tier}${mark}) "${topic}"
50393
+ ${r.preview}`;
50394
+ }
50395
+ return r.blockId ? `${r.ref} (${r.role ?? "message"}, in ${r.blockId})
50396
+ ${r.preview}` : `${r.ref} (${r.role ?? "message"})
50342
50397
  ${r.preview}`;
50343
50398
  });
50344
- return `Found ${results.length} block(s) for "${query}":
50399
+ const blockHits = results.filter((r) => r.kind === "block").length;
50400
+ const messageHits = results.length - blockHits;
50401
+ const what = [
50402
+ blockHits > 0 ? `${blockHits} block(s)` : "",
50403
+ messageHits > 0 ? `${messageHits} message(s)` : ""
50404
+ ].filter(Boolean).join(", ");
50405
+ return `Found ${what} for "${query}":
50345
50406
 
50346
50407
  ${lines.join("\n\n")}`;
50347
50408
  }