teamMemSecretGuard.ts
1 import { feature } from 'bun:bundle' 2 3 /** 4 * Check if a file write/edit to a team memory path contains secrets. 5 * Returns an error message if secrets are detected, or null if safe. 6 * 7 * This is called from FileWriteTool and FileEditTool validateInput to 8 * prevent the model from writing secrets into team memory files, which 9 * would be synced to all repository collaborators. 10 * 11 * Callers can import and call this unconditionally — the internal 12 * feature('TEAMMEM') guard keeps it inert when the build flag is off. 13 * secretScanner assembles sensitive prefixes at runtime (ANT_KEY_PFX). 14 */ 15 export function checkTeamMemSecrets( 16 filePath: string, 17 content: string, 18 ): string | null { 19 if (feature('TEAMMEM')) { 20 /* eslint-disable @typescript-eslint/no-require-imports */ 21 const { isTeamMemPath } = 22 require('../../memdir/teamMemPaths.js') as typeof import('../../memdir/teamMemPaths.js') 23 const { scanForSecrets } = 24 require('./secretScanner.js') as typeof import('./secretScanner.js') 25 /* eslint-enable @typescript-eslint/no-require-imports */ 26 27 if (!isTeamMemPath(filePath)) { 28 return null 29 } 30 31 const matches = scanForSecrets(content) 32 if (matches.length === 0) { 33 return null 34 } 35 36 const labels = matches.map(m => m.label).join(', ') 37 return ( 38 `Content contains potential secrets (${labels}) and cannot be written to team memory. ` + 39 'Team memory is shared with all repository collaborators. ' + 40 'Remove the sensitive content and try again.' 41 ) 42 } 43 return null 44 }