pub trait RustScannerExt<'text>: Sealed {
    // Required methods
    fn scan_rust_line_comment(&mut self) -> ScannerResult<'text, &'text str>;
    fn scan_rust_block_comment(&mut self) -> ScannerResult<'text, &'text str>;
    fn scan_rust_identifier(&mut self) -> ScannerResult<'text, &'text str>;
    fn scan_rust_raw_identifier(&mut self) -> ScannerResult<'text, &'text str>;
    fn scan_rust_char(&mut self) -> ScannerResult<'text, &'text str>;
    fn scan_rust_string(&mut self) -> ScannerResult<'text, &'text str>;
    fn scan_rust_raw_string(&mut self) -> ScannerResult<'text, &'text str>;
    fn scan_rust_int_dec(&mut self) -> ScannerResult<'text, &'text str>;
    fn scan_rust_int_hex(&mut self) -> ScannerResult<'text, &'text str>;
    fn scan_rust_int_oct(&mut self) -> ScannerResult<'text, &'text str>;
    fn scan_rust_int_bin(&mut self) -> ScannerResult<'text, &'text str>;
    fn scan_rust_float(&mut self) -> ScannerResult<'text, &'text str>;
}
Expand description

Scanner extension for scanning Rust tokens.

Note: When using the scan_rust_*() methods, the order they are called matters.

Required Methods§

source

fn scan_rust_line_comment(&mut self) -> ScannerResult<'text, &'text str>

Scans a single Rust line comment.

Note: This has the same lifetime as the original text, so the scanner can continue to be used while this exists.

Example
use text_scanner::{ext::RustScannerExt, Scanner};

let text = r#"
  // Line Comment
  //! Inner Doc Comment
  /// Outer Doc Comment
"#;

let comments = [
    (3..18,  "// Line Comment"),
    (21..42, "//! Inner Doc Comment"),
    (45..66, "/// Outer Doc Comment"),
];

let mut scanner = Scanner::new(text);
for comment in comments {
    scanner.skip_whitespace();
    assert_eq!(scanner.scan_rust_line_comment(), Ok(comment));
}
source

fn scan_rust_block_comment(&mut self) -> ScannerResult<'text, &'text str>

Scans a single Rust block comment.

Note: Rust block comment allow nested block comments.

Note: This has the same lifetime as the original text, so the scanner can continue to be used while this exists.

Example
use text_scanner::{ext::RustScannerExt, Scanner};

let text = r#"
  /* Block Comment */

  /* Multi
  // Line
     Block
     Comment */

  /* Multi
  // Line /*
     Nested
  /* Block */
     Comment */ */

  /* Unterminated Block Comment
"#;

let comments = [
    (3..22,    "/* Block Comment */"),
    (26..71,   "/* Multi\n  // Line\n     Block\n     Comment */"),
    (75..141,  "/* Multi\n  // Line /*\n     Nested\n  /* Block */\n     Comment */ */"),
    (145..175, "/* Unterminated Block Comment\n"),
];

let mut scanner = Scanner::new(text);
for comment in comments {
    scanner.skip_whitespace();
    assert_eq!(scanner.scan_rust_block_comment(), Ok(comment));
}
source

fn scan_rust_identifier(&mut self) -> ScannerResult<'text, &'text str>

Scans a single Rust identifier.

Note: This does not differentiate between Rust identifiers and Rust keywords. If needed manually check if the returned Ok string slice is a Rust keyword or not.

Note: This has the same lifetime as the original text, so the scanner can continue to be used while this exists.

Example
use text_scanner::{ext::RustScannerExt, Scanner};

let text = r#"
  foo
  foo_bar
  _foo_
  æøå
  ľúbiť
  東京
"#;

let idents = [
    (3..6,   "foo"),
    (9..16,  "foo_bar"),
    (19..24, "_foo_"),
    (27..33, "æøå"),
    (36..44, "ľúbiť"),
    (47..53, "東京"),
];

let mut scanner = Scanner::new(text);
for ident in idents {
    scanner.skip_whitespace();
    assert_eq!(scanner.scan_rust_identifier(), Ok(ident));
}
source

fn scan_rust_raw_identifier(&mut self) -> ScannerResult<'text, &'text str>

Scans a single raw Rust identifier.

Note: This does not differentiate between Rust identifiers and Rust keywords. If needed manually check if the returned Ok string slice is a Rust keyword or not.

Note: This has the same lifetime as the original text, so the scanner can continue to be used while this exists.

Example
use text_scanner::{ext::RustScannerExt, Scanner};

let text = r#"
  r#foo
  r#type
  r#while
  r#æøå
  r#ľúbiť
  r#東京
"#;

let idents = [
    (3..8,   "r#foo"),
    (11..17, "r#type"),
    (20..27, "r#while"),
    (30..38, "r#æøå"),
    (41..51, "r#ľúbiť"),
    (54..62, "r#東京"),
];

let mut scanner = Scanner::new(text);
for ident in idents {
    scanner.skip_whitespace();
    assert_eq!(scanner.scan_rust_raw_identifier(), Ok(ident));
}
source

fn scan_rust_char(&mut self) -> ScannerResult<'text, &'text str>

Scans a single Rust character.

Note: This has the same lifetime as the original text, so the scanner can continue to be used while this exists.

Example
use text_scanner::{ext::RustScannerExt, Scanner};

let text = r#"
  'A'
  'Æ'
  'Á'
  '東'
  '🦀'

  '"'
  '\\'
  '\''
  '\n'
  '\0'
"#;

let chars = [
    (3..6,     "'A'"),
    (9..13,    "'Æ'"),
    (16..20,   "'Á'"),
    (23..28,   "'東'"),
    (31..37,   "'🦀'"),
    (41..44,   "'\"'"),
    (47..51,   "'\\\\'"),
    (54..58,   "'\\''"),
    (61..65, "'\\n'"),
    (68..72, "'\\0'"),
];

let mut scanner = Scanner::new(text);
for c in chars {
    scanner.skip_whitespace();
    assert_eq!(scanner.scan_rust_char(), Ok(c));
}
source

fn scan_rust_string(&mut self) -> ScannerResult<'text, &'text str>

Scans a single Rust string.

Note: This has the same lifetime as the original text, so the scanner can continue to be used while this exists.

Example
use text_scanner::{ext::RustScannerExt, Scanner};

let text = r#"
  "Hello World"

  "Rust strings
   can span multiple
   lines"

  "Foo \" Bar"

  "Unterminated String
"#;

let strings = [
    (3..16,   "\"Hello World\""),
    (20..64,  "\"Rust strings\n   can span multiple\n   lines\""),
    (68..80,  "\"Foo \\\" Bar\""),
    (84..105, "\"Unterminated String\n"),
];

let mut scanner = Scanner::new(text);
for string in strings {
    scanner.skip_whitespace();
    assert_eq!(scanner.scan_rust_string(), Ok(string));
}
source

fn scan_rust_raw_string(&mut self) -> ScannerResult<'text, &'text str>

Scans a single raw Rust string.

Note: This has the same lifetime as the original text, so the scanner can continue to be used while this exists.

Example
use text_scanner::{ext::RustScannerExt, Scanner};

let text = r#####"
  r#"Hello World"#

  r###"Raw Rust strings"
      "can span multiple"
      "lines"###

  r##"Foo #"# Bar"##

  r###"Unterminated String
"#####;

let raw_strings = [
    (3..19,    "r#\"Hello World\"#"),
    (23..88,   "r###\"Raw Rust strings\"\n      \"can span multiple\"\n      \"lines\"###"),
    (92..110,  "r##\"Foo #\"# Bar\"##"),
    (114..139, "r###\"Unterminated String\n"),
];

let mut scanner = Scanner::new(text);
for raw_string in raw_strings {
    scanner.skip_whitespace();
    assert_eq!(scanner.scan_rust_raw_string(), Ok(raw_string));
}
source

fn scan_rust_int_dec(&mut self) -> ScannerResult<'text, &'text str>

Scans a single Rust integer decimal literal.

Note: Rust integer literals do not allow a sign in front of the literal, i.e. -10 is two tokens ["-", "10"].

Note: This has the same lifetime as the original text, so the scanner can continue to be used while this exists.

Example
use text_scanner::{ext::RustScannerExt, Scanner};

let text = r#"
  0
  123

  1_
  1__
  1_2_3
  1__2__3__
"#;

let integers = [
    (3..4,   "0"),
    (7..10,  "123"),
    (14..16, "1_"),
    (19..22, "1__"),
    (25..30, "1_2_3"),
    (33..42, "1__2__3__"),
];

let mut scanner = Scanner::new(text);
for integer in integers {
    scanner.skip_whitespace();
    assert_eq!(scanner.scan_rust_int_dec(), Ok(integer));
}
source

fn scan_rust_int_hex(&mut self) -> ScannerResult<'text, &'text str>

Scans a single Rust integer hex literal.

Note: This has the same lifetime as the original text, so the scanner can continue to be used while this exists.

Example
use text_scanner::{ext::RustScannerExt, Scanner};

let text = r#"
  0x0
  0xFF

  0x_FF_FF_FF_FF_
"#;

let hex_integers = [
    (3..6,   "0x0"),
    (9..13,  "0xFF"),
    (17..32, "0x_FF_FF_FF_FF_"),
];

let mut scanner = Scanner::new(text);
for hex_integer in hex_integers {
    scanner.skip_whitespace();
    assert_eq!(scanner.scan_rust_int_hex(), Ok(hex_integer));
}
source

fn scan_rust_int_oct(&mut self) -> ScannerResult<'text, &'text str>

Scans a single Rust integer octal literal.

Note: This has the same lifetime as the original text, so the scanner can continue to be used while this exists.

Example
use text_scanner::{ext::RustScannerExt, Scanner};

let text = r#"
  0o0
  0o100

  0o_1_0_0_
"#;

let oct_integers = [
    (3..6,   "0o0"),
    (9..14,  "0o100"),
    (18..27, "0o_1_0_0_"),
];

let mut scanner = Scanner::new(text);
for oct_integer in oct_integers {
    scanner.skip_whitespace();
    assert_eq!(scanner.scan_rust_int_oct(), Ok(oct_integer));
}
source

fn scan_rust_int_bin(&mut self) -> ScannerResult<'text, &'text str>

Scans a single Rust integer binary literal.

Note: This has the same lifetime as the original text, so the scanner can continue to be used while this exists.

Example
use text_scanner::{ext::RustScannerExt, Scanner};

let text = r#"
  0b0
  0b1
  0b10
  0b11
  0b100

  0b_1_0_0_
"#;

let bin_integers = [
    (3..6,   "0b0"),
    (9..12,  "0b1"),
    (15..19, "0b10"),
    (22..26, "0b11"),
    (29..34, "0b100"),
    (38..47, "0b_1_0_0_"),
];

let mut scanner = Scanner::new(text);
for bin_integer in bin_integers {
    scanner.skip_whitespace();
    assert_eq!(scanner.scan_rust_int_bin(), Ok(bin_integer));
}
source

fn scan_rust_float(&mut self) -> ScannerResult<'text, &'text str>

Scans a single Rust floating-point literal.

Note: This has the same lifetime as the original text, so the scanner can continue to be used while this exists.

Example
use text_scanner::{ext::RustScannerExt, Scanner};

let text = r#"
  12.
  12.34

  12.
  12.34

  12.34E56
  12.34E+56
  12.34E-56

  1_2_.
  1_2_.3_4_

  1_2_.3_4_E_5_6_
  1_2_.3_4_E+_5_6_
  1_2_.3_4_E-_5_6_
"#;

let floats = [
    (3..6,     "12."),
    (9..14,    "12.34"),
    (18..21,   "12."),
    (24..29,   "12.34"),
    (33..41,   "12.34E56"),
    (44..53,   "12.34E+56"),
    (56..65,   "12.34E-56"),
    (69..74,   "1_2_."),
    (77..86,   "1_2_.3_4_"),
    (90..105,  "1_2_.3_4_E_5_6_"),
    (108..124, "1_2_.3_4_E+_5_6_"),
    (127..143, "1_2_.3_4_E-_5_6_"),
];

let mut scanner = Scanner::new(text);
for float in floats {
    scanner.skip_whitespace();
    assert_eq!(scanner.scan_rust_float(), Ok(float));
}

Implementors§

source§

impl<'text> RustScannerExt<'text> for Scanner<'text>