From b79a5281aa90a90151d0e3ce87c0e54164d7c8be Mon Sep 17 00:00:00 2001 From: Jayesh Betala Date: Wed, 27 May 2026 13:25:26 +0530 Subject: [PATCH] fix(learnings): fail closed when cross-project row lacks trusted field The --cross-project trust gate used a denylist (e.trusted === false), so rows with no trusted field (legacy rows written before the field existed in #988, hand-edited rows, or rows from other tools) were admitted because undefined === false is false. Switch to an allowlist (e.trusted !== true) to match the documented intent: cross-project learnings load only when explicitly trusted. Current-format rows are unaffected. --- bin/gstack-learnings-search | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/bin/gstack-learnings-search b/bin/gstack-learnings-search index 665be6fc1..a8756e61a 100755 --- a/bin/gstack-learnings-search +++ b/bin/gstack-learnings-search @@ -90,10 +90,13 @@ for (const taggedLine of lines) { const isCrossProject = sourceTag === 'cross'; e._crossProject = isCrossProject; - // Trust gate: cross-project learnings only loaded if trusted (user-stated) - // This prevents prompt injection from one project's AI-generated learnings - // silently influencing reviews in another project. - if (isCrossProject && e.trusted === false) continue; + // Trust gate: cross-project learnings only loaded if explicitly trusted + // (user-stated). This prevents prompt injection from one project's + // AI-generated learnings silently influencing reviews in another project. + // Fail closed: rows missing the trusted field (legacy entries written + // before the field existed, hand-edited rows, or rows from other tools) + // are treated as untrusted rather than admitted by default. + if (isCrossProject && e.trusted !== true) continue; entries.push(e); } catch {}