Match bash color sequences

This commit is contained in:
Ferran Basora 2019-03-02 19:29:03 +00:00
parent 795a92150e
commit 45d93c644c

View File

@ -1,7 +1,8 @@
use std::collections::HashMap; use std::collections::HashMap;
use regex::Regex; use regex::Regex;
const PATTERNS: [(&'static str, &'static str); 10] = [ const PATTERNS: [(&'static str, &'static str); 11] = [
("bash", r"[[:cntrl:]]\[([0-9]{1,2};)?([0-9]{1,2})m"),
("url", r"((https?://|git@|git://|ssh://|ftp://|file:///)[\w?=%/_.:,;~@!#$&()*+-]*)"), ("url", r"((https?://|git@|git://|ssh://|ftp://|file:///)[\w?=%/_.:,;~@!#$&()*+-]*)"),
("diff_a", r"--- a/([^ ]+)"), ("diff_a", r"--- a/([^ ]+)"),
("diff_b", r"\+\+\+ b/([^ ]+)"), ("diff_b", r"\+\+\+ b/([^ ]+)"),
@ -46,7 +47,7 @@ impl<'a> State<'a> {
let mut matches = Vec::new(); let mut matches = Vec::new();
let patterns = PATTERNS.iter().map(|tuple| let patterns = PATTERNS.iter().map(|tuple|
Regex::new(tuple.1).unwrap() (tuple.0, Regex::new(tuple.1).unwrap())
).collect::<Vec<_>>(); ).collect::<Vec<_>>();
for (index, line) in self.lines.iter().enumerate() { for (index, line) in self.lines.iter().enumerate() {
@ -54,17 +55,17 @@ impl<'a> State<'a> {
let mut offset: i32 = 0; let mut offset: i32 = 0;
loop { loop {
let submatches = patterns.iter().filter_map(|pattern| let submatches = patterns.iter().filter_map(|tuple|
match pattern.find_iter(chunk).nth(0) { match tuple.1.find_iter(chunk).nth(0) {
Some(m) => Some((pattern, m)), Some(m) => Some((tuple.0, tuple.1.clone(), m)),
None => None None => None
} }
).collect::<Vec<_>>(); ).collect::<Vec<_>>();
let first_match_option = submatches.iter().min_by(|x, y| x.1.start().cmp(&y.1.start())); let first_match_option = submatches.iter().min_by(|x, y| x.2.start().cmp(&y.2.start()));
if let Some(first_match) = first_match_option { if let Some(first_match) = first_match_option {
let (pattern, matching) = first_match; let (name, pattern, matching) = first_match;
let text = &chunk[matching.start()..matching.end()]; // FIXME? matching.as_str() let text = matching.as_str();
if let Some(captures) = pattern.captures(text) { if let Some(captures) = pattern.captures(text) {
let (subtext, substart) = if let Some(capture) = captures.get(1) { let (subtext, substart) = if let Some(capture) = captures.get(1) {
@ -73,12 +74,15 @@ impl<'a> State<'a> {
(matching.as_str(), 0) (matching.as_str(), 0)
}; };
matches.push(Match{ // Never hint or broke bash color sequences
x: offset + matching.start() as i32 + substart as i32, if *name != "bash" {
y: index as i32, matches.push(Match{
text: subtext, x: offset + matching.start() as i32 + substart as i32,
hint: None y: index as i32,
}); text: subtext,
hint: None
});
}
chunk = chunk.get(matching.end()..).expect("Unknown chunk"); chunk = chunk.get(matching.end()..).expect("Unknown chunk");
offset = offset + matching.end() as i32; offset = offset + matching.end() as i32;
@ -177,6 +181,13 @@ mod tests {
assert_eq!(results.last().unwrap().hint.clone().unwrap(), "a"); assert_eq!(results.last().unwrap().hint.clone().unwrap(), "a");
} }
#[test]
fn match_bash () {
let output = "path: /var/log/nginx.log\npath: test/log/nginx.log";
assert_eq!(match_lines(output).len(), 2);
}
#[test] #[test]
fn match_paths () { fn match_paths () {
let output = "Lorem /tmp/foo/bar lorem\n Lorem /var/log/bootstrap.log lorem ../log/kern.log lorem"; let output = "Lorem /tmp/foo/bar lorem\n Lorem /var/log/bootstrap.log lorem ../log/kern.log lorem";