feat: custom secret patterns + rename Secret Scanner → Auto Redact
Users can now define custom regex patterns for proprietary token formats, internal URLs with keys, or any secret the built-in scanner doesn't cover. Patterns are added/toggled/removed from the Options page and apply to both the live interception (content.js) and the Test tab (popup.js). Renamed all user-facing "Secret scanning" labels to "Auto Redact" across popup and options. Internal variable names (secretScanning, SecretScanner) kept for backwards compatibility with stored settings. https://claude.ai/code/session_01KF4i7Ra7zCEDskxDBaNtcT
This commit is contained in:
@@ -2,7 +2,7 @@
|
||||
* Silent Send - Auto-Detect
|
||||
*
|
||||
* Scans text for potential PPI that the user hasn't configured.
|
||||
* This catches things the identity and secret scanner can't —
|
||||
* This catches things the identity and auto-redact scanner can't —
|
||||
* because the user forgot or didn't know to configure them.
|
||||
*
|
||||
* Returns warnings (not auto-redactions) so the user can decide.
|
||||
|
||||
@@ -198,9 +198,9 @@ const OrgPolicy = {
|
||||
},
|
||||
|
||||
/**
|
||||
* Get org-required secret scanner patterns.
|
||||
* Get org-required auto-redact patterns.
|
||||
*
|
||||
* @returns {Array} additional patterns to add to the secret scanner
|
||||
* @returns {Array} additional patterns to add to auto-redact
|
||||
*/
|
||||
async getOrgSecretPatterns() {
|
||||
const policy = await this.getPolicy();
|
||||
|
||||
@@ -1,11 +1,13 @@
|
||||
/**
|
||||
* Silent Send - Secret Scanner
|
||||
* Silent Send - Auto Redact (Secret Scanner)
|
||||
*
|
||||
* Detects common secret/credential patterns in text and either
|
||||
* warns or auto-redacts them. This catches things the identity-based
|
||||
* smart patterns can't: API keys, tokens, passwords, SSNs, credit
|
||||
* cards, private keys, connection strings, etc.
|
||||
*
|
||||
* Supports user-defined custom patterns for proprietary token formats.
|
||||
*
|
||||
* Each pattern has:
|
||||
* - name: human-readable label
|
||||
* - regex: detection pattern
|
||||
@@ -163,12 +165,37 @@ const SECRET_PATTERNS = [
|
||||
|
||||
const SecretScanner = {
|
||||
/**
|
||||
* Scan text for secrets. Returns list of findings.
|
||||
* Build the full pattern list (built-in + custom).
|
||||
* Custom patterns come from settings.customSecretPatterns.
|
||||
*/
|
||||
scan(text) {
|
||||
const findings = [];
|
||||
_buildPatterns(customPatterns) {
|
||||
const all = [...SECRET_PATTERNS];
|
||||
if (Array.isArray(customPatterns)) {
|
||||
for (const cp of customPatterns) {
|
||||
if (!cp.enabled || !cp.pattern) continue;
|
||||
try {
|
||||
all.push({
|
||||
name: cp.name || 'Custom Pattern',
|
||||
regex: new RegExp(cp.pattern, 'g'),
|
||||
redact: cp.redact || '[REDACTED-CUSTOM]',
|
||||
severity: 'critical',
|
||||
});
|
||||
} catch { /* invalid regex — skip */ }
|
||||
}
|
||||
}
|
||||
return all;
|
||||
},
|
||||
|
||||
for (const pattern of SECRET_PATTERNS) {
|
||||
/**
|
||||
* Scan text for secrets. Returns list of findings.
|
||||
* @param {string} text
|
||||
* @param {Array} [customPatterns] — from settings.customSecretPatterns
|
||||
*/
|
||||
scan(text, customPatterns) {
|
||||
const findings = [];
|
||||
const patterns = this._buildPatterns(customPatterns);
|
||||
|
||||
for (const pattern of patterns) {
|
||||
// Reset regex lastIndex
|
||||
pattern.regex.lastIndex = 0;
|
||||
let match;
|
||||
@@ -204,9 +231,11 @@ const SecretScanner = {
|
||||
/**
|
||||
* Redact all critical secrets in text. Warnings are not auto-redacted.
|
||||
* Returns { text, redactions[] }
|
||||
* @param {string} text
|
||||
* @param {Array} [customPatterns] — from settings.customSecretPatterns
|
||||
*/
|
||||
redact(text) {
|
||||
const findings = this.scan(text);
|
||||
redact(text, customPatterns) {
|
||||
const findings = this.scan(text, customPatterns);
|
||||
const redactions = [];
|
||||
let result = text;
|
||||
|
||||
|
||||
@@ -40,6 +40,7 @@ const DEFAULT_SETTINGS = {
|
||||
autoAddDetected: true,
|
||||
maxLogEntries: 100,
|
||||
customDomains: [],
|
||||
customSecretPatterns: [],
|
||||
categories: ['name', 'email', 'phone', 'address', 'ssn', 'dob', 'domain', 'password', 'general'],
|
||||
browserSync: false,
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user