Skip to main content

browser_automation_cli/
validation.rs

1//! Input validation helpers for CLI flags and paths.
2
3/// Check if a session name is valid (alphanumeric, hyphens, and underscores only).
4pub fn is_valid_session_name(name: &str) -> bool {
5    !name.is_empty()
6        && name
7            .chars()
8            .all(|c| c.is_alphanumeric() || c == '-' || c == '_')
9}
10
11/// Convert arbitrary caller-provided text into a valid session-name component.
12pub fn sanitize_session_component(value: &str) -> String {
13    let mut out = String::new();
14    let mut last_was_sep = false;
15
16    for c in value.chars() {
17        if c.is_alphanumeric() {
18            out.extend(c.to_lowercase());
19            last_was_sep = false;
20        } else if c == '-' || c == '_' {
21            if !out.is_empty() && !last_was_sep {
22                out.push(c);
23                last_was_sep = true;
24            }
25        } else if !out.is_empty() && !last_was_sep {
26            out.push('-');
27            last_was_sep = true;
28        }
29    }
30
31    while out.ends_with(['-', '_']) {
32        out.pop();
33    }
34
35    out
36}
37
38/// Generate error message for invalid session name
39pub fn session_name_error(name: &str) -> String {
40    format!(
41        "Invalid session name '{}'. Only alphanumeric characters, hyphens, and underscores are allowed.",
42        name
43    )
44}
45
46#[cfg(test)]
47mod tests {
48    use super::*;
49
50    #[test]
51    fn sanitize_session_component_produces_valid_component() {
52        let value = sanitize_session_component("Next Dev Loop: /Users/me/worktree!");
53
54        assert_eq!(value, "next-dev-loop-users-me-worktree");
55        assert!(is_valid_session_name(&value));
56    }
57
58    #[test]
59    fn sanitize_session_component_trims_separators() {
60        assert_eq!(sanitize_session_component(" --Agent__ "), "agent");
61    }
62}