@remnic/plugin-openclaw 1.0.13 → 1.0.15

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.
@@ -3,7 +3,7 @@ import {
3
3
  } from "./chunk-5LE4HTVL.js";
4
4
  import {
5
5
  FallbackLlmClient
6
- } from "./chunk-RQCTMECT.js";
6
+ } from "./chunk-BCKAR3OK.js";
7
7
  import "./chunk-3A5ELHTT.js";
8
8
  import {
9
9
  log
@@ -16,7 +16,7 @@ import {
16
16
  } from "./chunk-5LE4HTVL.js";
17
17
  import {
18
18
  FallbackLlmClient
19
- } from "./chunk-RQCTMECT.js";
19
+ } from "./chunk-BCKAR3OK.js";
20
20
  import "./chunk-3A5ELHTT.js";
21
21
  import "./chunk-7UZNLMW5.js";
22
22
  import "./chunk-6OJAU466.js";
@@ -40,6 +40,17 @@ function buildChatCompletionTokenLimit(model, maxTokens, options) {
40
40
  }
41
41
  return { max_tokens: safeMaxTokens };
42
42
  }
43
+ function supportsTemperature(model, options) {
44
+ const normalized = normalizedModel(model);
45
+ if (options?.assumeOpenAI === true && matchesModelFamily(normalized, /^gpt-5(?:$|[-.])/)) {
46
+ return false;
47
+ }
48
+ return true;
49
+ }
50
+ function buildChatCompletionTemperature(model, temperature, options) {
51
+ if (!supportsTemperature(model, options)) return {};
52
+ return { temperature };
53
+ }
43
54
 
44
55
  // ../remnic-core/src/resolve-provider-secret.ts
45
56
  import path from "path";
@@ -255,6 +266,20 @@ function loadModelsJsonProviders() {
255
266
  }
256
267
 
257
268
  // ../remnic-core/src/fallback-llm.ts
269
+ var PROVIDER_ALIASES = {
270
+ "openai-codex": ["codex"],
271
+ codex: ["openai-codex"],
272
+ "claude-cli": ["anthropic"]
273
+ };
274
+ var LEGACY_PROVIDER_IDS = /* @__PURE__ */ new Set(["openai-codex", "claude-cli"]);
275
+ var BUILT_IN_PROVIDER_FALLBACKS = {
276
+ anthropic: {
277
+ baseUrl: "https://api.anthropic.com/v1",
278
+ api: "anthropic-messages",
279
+ apiKey: "secretref-managed",
280
+ models: []
281
+ }
282
+ };
258
283
  var FallbackLlmClient = class {
259
284
  gatewayConfig;
260
285
  runtimeContext;
@@ -412,14 +437,59 @@ var FallbackLlmClient = class {
412
437
  log.warn(`fallback LLM: invalid model format: ${modelString}`);
413
438
  return null;
414
439
  }
415
- const providerId = parts[0];
440
+ const requestedProviderId = parts[0];
416
441
  const modelId = parts.slice(1).join("/");
417
- const providerConfig = providers[providerId] ?? this.resolveFromModelsJson(providerId);
442
+ const resolvedProvider = this.resolveProviderConfig(requestedProviderId, providers);
443
+ const providerConfig = resolvedProvider?.config;
418
444
  if (!providerConfig) {
419
- log.warn(`fallback LLM: provider not found: ${providerId}`);
445
+ log.warn(
446
+ `fallback LLM: provider not found: ${requestedProviderId} (tried: ${this.providerResolutionCandidates(requestedProviderId).join(", ")})`
447
+ );
420
448
  return null;
421
449
  }
422
- return { providerId, modelId, providerConfig, modelString };
450
+ return {
451
+ providerId: resolvedProvider.providerId,
452
+ modelId,
453
+ providerConfig,
454
+ modelString
455
+ };
456
+ }
457
+ resolveProviderConfig(providerId, providers) {
458
+ const candidates = this.providerResolutionCandidates(providerId);
459
+ const aliasCandidates = candidates.filter((candidate) => candidate !== providerId);
460
+ const fallbackCandidates = LEGACY_PROVIDER_IDS.has(providerId) ? [...aliasCandidates, providerId] : [providerId, ...aliasCandidates];
461
+ for (const candidate of candidates) {
462
+ const config = providers[candidate];
463
+ if (config) {
464
+ if (candidate !== providerId) {
465
+ log.debug(`fallback LLM: provider "${providerId}" resolved via alias "${candidate}"`);
466
+ }
467
+ return { providerId: candidate, config };
468
+ }
469
+ }
470
+ for (const candidate of fallbackCandidates) {
471
+ const config = this.resolveFromModelsJson(candidate);
472
+ if (config) {
473
+ if (candidate !== providerId) {
474
+ log.debug(`fallback LLM: provider "${providerId}" resolved via models.json alias "${candidate}"`);
475
+ }
476
+ return { providerId: candidate, config };
477
+ }
478
+ const builtInConfig = BUILT_IN_PROVIDER_FALLBACKS[candidate];
479
+ if (builtInConfig) {
480
+ if (candidate === providerId) {
481
+ log.debug(`fallback LLM: provider "${providerId}" resolved from built-in defaults`);
482
+ return { providerId, config: builtInConfig };
483
+ }
484
+ log.debug(`fallback LLM: provider "${providerId}" resolved via built-in alias "${candidate}"`);
485
+ return { providerId: candidate, config: builtInConfig };
486
+ }
487
+ }
488
+ return null;
489
+ }
490
+ providerResolutionCandidates(providerId) {
491
+ const candidates = [providerId, ...PROVIDER_ALIASES[providerId] ?? []];
492
+ return [...new Set(candidates)];
423
493
  }
424
494
  /**
425
495
  * Look up a provider from the gateway's materialized models.json, which
@@ -540,7 +610,9 @@ var FallbackLlmClient = class {
540
610
  const body = {
541
611
  model: modelId,
542
612
  messages,
543
- temperature: options.temperature ?? 0.3,
613
+ ...buildChatCompletionTemperature(modelId, options.temperature ?? 0.3, {
614
+ assumeOpenAI
615
+ }),
544
616
  ...buildChatCompletionTokenLimit(modelId, options.maxTokens ?? 4096, {
545
617
  assumeOpenAI
546
618
  })
@@ -593,7 +665,9 @@ var FallbackLlmClient = class {
593
665
  model: modelId,
594
666
  input,
595
667
  max_output_tokens: Math.max(0, Math.floor(options.maxTokens ?? 4096)),
596
- temperature: options.temperature ?? 0.3
668
+ ...buildChatCompletionTemperature(modelId, options.temperature ?? 0.3, {
669
+ assumeOpenAI: shouldAssumeOpenAiChatCompletions(config.baseUrl)
670
+ })
597
671
  };
598
672
  if (instructions.length > 0) {
599
673
  body.instructions = instructions;
@@ -831,7 +831,7 @@ var CompoundingEngine = class {
831
831
  let promotionCandidates = this.config.compoundingSemanticEnabled ? this.derivePromotionCandidates(outcomeSummary, mistakes.registry, rubrics) : [];
832
832
  if (this.config.cmcConsolidationEnabled) {
833
833
  try {
834
- const { deriveCausalPromotionCandidates, materializeAfterCausalConsolidation } = await import("./causal-consolidation-YI53C2AO.js");
834
+ const { deriveCausalPromotionCandidates, materializeAfterCausalConsolidation } = await import("./causal-consolidation-K65BZXWS.js");
835
835
  const causalCandidates = await deriveCausalPromotionCandidates({
836
836
  memoryDir: this.config.memoryDir,
837
837
  causalTrajectoryStoreDir: this.config.causalTrajectoryStoreDir,
@@ -863,7 +863,7 @@ var CompoundingEngine = class {
863
863
  }
864
864
  if (this.config.calibrationEnabled) {
865
865
  try {
866
- const { runCalibrationConsolidation } = await import("./calibration-WCHOK6DX.js");
866
+ const { runCalibrationConsolidation } = await import("./calibration-WBEDZUR3.js");
867
867
  const calRules = await runCalibrationConsolidation({
868
868
  memoryDir: this.config.memoryDir,
869
869
  gatewayConfig: this.config.gatewayConfig,
@@ -1,7 +1,7 @@
1
1
  import {
2
2
  CompoundingEngine,
3
3
  defaultTierMigrationCycleBudget
4
- } from "./chunk-OAE7AQ6R.js";
4
+ } from "./chunk-URJUGPZW.js";
5
5
  import "./chunk-EXDYWXMB.js";
6
6
  import "./chunk-7UZNLMW5.js";
7
7
  import "./chunk-6OJAU466.js";
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  FallbackLlmClient
3
- } from "./chunk-RQCTMECT.js";
3
+ } from "./chunk-BCKAR3OK.js";
4
4
  import "./chunk-3A5ELHTT.js";
5
5
  import "./chunk-UFU5GGGA.js";
6
6
  import "./chunk-I6B2W2IY.js";
package/dist/index.js CHANGED
@@ -115,7 +115,7 @@ import {
115
115
  CompoundingEngine,
116
116
  SharedContextManager,
117
117
  defaultTierMigrationCycleBudget
118
- } from "./chunk-OAE7AQ6R.js";
118
+ } from "./chunk-URJUGPZW.js";
119
119
  import {
120
120
  ZodError,
121
121
  external_exports
@@ -132,7 +132,7 @@ import {
132
132
  buildChatCompletionTokenLimit,
133
133
  findGatewayRuntimeModules,
134
134
  shouldAssumeOpenAiChatCompletions
135
- } from "./chunk-RQCTMECT.js";
135
+ } from "./chunk-BCKAR3OK.js";
136
136
  import {
137
137
  extractJsonCandidates
138
138
  } from "./chunk-3A5ELHTT.js";
@@ -601,6 +601,9 @@ var MEMORY_OS_PRESETS = {
601
601
  contextCompressionActionsEnabled: true,
602
602
  compressionGuidelineLearningEnabled: true,
603
603
  compressionGuidelineSemanticRefinementEnabled: true,
604
+ explicitCueRecallEnabled: true,
605
+ explicitCueRecallMaxChars: 3200,
606
+ lcmEnabled: true,
604
607
  maxProactiveQuestionsPerExtraction: 4,
605
608
  maxCompressionTokensPerHour: 3e3,
606
609
  behaviorLoopAutoTuneEnabled: true
@@ -1897,6 +1900,9 @@ function parseConfig(raw) {
1897
1900
  temporalMemoryTreeEnabled: cfg.temporalMemoryTreeEnabled === true,
1898
1901
  tmtHourlyMinMemories: typeof cfg.tmtHourlyMinMemories === "number" ? cfg.tmtHourlyMinMemories : 3,
1899
1902
  tmtSummaryMaxTokens: typeof cfg.tmtSummaryMaxTokens === "number" ? cfg.tmtSummaryMaxTokens : 300,
1903
+ explicitCueRecallEnabled: coerceBool(cfg.explicitCueRecallEnabled) === true,
1904
+ explicitCueRecallMaxChars: coerceNumber(cfg.explicitCueRecallMaxChars) !== void 0 ? Math.max(0, Math.floor(coerceNumber(cfg.explicitCueRecallMaxChars))) : 2400,
1905
+ explicitCueRecallMaxReferences: coerceNumber(cfg.explicitCueRecallMaxReferences) !== void 0 ? Math.max(0, Math.floor(coerceNumber(cfg.explicitCueRecallMaxReferences))) : 24,
1900
1906
  // Lossless Context Management (LCM)
1901
1907
  lcmEnabled: cfg.lcmEnabled === true,
1902
1908
  lcmLeafBatchSize: typeof cfg.lcmLeafBatchSize === "number" ? Math.max(2, Math.floor(cfg.lcmLeafBatchSize)) : 8,
@@ -2254,6 +2260,12 @@ function buildDefaultRecallPipeline(cfg) {
2254
2260
  enabled: cfg.sharedContextEnabled === true,
2255
2261
  maxChars: typeof cfg.sharedContextMaxInjectChars === "number" ? Math.max(0, Math.floor(cfg.sharedContextMaxInjectChars)) : 4e3
2256
2262
  },
2263
+ {
2264
+ id: "explicit-cue",
2265
+ enabled: coerceBool(cfg.explicitCueRecallEnabled) === true,
2266
+ maxChars: coerceNumber(cfg.explicitCueRecallMaxChars) !== void 0 ? Math.max(0, Math.floor(coerceNumber(cfg.explicitCueRecallMaxChars))) : 2400,
2267
+ maxResults: coerceNumber(cfg.explicitCueRecallMaxReferences) !== void 0 ? Math.max(0, Math.floor(coerceNumber(cfg.explicitCueRecallMaxReferences))) : 24
2268
+ },
2257
2269
  {
2258
2270
  id: "profile",
2259
2271
  enabled: true,
@@ -23087,6 +23099,827 @@ async function readRecentEntityTranscriptEntries(transcriptEntriesPromise, recen
23087
23099
  }
23088
23100
  var entityRecentTranscriptLookbackHours = RECENT_TRANSCRIPT_LOOKBACK_HOURS;
23089
23101
 
23102
+ // ../remnic-core/src/evidence-pack.ts
23103
+ var DEFAULT_MAX_ITEM_CHARS = 1200;
23104
+ function buildEvidencePack(items, options) {
23105
+ const budget = normalizePositiveInteger(options.maxChars);
23106
+ if (budget <= 0 || items.length === 0) {
23107
+ return "";
23108
+ }
23109
+ const maxItemChars = normalizePositiveInteger(
23110
+ options.maxItemChars ?? DEFAULT_MAX_ITEM_CHARS
23111
+ );
23112
+ if (maxItemChars <= 0) {
23113
+ return "";
23114
+ }
23115
+ const title = options.title ?? "Evidence";
23116
+ const lines = [`## ${title}`];
23117
+ const seenIds = /* @__PURE__ */ new Set();
23118
+ const seenContent = /* @__PURE__ */ new Set();
23119
+ let used = lines[0].length;
23120
+ for (const item of items) {
23121
+ const content = item.content.trim();
23122
+ if (!content) continue;
23123
+ const id = item.id ?? evidenceItemFallbackId(item);
23124
+ if (id && seenIds.has(id)) continue;
23125
+ const contentKey = normalizeEvidenceContent(content);
23126
+ if (seenContent.has(contentKey)) continue;
23127
+ const label = formatEvidenceLabel(item);
23128
+ const clipped = clipText(content, maxItemChars);
23129
+ const block = `${label}: ${clipped}`;
23130
+ const separatorLength = lines.length > 0 ? 2 : 0;
23131
+ const remaining = budget - used - separatorLength;
23132
+ if (remaining <= 0) break;
23133
+ const finalBlock = block.length > remaining ? clipText(block, remaining) : block;
23134
+ if (!finalBlock.trim()) break;
23135
+ lines.push(finalBlock);
23136
+ used += separatorLength + finalBlock.length;
23137
+ if (id) seenIds.add(id);
23138
+ seenContent.add(contentKey);
23139
+ }
23140
+ return lines.length === 1 ? "" : lines.join("\n\n");
23141
+ }
23142
+ function normalizePositiveInteger(value) {
23143
+ if (!Number.isFinite(value) || value <= 0) {
23144
+ return 0;
23145
+ }
23146
+ return Math.floor(value);
23147
+ }
23148
+ function evidenceItemFallbackId(item) {
23149
+ if (item.sessionId && typeof item.turnIndex === "number") {
23150
+ return `${item.sessionId}:${item.turnIndex}`;
23151
+ }
23152
+ return void 0;
23153
+ }
23154
+ function normalizeEvidenceContent(content) {
23155
+ return content.toLowerCase().replace(/\s+/g, " ").trim();
23156
+ }
23157
+ function formatEvidenceLabel(item) {
23158
+ const parts = [];
23159
+ if (item.sessionId) parts.push(item.sessionId);
23160
+ if (typeof item.turnIndex === "number") parts.push(`turn ${item.turnIndex}`);
23161
+ if (item.role) parts.push(item.role);
23162
+ if (typeof item.score === "number" && Number.isFinite(item.score)) {
23163
+ parts.push(`score ${item.score.toFixed(3)}`);
23164
+ }
23165
+ return parts.length > 0 ? `[${parts.join(", ")}]` : "[evidence]";
23166
+ }
23167
+ function clipText(text, maxChars) {
23168
+ if (text.length <= maxChars) {
23169
+ return text;
23170
+ }
23171
+ if (maxChars <= 1) {
23172
+ return text.slice(0, maxChars);
23173
+ }
23174
+ if (maxChars <= 3) {
23175
+ return text.slice(0, maxChars);
23176
+ }
23177
+ return `${text.slice(0, maxChars - 3).trimEnd()}...`;
23178
+ }
23179
+
23180
+ // ../remnic-core/src/explicit-cue-recall.ts
23181
+ var DEFAULT_MAX_CHARS = 2400;
23182
+ var DEFAULT_MAX_ITEM_CHARS2 = 1200;
23183
+ var DEFAULT_MAX_REFERENCES = 24;
23184
+ var REFERENCE_SCAN_TOKEN_FACTOR = 3;
23185
+ var TURN_REFERENCE_WINDOW_RADIUS = 0;
23186
+ var LEXICAL_CUE_WINDOW_RADIUS = 1;
23187
+ var LEXICAL_CUE_SEARCH_LIMIT = 3;
23188
+ var LEXICAL_CUE_MAX_TOKENS = 400;
23189
+ var LATEST_STATE_CUES = /* @__PURE__ */ new Set([
23190
+ "as of",
23191
+ "currently",
23192
+ "latest",
23193
+ "most recent",
23194
+ "newest",
23195
+ "now",
23196
+ "updated",
23197
+ "changed",
23198
+ "change"
23199
+ ]);
23200
+ var STRUCTURED_PLAN_FIELD_CUES = /* @__PURE__ */ new Set([
23201
+ "accommodation",
23202
+ "attraction",
23203
+ "breakfast",
23204
+ "current city",
23205
+ "dinner",
23206
+ "flight",
23207
+ "flights",
23208
+ "hotel",
23209
+ "lunch",
23210
+ "restaurant",
23211
+ "restaurants",
23212
+ "transportation",
23213
+ "traveler",
23214
+ "travelers"
23215
+ ]);
23216
+ var STRUCTURED_PLAN_DEPENDENCY_CUES = /* @__PURE__ */ new Set([
23217
+ "comparison",
23218
+ "constraint",
23219
+ "constraints",
23220
+ "dependency",
23221
+ "dependencies",
23222
+ "join",
23223
+ "same",
23224
+ "shared"
23225
+ ]);
23226
+ var BENCHMARK_ABILITY_CUES = /* @__PURE__ */ new Map([
23227
+ ["information extraction", "ability=information_extraction"],
23228
+ ["knowledge update", "ability=knowledge_update"],
23229
+ ["multi session reasoning", "ability=multi_session_reasoning"],
23230
+ ["multi-session reasoning", "ability=multi_session_reasoning"],
23231
+ ["instruction following", "ability=instruction_following"]
23232
+ ]);
23233
+ var BENCHMARK_ANCHOR_VALUE_STOPWORDS = /* @__PURE__ */ new Set([
23234
+ "a",
23235
+ "about",
23236
+ "an",
23237
+ "for",
23238
+ "from",
23239
+ "in",
23240
+ "on",
23241
+ "the",
23242
+ "to",
23243
+ "use",
23244
+ "using",
23245
+ "with"
23246
+ ]);
23247
+ var RELATIVE_TEMPORAL_CUES = [
23248
+ "as of",
23249
+ "most recent",
23250
+ "last time",
23251
+ "last week",
23252
+ "last month",
23253
+ "last year",
23254
+ "last session",
23255
+ "last conversation",
23256
+ "next time",
23257
+ "next week",
23258
+ "next month",
23259
+ "next year",
23260
+ "next session",
23261
+ "next conversation",
23262
+ "previous time",
23263
+ "previous week",
23264
+ "previous month",
23265
+ "previous year",
23266
+ "previous session",
23267
+ "previous conversation",
23268
+ "prior time",
23269
+ "prior week",
23270
+ "prior month",
23271
+ "prior year",
23272
+ "prior session",
23273
+ "prior conversation",
23274
+ "today",
23275
+ "yesterday",
23276
+ "tomorrow",
23277
+ "tonight",
23278
+ "earlier",
23279
+ "later",
23280
+ "recently",
23281
+ "previously",
23282
+ "currently",
23283
+ "now",
23284
+ "latest",
23285
+ "newest",
23286
+ "oldest",
23287
+ "earliest",
23288
+ "before",
23289
+ "after",
23290
+ "since",
23291
+ "updated",
23292
+ "changed",
23293
+ "change"
23294
+ ];
23295
+ var SPEAKER_NAME_STOPWORDS = /* @__PURE__ */ new Set([
23296
+ "A",
23297
+ "According",
23298
+ "An",
23299
+ "And",
23300
+ "Are",
23301
+ "As",
23302
+ "At",
23303
+ "Before",
23304
+ "Can",
23305
+ "Compare",
23306
+ "Could",
23307
+ "Did",
23308
+ "Do",
23309
+ "Does",
23310
+ "For",
23311
+ "From",
23312
+ "Had",
23313
+ "Has",
23314
+ "Have",
23315
+ "How",
23316
+ "In",
23317
+ "Is",
23318
+ "It",
23319
+ "Join",
23320
+ "Of",
23321
+ "On",
23322
+ "Or",
23323
+ "Please",
23324
+ "Review",
23325
+ "Step",
23326
+ "Tell",
23327
+ "The",
23328
+ "To",
23329
+ "Turn",
23330
+ "Use",
23331
+ "Was",
23332
+ "Were",
23333
+ "What",
23334
+ "When",
23335
+ "Where",
23336
+ "Which",
23337
+ "Who",
23338
+ "Why",
23339
+ "Will",
23340
+ "Would"
23341
+ ]);
23342
+ var QUESTION_SLOT_STOPWORDS = /* @__PURE__ */ new Set([
23343
+ "answer",
23344
+ "choice",
23345
+ "did",
23346
+ "does",
23347
+ "do",
23348
+ "is",
23349
+ "should",
23350
+ "single",
23351
+ "the",
23352
+ "user",
23353
+ "was",
23354
+ "were"
23355
+ ]);
23356
+ async function buildExplicitCueRecallSection(options) {
23357
+ const engine = options.engine;
23358
+ const query = options.query.trim();
23359
+ const maxChars = normalizePositiveInteger2(options.maxChars, DEFAULT_MAX_CHARS);
23360
+ if (!engine || query.length === 0 || maxChars <= 0) {
23361
+ return "";
23362
+ }
23363
+ const maxReferences = normalizePositiveInteger2(
23364
+ options.maxReferences,
23365
+ DEFAULT_MAX_REFERENCES
23366
+ );
23367
+ if (maxReferences <= 0) {
23368
+ return "";
23369
+ }
23370
+ const evidenceItems = [];
23371
+ const seenTurns = /* @__PURE__ */ new Set();
23372
+ await collectTurnReferenceEvidence({
23373
+ engine,
23374
+ sessionId: options.sessionId,
23375
+ query,
23376
+ maxReferences,
23377
+ evidenceItems,
23378
+ seenTurns
23379
+ });
23380
+ await collectLexicalCueEvidence({
23381
+ engine,
23382
+ sessionId: options.sessionId,
23383
+ query,
23384
+ maxReferences,
23385
+ includeBenchmarkAnchorCues: options.includeBenchmarkAnchorCues,
23386
+ includeStructuredPlanCues: options.includeStructuredPlanCues,
23387
+ evidenceItems,
23388
+ seenTurns
23389
+ });
23390
+ return buildEvidencePack(evidenceItems, {
23391
+ title: "Explicit Cue Evidence",
23392
+ maxChars,
23393
+ maxItemChars: normalizePositiveInteger2(
23394
+ options.maxItemChars,
23395
+ DEFAULT_MAX_ITEM_CHARS2
23396
+ )
23397
+ });
23398
+ }
23399
+ async function collectTurnReferenceEvidence(options) {
23400
+ if (!options.sessionId) {
23401
+ return;
23402
+ }
23403
+ const references = collectExplicitTurnReferences(options.query).slice(
23404
+ 0,
23405
+ options.maxReferences
23406
+ );
23407
+ if (references.length === 0) {
23408
+ return;
23409
+ }
23410
+ const windows = /* @__PURE__ */ new Map();
23411
+ for (const reference of references) {
23412
+ for (const center of candidateTurnIndexesForReference(reference)) {
23413
+ if (center < 0) {
23414
+ continue;
23415
+ }
23416
+ const fromTurn = Math.max(0, center - TURN_REFERENCE_WINDOW_RADIUS);
23417
+ const toTurn = center + TURN_REFERENCE_WINDOW_RADIUS;
23418
+ windows.set(`${fromTurn}:${toTurn}`, { fromTurn, toTurn });
23419
+ }
23420
+ }
23421
+ for (const window of [...windows.values()].sort(
23422
+ (left, right) => left.fromTurn - right.fromTurn || left.toTurn - right.toTurn
23423
+ )) {
23424
+ const expanded = await options.engine.expandContext(
23425
+ options.sessionId,
23426
+ window.fromTurn,
23427
+ window.toTurn,
23428
+ 2e3
23429
+ );
23430
+ appendExpandedEvidence(
23431
+ options.evidenceItems,
23432
+ options.seenTurns,
23433
+ options.sessionId,
23434
+ expanded
23435
+ );
23436
+ }
23437
+ }
23438
+ async function collectLexicalCueEvidence(options) {
23439
+ const cues = collectLexicalCues(options.query, {
23440
+ includeBenchmarkAnchorCues: options.includeBenchmarkAnchorCues,
23441
+ includeStructuredPlanCues: options.includeStructuredPlanCues
23442
+ }).slice(0, options.maxReferences);
23443
+ const preferLatest = hasLatestStateIntent(options.query);
23444
+ for (const cue of cues) {
23445
+ const results = sortLexicalCueResults(
23446
+ await options.engine.searchContextFull(
23447
+ cue,
23448
+ LEXICAL_CUE_SEARCH_LIMIT,
23449
+ options.sessionId
23450
+ ),
23451
+ preferLatest
23452
+ );
23453
+ for (const result of results) {
23454
+ const windowRadius = preferLatest ? 0 : LEXICAL_CUE_WINDOW_RADIUS;
23455
+ const fromTurn = Math.max(0, result.turn_index - windowRadius);
23456
+ const toTurn = result.turn_index + windowRadius;
23457
+ const expanded = await options.engine.expandContext(
23458
+ result.session_id,
23459
+ fromTurn,
23460
+ toTurn,
23461
+ LEXICAL_CUE_MAX_TOKENS
23462
+ );
23463
+ if (expanded.length === 0) {
23464
+ appendEvidenceItem(options.evidenceItems, options.seenTurns, {
23465
+ id: `${result.session_id}:${result.turn_index}`,
23466
+ sessionId: result.session_id,
23467
+ turnIndex: result.turn_index,
23468
+ role: result.role,
23469
+ content: result.content,
23470
+ ...typeof result.score === "number" ? { score: result.score } : {}
23471
+ });
23472
+ continue;
23473
+ }
23474
+ appendExpandedEvidence(
23475
+ options.evidenceItems,
23476
+ options.seenTurns,
23477
+ result.session_id,
23478
+ expanded
23479
+ );
23480
+ }
23481
+ }
23482
+ }
23483
+ function appendExpandedEvidence(evidenceItems, seenTurns, sessionId, expanded) {
23484
+ for (const message of expanded) {
23485
+ appendEvidenceItem(evidenceItems, seenTurns, {
23486
+ id: `${sessionId}:${message.turn_index}`,
23487
+ sessionId,
23488
+ turnIndex: message.turn_index,
23489
+ role: message.role,
23490
+ content: message.content
23491
+ });
23492
+ }
23493
+ }
23494
+ function appendEvidenceItem(evidenceItems, seenTurns, item) {
23495
+ if (seenTurns.has(item.id)) {
23496
+ return;
23497
+ }
23498
+ seenTurns.add(item.id);
23499
+ evidenceItems.push(item);
23500
+ }
23501
+ function collectExplicitTurnReferences(query) {
23502
+ const references = /* @__PURE__ */ new Map();
23503
+ const addReference = (value, label) => {
23504
+ const existing = references.get(String(value));
23505
+ references.set(String(value), {
23506
+ number: value,
23507
+ includeDirectTurn: (existing?.includeDirectTurn ?? false) || label === "turn"
23508
+ });
23509
+ };
23510
+ const tokens = tokenizeReferenceQuery(query);
23511
+ for (let index = 0; index < tokens.length; index += 1) {
23512
+ const label = normalizeReferenceLabel(tokens[index]);
23513
+ if (!label) {
23514
+ continue;
23515
+ }
23516
+ const parsed = parseReferenceNumbers(tokens, index + 1);
23517
+ for (const number of parsed.numbers) {
23518
+ addReference(number, label);
23519
+ }
23520
+ index = Math.max(index, parsed.nextIndex - 1);
23521
+ }
23522
+ return [...references.values()].sort((left, right) => left.number - right.number);
23523
+ }
23524
+ function collectLexicalCues(query, options = {}) {
23525
+ const cues = /* @__PURE__ */ new Set();
23526
+ for (const match of query.matchAll(/\b[A-Za-z][A-Za-z0-9]{0,12}\d+:\d+\b/g)) {
23527
+ cues.add(match[0]);
23528
+ }
23529
+ for (const match of query.matchAll(/\b\d{4}-\d{2}-\d{2}(?:T\d{2}:\d{2}(?::\d{2})?Z?)?\b/g)) {
23530
+ cues.add(match[0]);
23531
+ }
23532
+ for (const cue of collectTemporalLexicalCues(query)) {
23533
+ cues.add(cue);
23534
+ }
23535
+ for (const cue of collectQuestionSlotCues(query)) {
23536
+ cues.add(cue);
23537
+ }
23538
+ if (options.includeBenchmarkAnchorCues) {
23539
+ for (const cue of collectBenchmarkAnchorCues(query)) {
23540
+ cues.add(cue);
23541
+ }
23542
+ }
23543
+ if (options.includeStructuredPlanCues) {
23544
+ for (const cue of collectStructuredPlanCues(query)) {
23545
+ cues.add(cue);
23546
+ }
23547
+ }
23548
+ for (const match of query.matchAll(/\b(?:session|source|chat|plan|task|event|file|tool)[_-][A-Za-z0-9][A-Za-z0-9_.:-]{0,80}\b/gi)) {
23549
+ cues.add(match[0]);
23550
+ }
23551
+ for (const match of query.matchAll(/\b[A-Z][a-z]{1,30}(?:\s+[A-Z][a-z]{1,30}){0,2}\b/g)) {
23552
+ const value = normalizeSpeakerNameCue(match[0]);
23553
+ if (value) {
23554
+ cues.add(value);
23555
+ }
23556
+ }
23557
+ for (const match of query.matchAll(/\[([A-Za-z0-9][A-Za-z0-9_.:/ -]{1,80})\]/g)) {
23558
+ const value = match[1]?.trim();
23559
+ if (value) {
23560
+ cues.add(value);
23561
+ }
23562
+ }
23563
+ return [...cues].sort((left, right) => left.localeCompare(right));
23564
+ }
23565
+ function collectQuestionSlotCues(query) {
23566
+ const cues = /* @__PURE__ */ new Set();
23567
+ for (const match of query.matchAll(
23568
+ /\b(?:what|which)\s+([a-z][a-z0-9_-]{2,30})\s+(?:does|do|did|is|are|was|were|should|would|could|can|will)\b/gi
23569
+ )) {
23570
+ const value = match[1]?.toLowerCase();
23571
+ if (value && !QUESTION_SLOT_STOPWORDS.has(value)) {
23572
+ cues.add(value);
23573
+ }
23574
+ }
23575
+ return [...cues].sort((left, right) => left.localeCompare(right));
23576
+ }
23577
+ function collectBenchmarkAnchorCues(query) {
23578
+ const cues = /* @__PURE__ */ new Set();
23579
+ const normalizedQuery = query.toLowerCase().replace(/\s+/g, " ");
23580
+ for (const [phrase, cue] of BENCHMARK_ABILITY_CUES) {
23581
+ if (containsBoundedPhrase(normalizedQuery, phrase)) {
23582
+ cues.add(cue);
23583
+ }
23584
+ }
23585
+ const tokens = tokenizeAnchorQuery(query);
23586
+ for (let index = 0; index < tokens.length; index += 1) {
23587
+ let prefix = normalizeBenchmarkAnchorPrefix(tokens[index]);
23588
+ if (!prefix) {
23589
+ continue;
23590
+ }
23591
+ let valueIndex = index + 1;
23592
+ if (prefix === "source" && tokens[valueIndex]?.toLowerCase() === "chat") {
23593
+ prefix = "source_chat";
23594
+ valueIndex += 1;
23595
+ }
23596
+ const maybeIdLabel = tokens[valueIndex]?.toLowerCase();
23597
+ if (maybeIdLabel === "id" || maybeIdLabel === "ids") {
23598
+ valueIndex += 1;
23599
+ }
23600
+ let consumedValue = false;
23601
+ for (let currentValueIndex = valueIndex; currentValueIndex < tokens.length; currentValueIndex += 1) {
23602
+ const rawValue = tokens[currentValueIndex];
23603
+ const normalizedValue = rawValue?.toLowerCase();
23604
+ if (!rawValue || normalizeBenchmarkAnchorPrefix(rawValue)) {
23605
+ break;
23606
+ }
23607
+ if (normalizedValue === "and" || normalizedValue === "or") {
23608
+ continue;
23609
+ }
23610
+ if (BENCHMARK_ANCHOR_VALUE_STOPWORDS.has(normalizedValue)) {
23611
+ break;
23612
+ }
23613
+ if (!isBenchmarkAnchorValue(rawValue)) {
23614
+ break;
23615
+ }
23616
+ addBenchmarkAnchorCues(cues, prefix, rawValue);
23617
+ consumedValue = true;
23618
+ index = currentValueIndex;
23619
+ }
23620
+ if (!consumedValue) {
23621
+ continue;
23622
+ }
23623
+ }
23624
+ return [...cues].sort((left, right) => left.localeCompare(right));
23625
+ }
23626
+ function addBenchmarkAnchorCues(cues, prefix, rawValue) {
23627
+ cues.add(`${prefix}_id=${rawValue}`);
23628
+ cues.add(`${prefix}-${rawValue}`);
23629
+ if (prefix === "source_chat") {
23630
+ cues.add(`chat_id=${rawValue}`);
23631
+ }
23632
+ }
23633
+ function isBenchmarkAnchorValue(token) {
23634
+ for (const char of token) {
23635
+ if (isAsciiDigitChar(char)) {
23636
+ return true;
23637
+ }
23638
+ }
23639
+ return false;
23640
+ }
23641
+ function isAsciiDigitChar(char) {
23642
+ const code = char.charCodeAt(0);
23643
+ return code >= 48 && code <= 57;
23644
+ }
23645
+ function normalizeBenchmarkAnchorPrefix(token) {
23646
+ switch (token?.toLowerCase()) {
23647
+ case "ability":
23648
+ case "chat":
23649
+ case "plan":
23650
+ case "rubric":
23651
+ case "source":
23652
+ return token.toLowerCase();
23653
+ default:
23654
+ return void 0;
23655
+ }
23656
+ }
23657
+ function tokenizeAnchorQuery(query) {
23658
+ const tokens = [];
23659
+ let current = "";
23660
+ const push = () => {
23661
+ const token = trimTrailingAnchorTokenPunctuation(current);
23662
+ if (token.length > 0) {
23663
+ tokens.push(token);
23664
+ }
23665
+ current = "";
23666
+ };
23667
+ for (const char of query) {
23668
+ if (isAsciiLetterOrDigit(char) || char === "_" || char === "-" || char === "." || char === ":") {
23669
+ current += char;
23670
+ continue;
23671
+ }
23672
+ push();
23673
+ }
23674
+ push();
23675
+ return tokens;
23676
+ }
23677
+ function trimTrailingAnchorTokenPunctuation(token) {
23678
+ let end = token.length;
23679
+ while (end > 0) {
23680
+ const char = token[end - 1];
23681
+ if (char !== "." && char !== ":" && char !== ";" && char !== "!" && char !== "?") {
23682
+ break;
23683
+ }
23684
+ end -= 1;
23685
+ }
23686
+ return token.slice(0, end);
23687
+ }
23688
+ function collectStructuredPlanCues(query) {
23689
+ const cues = /* @__PURE__ */ new Set();
23690
+ const normalizedQuery = query.toLowerCase().replace(/\s+/g, " ");
23691
+ for (const cue of STRUCTURED_PLAN_FIELD_CUES) {
23692
+ if (containsBoundedPhrase(normalizedQuery, cue)) {
23693
+ cues.add(cue);
23694
+ }
23695
+ }
23696
+ if (cues.size === 0) {
23697
+ return [];
23698
+ }
23699
+ for (const cue of STRUCTURED_PLAN_DEPENDENCY_CUES) {
23700
+ if (containsBoundedPhrase(normalizedQuery, cue)) {
23701
+ cues.add(cue);
23702
+ }
23703
+ }
23704
+ return [...cues].sort((left, right) => left.localeCompare(right));
23705
+ }
23706
+ function containsBoundedPhrase(normalizedHaystack, phrase) {
23707
+ let searchFrom = 0;
23708
+ while (searchFrom < normalizedHaystack.length) {
23709
+ const index = normalizedHaystack.indexOf(phrase, searchFrom);
23710
+ if (index < 0) {
23711
+ return false;
23712
+ }
23713
+ const afterIndex = index + phrase.length;
23714
+ if (isTemporalCueBoundary(normalizedHaystack[index - 1]) && isTemporalCueBoundary(normalizedHaystack[afterIndex])) {
23715
+ return true;
23716
+ }
23717
+ searchFrom = afterIndex;
23718
+ }
23719
+ return false;
23720
+ }
23721
+ function collectTemporalLexicalCues(query) {
23722
+ const cues = /* @__PURE__ */ new Set();
23723
+ const normalizedQuery = query.toLowerCase().replace(/\s+/g, " ");
23724
+ for (const cue of RELATIVE_TEMPORAL_CUES) {
23725
+ if (containsBoundedPhrase(normalizedQuery, cue)) {
23726
+ cues.add(cue);
23727
+ }
23728
+ }
23729
+ return [...cues].sort((left, right) => left.localeCompare(right));
23730
+ }
23731
+ function hasLatestStateIntent(query) {
23732
+ return collectTemporalLexicalCues(query).some(
23733
+ (cue) => LATEST_STATE_CUES.has(cue)
23734
+ );
23735
+ }
23736
+ function sortLexicalCueResults(results, preferLatest) {
23737
+ return [...results].sort((left, right) => {
23738
+ if (preferLatest) {
23739
+ const sessionOrder2 = left.session_id.localeCompare(right.session_id);
23740
+ if (sessionOrder2 !== 0) {
23741
+ return sessionOrder2;
23742
+ }
23743
+ const turnOrder = right.turn_index - left.turn_index;
23744
+ if (turnOrder !== 0) {
23745
+ return turnOrder;
23746
+ }
23747
+ return (right.score ?? 0) - (left.score ?? 0);
23748
+ }
23749
+ const scoreDelta = (right.score ?? 0) - (left.score ?? 0);
23750
+ if (scoreDelta !== 0) {
23751
+ return scoreDelta;
23752
+ }
23753
+ const sessionOrder = left.session_id.localeCompare(right.session_id);
23754
+ if (sessionOrder !== 0) {
23755
+ return sessionOrder;
23756
+ }
23757
+ return left.turn_index - right.turn_index;
23758
+ });
23759
+ }
23760
+ function normalizeSpeakerNameCue(value) {
23761
+ const words = value.trim().split(/\s+/).filter(Boolean);
23762
+ while (words.length > 0 && SPEAKER_NAME_STOPWORDS.has(words[0])) {
23763
+ words.shift();
23764
+ }
23765
+ while (words.length > 0 && SPEAKER_NAME_STOPWORDS.has(words[words.length - 1])) {
23766
+ words.pop();
23767
+ }
23768
+ return words.length > 0 ? words.join(" ") : void 0;
23769
+ }
23770
+ function isTemporalCueBoundary(char) {
23771
+ if (!char) {
23772
+ return true;
23773
+ }
23774
+ return !isAsciiLetterOrDigit(char);
23775
+ }
23776
+ function tokenizeReferenceQuery(query) {
23777
+ const tokens = [];
23778
+ let current = "";
23779
+ const flushCurrent = () => {
23780
+ if (current) {
23781
+ tokens.push(current);
23782
+ current = "";
23783
+ }
23784
+ };
23785
+ for (const char of query) {
23786
+ if (isAsciiLetterOrDigit(char)) {
23787
+ current += char;
23788
+ continue;
23789
+ }
23790
+ flushCurrent();
23791
+ if (char === "#" || char === ",") {
23792
+ tokens.push(char);
23793
+ } else if (isReferenceDash(char)) {
23794
+ tokens.push("-");
23795
+ }
23796
+ }
23797
+ flushCurrent();
23798
+ return tokens;
23799
+ }
23800
+ function parseReferenceNumbers(tokens, startIndex) {
23801
+ const numbers = [];
23802
+ let lastNumber;
23803
+ let pendingRangeStart;
23804
+ let index = startIndex;
23805
+ const scanEnd = Math.min(
23806
+ tokens.length,
23807
+ startIndex + DEFAULT_MAX_REFERENCES * REFERENCE_SCAN_TOKEN_FACTOR
23808
+ );
23809
+ for (; index < scanEnd; index += 1) {
23810
+ const token = tokens[index];
23811
+ const normalized = token.toLowerCase();
23812
+ const value = parseNonNegativeIntegerToken(token);
23813
+ if (value !== void 0) {
23814
+ if (pendingRangeStart !== void 0) {
23815
+ numbers.push(...expandReferenceRange(pendingRangeStart, value));
23816
+ pendingRangeStart = void 0;
23817
+ } else {
23818
+ numbers.push(value);
23819
+ }
23820
+ lastNumber = value;
23821
+ continue;
23822
+ }
23823
+ if (normalized === "#" || normalized === "number" || normalized === ",") {
23824
+ continue;
23825
+ }
23826
+ if (normalized === "-" || normalized === "to" || normalized === "through" || normalized === "thru") {
23827
+ if (lastNumber !== void 0) {
23828
+ if (numbers[numbers.length - 1] === lastNumber) {
23829
+ numbers.pop();
23830
+ }
23831
+ pendingRangeStart = lastNumber;
23832
+ }
23833
+ continue;
23834
+ }
23835
+ if (normalized === "and" && numbers.length > 0) {
23836
+ continue;
23837
+ }
23838
+ if (normalizeReferenceLabel(token)) {
23839
+ break;
23840
+ }
23841
+ break;
23842
+ }
23843
+ if (pendingRangeStart !== void 0) {
23844
+ numbers.push(pendingRangeStart);
23845
+ }
23846
+ return {
23847
+ numbers: [...new Set(numbers)],
23848
+ nextIndex: index
23849
+ };
23850
+ }
23851
+ function expandReferenceRange(start, end) {
23852
+ const low = Math.min(start, end);
23853
+ const high = Math.max(start, end);
23854
+ if (high - low + 1 > DEFAULT_MAX_REFERENCES) {
23855
+ return [start, end];
23856
+ }
23857
+ const values = [];
23858
+ for (let value = low; value <= high; value += 1) {
23859
+ values.push(value);
23860
+ }
23861
+ return values;
23862
+ }
23863
+ function normalizeReferenceLabel(token) {
23864
+ const normalized = token?.toLowerCase();
23865
+ switch (normalized) {
23866
+ case "step":
23867
+ case "steps":
23868
+ return "step";
23869
+ case "turn":
23870
+ case "turns":
23871
+ return "turn";
23872
+ case "action":
23873
+ case "actions":
23874
+ return "action";
23875
+ case "observation":
23876
+ case "observations":
23877
+ return "observation";
23878
+ default:
23879
+ return void 0;
23880
+ }
23881
+ }
23882
+ function candidateTurnIndexesForReference(reference) {
23883
+ const candidates = /* @__PURE__ */ new Set();
23884
+ if (reference.includeDirectTurn) {
23885
+ for (let offset = -1; offset <= 1; offset += 1) {
23886
+ candidates.add(reference.number + offset);
23887
+ }
23888
+ }
23889
+ const pairedBase = reference.number * 2;
23890
+ for (let offset = -2; offset <= 3; offset += 1) {
23891
+ candidates.add(pairedBase + offset);
23892
+ }
23893
+ return [...candidates].sort((left, right) => left - right);
23894
+ }
23895
+ function parseNonNegativeIntegerToken(token) {
23896
+ if (token.length === 0) {
23897
+ return void 0;
23898
+ }
23899
+ let value = 0;
23900
+ for (const char of token) {
23901
+ const code = char.charCodeAt(0);
23902
+ if (code < 48 || code > 57) {
23903
+ return void 0;
23904
+ }
23905
+ value = value * 10 + (code - 48);
23906
+ }
23907
+ return value;
23908
+ }
23909
+ function normalizePositiveInteger2(value, fallback) {
23910
+ if (typeof value !== "number" || !Number.isFinite(value)) {
23911
+ return fallback;
23912
+ }
23913
+ return Math.max(0, Math.floor(value));
23914
+ }
23915
+ function isAsciiLetterOrDigit(char) {
23916
+ const code = char.charCodeAt(0);
23917
+ return code >= 48 && code <= 57 || code >= 65 && code <= 90 || code >= 97 && code <= 122;
23918
+ }
23919
+ function isReferenceDash(char) {
23920
+ return char === "-" || char === "\u2010" || char === "\u2011" || char === "\u2012" || char === "\u2013" || char === "\u2014" || char === "\u2015";
23921
+ }
23922
+
23090
23923
  // ../remnic-core/src/recall-query-policy.ts
23091
23924
  var DEFAULT_STOPWORDS = /* @__PURE__ */ new Set([
23092
23925
  "the",
@@ -34089,7 +34922,7 @@ ${doc.content}` : doc.content,
34089
34922
  );
34090
34923
  return result;
34091
34924
  }
34092
- const { FallbackLlmClient: FallbackLlmClient2 } = await import("./fallback-llm-WCWNGIQ3.js");
34925
+ const { FallbackLlmClient: FallbackLlmClient2 } = await import("./fallback-llm-7PHTDZ4M.js");
34093
34926
  const useGateway = this.config.modelSource === "gateway";
34094
34927
  const modelSetting = this.config.semanticConsolidationModel;
34095
34928
  if (modelSetting === "fast" && this.fastLlm && !useGateway) {
@@ -36852,7 +37685,7 @@ ${lines.join("\n\n")}`;
36852
37685
  return null;
36853
37686
  }
36854
37687
  try {
36855
- const { getCalibrationRulesForRecall, buildCalibrationRecallSection } = await import("./calibration-WCHOK6DX.js");
37688
+ const { getCalibrationRulesForRecall, buildCalibrationRecallSection } = await import("./calibration-WBEDZUR3.js");
36856
37689
  const rules = await getCalibrationRulesForRecall(this.config.memoryDir);
36857
37690
  if (rules.length === 0) {
36858
37691
  recordRecallSectionMetric({
@@ -37930,6 +38763,27 @@ ${formatted}`;
37930
38763
  this.profiler.startSpan("assembly", profileTraceId);
37931
38764
  if (sharedCtx)
37932
38765
  this.appendRecallSection(sectionBuckets, "shared-context", sharedCtx);
38766
+ const explicitCueMaxChars = this.getRecallSectionMaxChars("explicit-cue") ?? this.config.explicitCueRecallMaxChars;
38767
+ if (this.config.explicitCueRecallEnabled && this.isRecallSectionEnabled("explicit-cue") && explicitCueMaxChars !== 0 && this.lcmEngine?.enabled && recallMode !== "no_recall") {
38768
+ try {
38769
+ const explicitCueSection = await buildExplicitCueRecallSection({
38770
+ engine: this.lcmEngine,
38771
+ sessionId: sessionKey,
38772
+ query: retrievalQuery,
38773
+ maxChars: explicitCueMaxChars,
38774
+ maxReferences: this.getRecallSectionNumber("explicit-cue", "maxResults") ?? this.config.explicitCueRecallMaxReferences
38775
+ });
38776
+ if (explicitCueSection) {
38777
+ this.appendRecallSection(
38778
+ sectionBuckets,
38779
+ "explicit-cue",
38780
+ explicitCueSection
38781
+ );
38782
+ }
38783
+ } catch (err) {
38784
+ log.debug(`Explicit cue recall assembly error: ${err}`);
38785
+ }
38786
+ }
37933
38787
  if (profile)
37934
38788
  this.appendRecallSection(
37935
38789
  sectionBuckets,
@@ -63117,7 +63971,7 @@ async function runSemanticRulePromoteCliCommand(options) {
63117
63971
  });
63118
63972
  }
63119
63973
  async function runCompoundingPromoteCliCommand(options) {
63120
- const { CompoundingEngine: CompoundingEngine2 } = await import("./engine-BIYI3P4J.js");
63974
+ const { CompoundingEngine: CompoundingEngine2 } = await import("./engine-KJWHWWLM.js");
63121
63975
  const config = parseConfig({
63122
63976
  memoryDir: options.memoryDir,
63123
63977
  qmdEnabled: false,
@@ -70914,8 +71768,7 @@ function buildTurnFingerprint(input) {
70914
71768
  // ../../src/index.ts
70915
71769
  import {
70916
71770
  resolvePrincipal as resolvePrincipal2,
70917
- resolveAgentAccessAuthToken as resolveAgentAccessAuthToken2,
70918
- hasEnabledLiveConnector as hasEnabledLiveConnector2
71771
+ resolveAgentAccessAuthToken as resolveAgentAccessAuthToken2
70919
71772
  } from "@remnic/core";
70920
71773
 
70921
71774
  // ../remnic-core/src/surfaces/dreams.ts
@@ -71494,6 +72347,17 @@ function liveConnectorCronExprForConfig(connectors) {
71494
72347
  return hasEnabledConnector ? ENABLED_LIVE_CONNECTOR_CRON_EXPR : DEFAULT_LIVE_CONNECTOR_CRON_EXPR;
71495
72348
  }
71496
72349
 
72350
+ // ../../src/openclaw-live-connector-config.ts
72351
+ function hasEnabledLiveConnectorConfig(config) {
72352
+ if (!config || typeof config !== "object" || Array.isArray(config)) return false;
72353
+ return Object.values(config).some((connector) => {
72354
+ if (!connector || typeof connector !== "object" || Array.isArray(connector)) {
72355
+ return false;
72356
+ }
72357
+ return connector.enabled === true;
72358
+ });
72359
+ }
72360
+
71497
72361
  // ../../src/index.ts
71498
72362
  var ENGRAM_MIGRATION_PROMISE = "__openclawEngramMigrationPromise";
71499
72363
  var CLI_REGISTERED_GUARD = "__openclawEngramCliRegistered";
@@ -71605,7 +72469,7 @@ function readPluginHooksPolicy(apiConfig, pluginId) {
71605
72469
  return loadPluginEntryFromFile(pluginId)?.["hooks"];
71606
72470
  }
71607
72471
  async function maybeRegisterLiveConnectorCron(orchestrator) {
71608
- if (!hasEnabledLiveConnector2(orchestrator.config.connectors)) return;
72472
+ if (!hasEnabledLiveConnectorConfig(orchestrator.config.connectors)) return;
71609
72473
  const jobsPath = path99.join(resolveHomeDir(), ".openclaw", "cron", "jobs.json");
71610
72474
  try {
71611
72475
  if (!existsSync12(jobsPath)) {
@@ -2192,6 +2192,23 @@
2192
2192
  "default": 300,
2193
2193
  "description": "Max tokens for each TMT summary node. Default: 300."
2194
2194
  },
2195
+ "explicitCueRecallEnabled": {
2196
+ "type": "boolean",
2197
+ "default": false,
2198
+ "description": "Front-load exact LCM evidence for query-visible cues such as turns, dates, ids, files, and tools."
2199
+ },
2200
+ "explicitCueRecallMaxChars": {
2201
+ "type": "number",
2202
+ "default": 2400,
2203
+ "minimum": 0,
2204
+ "description": "Character budget for the explicit cue evidence recall section."
2205
+ },
2206
+ "explicitCueRecallMaxReferences": {
2207
+ "type": "number",
2208
+ "default": 24,
2209
+ "minimum": 0,
2210
+ "description": "Maximum query-visible cues expanded by explicit cue recall."
2211
+ },
2195
2212
  "queryExpansionEnabled": {
2196
2213
  "type": "boolean",
2197
2214
  "default": false,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@remnic/plugin-openclaw",
3
- "version": "1.0.13",
3
+ "version": "1.0.15",
4
4
  "description": "OpenClaw adapter for Remnic memory — thin wrapper delegating to @remnic/core",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",
@@ -25,7 +25,7 @@
25
25
  },
26
26
  "dependencies": {
27
27
  "openai": "^6.0.0",
28
- "@remnic/core": "^1.1.5"
28
+ "@remnic/core": "^1.1.7"
29
29
  },
30
30
  "peerDependencies": {
31
31
  "openclaw": ">=2026.4.8"