fix(core): enforce secret scanning before team memory sync#115
Merged
Conversation
Wire the existing `scan_for_secrets` into `scan_local_files`, the choke point every entry passes through before a team-memory push. A file with any detected secret is now blocked from sync entirely, and only the matched pattern labels and the file path are logged (via tracing::warn) — never the matched text — so the log cannot leak the credential. Implements the team-memory-upload acceptance criteria of #102: - scan_for_secrets is called before team memory upload - secret-like content blocks the memory write - logs do not include matched secret values Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
There was a problem hiding this comment.
Pull request overview
This PR enforces secret scanning on the team-memory sync upload path by invoking scan_for_secrets during TeamMemorySync::scan_local_files, blocking any .md file that matches a secret pattern from being packed/uploaded. This closes the gap where secret scanning previously existed but was only exercised in tests, not enforced on the upload boundary.
Changes:
- Add secret scanning enforcement to
scan_local_files, skipping secret-bearing files and emitting a warning that includes only labels + path. - Add integration-style tests ensuring secret-bearing files are excluded from scan results while clean files still upload.
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Comment on lines
+365
to
+381
| // Enforce secret scanning before a file can ever be packed | ||
| // for upload. A file with detected secrets is blocked from | ||
| // sync entirely. Only the pattern labels and path are | ||
| // logged — never the matched text — so the log itself does | ||
| // not leak the credential. | ||
| let secrets = scan_for_secrets(&content); | ||
| if !secrets.is_empty() { | ||
| let labels: Vec<&str> = | ||
| secrets.iter().map(|m| m.label.as_str()).collect(); | ||
| warn!( | ||
| "Blocking team memory file {:?} from sync: detected {} \ | ||
| ({} secret pattern(s))", | ||
| key, | ||
| labels.join(", "), | ||
| labels.len(), | ||
| ); | ||
| continue; |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Closes part of #102. The repo already had a
scan_for_secretsfunction, but it was only exercised in tests — it was not enforced on the upload path, so a team-memory.mdfile containing an API key, token, or private key could be packed and synced to the shared store.This wires
scan_for_secretsintoscan_local_files— the single choke point every entry passes through beforepush/upload_batch. A file with any detected secret is now blocked from sync entirely.What changed
scan_local_filesscans each.mdfile's content; ifscan_for_secretsreturns any match, the file is skipped (never packed for upload).tracing::warn— never the matched text — so the log itself cannot leak the credential.Acceptance criteria (#102, team-memory-upload slice)
scan_for_secretsis called before team memory uploadTests
Added two
scan_local_filestests; full module suite green (25 passed, 0 failed):test_scan_local_files_blocks_file_with_secret— a secret-bearing file is excluded while a clean sibling still uploads.test_scan_local_files_blocks_all_when_every_file_has_secret— an all-secrets dir yields zero upload entries.Scope / notes
origin/main; no rebase of other in-flight branches.🤖 Generated with Claude Code