cursortanium 0.1.0

A solid cursor for Rust
Documentation
mod helpers;

use cursortanium::Cursor;
use helpers::{run_parse_test, TestCase};

fn parse(cursor: &mut Cursor) -> Option<String> {
    let mut tokens = vec![];

    while let Some(token) = parse_token(&mut *cursor) {
        tokens.push(token);
    }

    Some(tokens.concat())
}

fn parse_token(cursor: &mut Cursor) -> Option<String> {
    match parse_hyphens(&mut *cursor) {
        None => parse_string(&mut *cursor),
        a => a,
    }
}

fn parse_hyphens(cursor: &mut Cursor) -> Option<String> {
    if !cursor.starts_with("-") {
        return None;
    }

    let marker = cursor.clone();

    while cursor.starts_with("-") {
        cursor.next_mut(1);
    }

    Some(marker.take_until(&cursor))
}

fn parse_string(cursor: &mut Cursor) -> Option<String> {
    let mut chunks = vec![];

    if cursor.starts_with("\"") {
        cursor.next_mut(1);
    } else {
        return None;
    };

    let mut marker = cursor.clone();

    while !cursor.starts_with("\"") && !cursor.is_eof() {
        if cursor.starts_with("\\") {
            chunks.push(marker.take_until(&cursor));
            cursor.next_mut(1);
            marker = cursor.clone();
            cursor.next_mut(1);
        } else {
            cursor.next_mut(1);
        }
    }

    chunks.push(marker.take_until(&cursor));

    if cursor.starts_with("\"") {
        cursor.next_mut(1);
    };

    Some(chunks.concat())
}

#[test]
fn test_parse_string() {
    let mut test_cases = vec![];

    test_cases.push(TestCase(
        String::from(
            r#"
                🌖----"Hello, \"World\""----🌖
            "#,
        ),
        String::from(r#"----Hello, "World"----"#),
    ));

    for test_case in test_cases {
        run_parse_test(parse, test_case);
    }
}