Skip to content

Commit b5de5da

Browse files
committed
adding tests
1 parent 3bee2a9 commit b5de5da

File tree

2 files changed

+487
-33
lines changed

2 files changed

+487
-33
lines changed

pkg/telemetry/telemetry.go

Lines changed: 47 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -163,62 +163,76 @@ func checkConfigFileExists() bool {
163163

164164
// sanitizeErrorMessage removes potentially sensitive data from error messages
165165
func sanitizeErrorMessage(msg string) string {
166-
// Remove potential API tokens (sk_, ghp_, glpat_, npm_, pypi_, etc.)
167-
tokenPattern := regexp.MustCompile(`\b(sk|ghp|gh[pousr]|glpat|pypi|npm)_[A-Za-z0-9_-]+`)
166+
// Order matters! Process in this sequence to avoid conflicts
167+
168+
// 1. Remove URLs with embedded credentials FIRST (before email pattern catches them)
169+
urlCredsPattern := regexp.MustCompile(`https?://[^:]+:[^@]+@[^\s]+`)
170+
msg = urlCredsPattern.ReplaceAllString(msg, "[URL]")
171+
172+
// 2. Remove database/connection strings (enhanced to cover more protocols)
173+
connStringPattern := regexp.MustCompile(`(?i)(mongodb(\+srv)?|mysql|mariadb|postgresql|postgres|redis|mssql|oracle)://[^\s]+`)
174+
msg = connStringPattern.ReplaceAllString(msg, "$1://[CONNECTION]")
175+
176+
// 3. Remove potential API tokens - Fixed to include glpat with dash or underscore separator
177+
tokenPattern := regexp.MustCompile(`\b(sk|ghp|gh[pousr]|pypi|npm)_[A-Za-z0-9_-]+|\bglpat[-_][A-Za-z0-9_-]+`)
168178
msg = tokenPattern.ReplaceAllString(msg, "[TOKEN]")
169179

170-
// Remove AWS access keys (AKIA...)
180+
// 4. Remove AWS access keys (AKIA...)
171181
awsKeyPattern := regexp.MustCompile(`AKIA[0-9A-Z]{16}`)
172182
msg = awsKeyPattern.ReplaceAllString(msg, "[AWS_KEY]")
173183

174-
// Remove email addresses
184+
// 5. Remove email addresses (after URL credentials to avoid conflicts)
175185
emailPattern := regexp.MustCompile(`[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}`)
176186
msg = emailPattern.ReplaceAllString(msg, "[EMAIL]")
177187

178-
// Remove URLs with embedded credentials (https://user:pass@host)
179-
urlCredsPattern := regexp.MustCompile(`https?://[^:]+:[^@]+@[^\s]+`)
180-
msg = urlCredsPattern.ReplaceAllString(msg, "[URL]")
181-
182-
// Remove database/connection strings (enhanced to cover more protocols)
183-
connStringPattern := regexp.MustCompile(`(?i)(mongodb(\+srv)?|mysql|mariadb|postgresql|postgres|redis|mssql|oracle)://[^\s]+`)
184-
msg = connStringPattern.ReplaceAllString(msg, "$1://[CONNECTION]")
185-
186-
// Remove IPv4 addresses
188+
// 6. Remove IPv4 addresses
187189
ipv4Pattern := regexp.MustCompile(`\b(?:\d{1,3}\.){3}\d{1,3}\b`)
188190
msg = ipv4Pattern.ReplaceAllString(msg, "[IP]")
189191

190-
// Remove IPv6 addresses (simplified pattern covering common formats)
192+
// 7. Remove IPv6 addresses - Fixed to handle :: notation properly
191193
ipv6Pattern := regexp.MustCompile(`\b(?:[0-9a-fA-F]{1,4}:){7}[0-9a-fA-F]{1,4}\b|` +
194+
`\b(?:[0-9a-fA-F]{1,4}:){1,6}:[0-9a-fA-F]{1,4}\b|` +
192195
`\b(?:[0-9a-fA-F]{1,4}:){1,7}:\b|` +
193-
`\b:(?::[0-9a-fA-F]{1,4}){1,7}\b`)
196+
`\b::(?:[0-9a-fA-F]{1,4}:){0,6}[0-9a-fA-F]{1,4}\b|` +
197+
`\b[0-9a-fA-F]{1,4}::(?:[0-9a-fA-F]{1,4}:){0,5}[0-9a-fA-F]{1,4}\b|` +
198+
`\bfe80::[0-9a-fA-F:]+\b`)
194199
msg = ipv6Pattern.ReplaceAllString(msg, "[IP]")
195200

196-
// Remove file system paths - conservative to avoid API path false positives
197-
// Focus on protecting actual filesystem locations
198-
// Home directories
199-
homePattern := regexp.MustCompile(`(?:/(?:home|Users)/[^\s/]+|C:\\Users\\[^\s\\]+)`)
201+
// 8. Remove file system paths - order matters, most specific first
202+
// Home directories (exact match)
203+
homePattern := regexp.MustCompile(`/(?:home|Users)/[^\s/]+`)
200204
msg = homePattern.ReplaceAllString(msg, "[HOME]")
201205

206+
// Windows home directories
207+
windowsHomePattern := regexp.MustCompile(`C:\\Users\\[^\s\\]+`)
208+
msg = windowsHomePattern.ReplaceAllString(msg, "[HOME]")
209+
202210
// Temp directories
203-
tempPattern := regexp.MustCompile(`(?:/(?:tmp|var/tmp)/[^\s:]+)`)
211+
tempPattern := regexp.MustCompile(`/(?:tmp|var/tmp)/[^\s:]+`)
204212
msg = tempPattern.ReplaceAllString(msg, "[TEMP]")
205213

206-
// Absolute file paths with 3+ segments (likely filesystem, not API)
207-
absolutePathPattern := regexp.MustCompile(`(?:^|\s)(/[a-z]+(?:/[^\s:]+){2,})`)
208-
msg = absolutePathPattern.ReplaceAllString(msg, " [PATH]")
214+
// Home-relative paths - Fixed to accept single segment (~/file.txt)
215+
homeRelativePattern := regexp.MustCompile(`~(?:/[^\s:]+){1,}`)
216+
msg = homeRelativePattern.ReplaceAllString(msg, "[PATH]")
209217

210-
// Windows paths with backslashes
211-
windowsPathPattern := regexp.MustCompile(`[A-Z]:\\[^\s]+`)
212-
msg = windowsPathPattern.ReplaceAllString(msg, "[PATH]")
218+
// Absolute file paths - Only match known filesystem roots to avoid API false positives
219+
// Fixed: Don't include leading space in replacement
220+
absolutePathPattern := regexp.MustCompile(`(?:^|\s)(/(usr|home|var|opt|etc|srv|tmp|mnt)(?:/[^\s:]+)+)`)
221+
msg = absolutePathPattern.ReplaceAllStringFunc(msg, func(match string) string {
222+
if strings.HasPrefix(match, " ") {
223+
return " [PATH]" // Preserve single space
224+
}
225+
return "[PATH]" // Start of string
226+
})
213227

214-
// Home-relative paths
215-
homeRelativePattern := regexp.MustCompile(`~(?:/[^\s:]+){2,}`)
216-
msg = homeRelativePattern.ReplaceAllString(msg, "[PATH]")
228+
// Windows paths - Fixed to handle spaces in paths (Program Files)
229+
windowsPathPattern := regexp.MustCompile(`[A-Z]:[\\][^\n:]+`)
230+
msg = windowsPathPattern.ReplaceAllString(msg, "[PATH]")
217231

218-
// Remove potential passwords/secrets in error messages
219-
// Matches: password=xxx, password="xxx", password: xxx, api_key=xxx
220-
// Bounded to 100 chars to prevent runaway matching
221-
passwordPattern := regexp.MustCompile(`(?i)(password|passwd|pwd|secret|api[_-]?key)[\s=:]["']?([^\s,;"']{1,100})["']?`)
232+
// 9. Remove potential passwords/secrets - Fixed to handle colons and quotes properly
233+
// Matches: password=xxx, password:"xxx", password: xxx, api_key:xxx
234+
// Handle quoted values specially to avoid partial matches
235+
passwordPattern := regexp.MustCompile(`(?i)(password|passwd|pwd|secret|api[_-]key)[\s=:]+(?:"([^"]{1,100})"|'([^']{1,100})'|([^\s,;"'\n]{1,100}))`)
222236
msg = passwordPattern.ReplaceAllString(msg, "$1=[REDACTED]")
223237

224238
return msg

0 commit comments

Comments
 (0)