photon_backend/
sanitize.rs1pub const MAX_ERROR_MESSAGE_CHARS: usize = 512;
5
6#[must_use]
11pub fn sanitize_error_message(raw: &str) -> String {
12 let mut out = raw.replace('\0', "");
13 for needle in [
14 "password=",
15 "Password=",
16 "secret=",
17 "Secret=",
18 "token=",
19 "Token=",
20 "Bearer ",
21 "authorization:",
22 ] {
23 if let Some(idx) = out.find(needle) {
24 let end = (idx + needle.len() + 8).min(out.len());
25 out.replace_range(idx..end, &format!("{needle}[redacted]"));
26 }
27 }
28 if out.chars().count() > MAX_ERROR_MESSAGE_CHARS {
29 out = out.chars().take(MAX_ERROR_MESSAGE_CHARS).collect();
30 out.push('…');
31 }
32 out
33}
34
35#[cfg(test)]
36mod tests {
37 use super::*;
38
39 #[test]
40 fn truncates_long_messages() {
41 let long = "x".repeat(800);
42 let s = sanitize_error_message(&long);
43 assert!(s.chars().count() <= MAX_ERROR_MESSAGE_CHARS + 1);
44 assert!(s.ends_with('…'));
45 }
46
47 #[test]
48 fn redacts_password_prefix() {
49 let s = sanitize_error_message("db failed password=hunter2 more");
50 assert!(s.contains("[redacted]"));
51 assert!(!s.contains("hunter2"));
52 }
53
54 #[test]
55 fn leaves_short_benign_messages() {
56 let s = sanitize_error_message("handler returned Err");
57 assert_eq!(s, "handler returned Err");
58 }
59}