//! Cookie security pattern detection.
//!
//! Compiled regex patterns for detecting insecure cookie configurations
//! across different languages and frameworks.

use regex::Regex;

/// Compiled regex patterns for detecting insecure cookie flags.
pub struct CookiePatterns {
    // Python/Flask/Django patterns
    pub python_secure_false: Regex,
    pub python_httponly_false: Regex,
    pub django_session_insecure: Regex,
    pub django_csrf_insecure: Regex,

    // JavaScript/Express patterns
    pub js_secure_false: Regex,
    pub js_httponly_false: Regex,

    // Generic patterns
    pub samesite_none: Regex,

    // YAML/Config patterns
    pub yaml_cookie_insecure: Regex,

    // Go patterns
    pub go_secure_false: Regex,
    pub go_httponly_false: Regex,
}

impl CookiePatterns {
    /// Compile all cookie security detection patterns.
    ///
    /// # Panics
    /// Panics if any regex pattern is invalid (programmer error).
    #[allow(clippy::expect_used)]
    pub fn compile() -> Self {
        Self {
            // Python/Flask patterns
            python_secure_false: Regex::new(r#"(?i)set_cookie\s*\([^)]*secure\s*=\s*False"#)
                .expect("valid regex"),

            python_httponly_false: Regex::new(r#"(?i)set_cookie\s*\([^)]*httponly\s*=\s*False"#)
                .expect("valid regex"),

            // Django settings
            django_session_insecure: Regex::new(
                r#"(?i)SESSION_COOKIE_(?:SECURE|HTTPONLY)\s*=\s*False"#,
            )
            .expect("valid regex"),

            django_csrf_insecure: Regex::new(r#"(?i)CSRF_COOKIE_(?:SECURE|HTTPONLY)\s*=\s*False"#)
                .expect("valid regex"),

            // JavaScript/Express patterns
            js_secure_false: Regex::new(r#"(?i)\.cookie\s*\([^)]*\{[^}]*secure\s*:\s*false"#)
                .expect("valid regex"),

            js_httponly_false: Regex::new(r#"(?i)\.cookie\s*\([^)]*\{[^}]*httpOnly\s*:\s*false"#)
                .expect("valid regex"),

            // SameSite=None requires Secure flag
            samesite_none: Regex::new(
                r#"(?i)(?:sameSite|samesite|same_site)\s*[:=]\s*["']?[Nn]one["']?"#,
            )
            .expect("valid regex"),

            // YAML config patterns
            yaml_cookie_insecure: Regex::new(
                r#"(?i)(?:cookie|session)[_-]?(?:secure|httponly)\s*:\s*(?:false|no|0)"#,
            )
            .expect("valid regex"),

            // Go patterns
            go_secure_false: Regex::new(r#"(?i)(?:&?http\.Cookie\s*\{[^}]*)?Secure\s*:\s*false"#)
                .expect("valid regex"),

            go_httponly_false: Regex::new(
                r#"(?i)(?:&?http\.Cookie\s*\{[^}]*)?HttpOnly\s*:\s*false"#,
            )
            .expect("valid regex"),
        }
    }

    /// Check if a line has `secure: true` or equivalent in any supported format.
    pub fn has_secure_flag(line: &str) -> bool {
        let line_lower = line.to_lowercase();
        [
            "secure: true",
            "secure:true",
            "secure = true",
            "secure=true",
            "\"secure\": true",
            "secure: yes",
            "secure: 1",
        ]
        .iter()
        .any(|p| line_lower.contains(p))
    }
}
