crabmate 0.4.0

Rust AI agent: OpenAI-compatible chat/completions, function calling, HTTP serve, ops CLI
Documentation
//! 正则表达式测试工具(纯内存)

use regex::Regex;

pub fn run(args_json: &str) -> String {
    let args: super::tool_param_types::RegexTestArgs = match serde_json::from_str(args_json) {
        Ok(a) => a,
        Err(e) => return format!("参数 JSON 无效: {e}"),
    };
    let pattern = args.pattern.trim();
    if pattern.is_empty() {
        return "错误:缺少 pattern 参数".to_string();
    }
    let re = match Regex::new(pattern) {
        Ok(r) => r,
        Err(e) => return format!("正则编译失败:{}", e),
    };
    let test_strings: Vec<&str> = args.test_strings.iter().map(String::as_str).collect();
    if test_strings.is_empty() {
        return "错误:缺少 test_strings 数组参数".to_string();
    }
    if test_strings.len() > 100 {
        return "错误:test_strings 上限 100 条".to_string();
    }

    let mut results = Vec::new();
    for s in &test_strings {
        if let Some(m) = re.captures(s) {
            let groups: Vec<String> = m
                .iter()
                .enumerate()
                .filter_map(|(i, g)| g.map(|g| format!("  group[{}]: {:?}", i, g.as_str())))
                .collect();
            results.push(format!("{:?}\n{}", s, groups.join("\n")));
        } else {
            results.push(format!("{:?}", s));
        }
    }
    let matched = results.iter().filter(|r| r.starts_with('')).count();
    format!(
        "pattern: {}\n匹配: {}/{}\n\n{}",
        pattern,
        matched,
        test_strings.len(),
        results.join("\n\n")
    )
}

#[cfg(test)]
mod tests {
    use super::*;

    #[test]
    fn basic_match() {
        let out = run(r#"{"pattern":"\\d+","test_strings":["abc123","hello"]}"#);
        assert!(out.contains("匹配: 1/2"));
        assert!(out.contains(''));
        assert!(out.contains(''));
    }

    #[test]
    fn capture_groups() {
        let out = run(r#"{"pattern":"(\\w+)@(\\w+)","test_strings":["user@host"]}"#);
        assert!(out.contains("group[1]"));
        assert!(out.contains("group[2]"));
    }

    #[test]
    fn invalid_regex() {
        let out = run(r#"{"pattern":"[invalid","test_strings":["x"]}"#);
        assert!(out.contains("正则编译失败"));
    }

    #[test]
    fn empty_pattern() {
        let out = run(r#"{"pattern":"","test_strings":["x"]}"#);
        assert!(out.contains("缺少 pattern"));
    }
}