#[cfg(test)]
#[allow(clippy::module_inception)]
pub mod ansi_test_utils {
use ansi_term;
use crate::ansi;
use crate::config::Config;
use crate::delta::State;
use crate::paint;
use crate::style::Style;
pub fn assert_line_has_style(
output: &str,
line_number: usize,
expected_prefix: &str,
expected_style: &str,
config: &Config,
) {
assert!(_line_has_style(
output,
line_number,
expected_prefix,
expected_style,
config,
false,
));
}
pub fn assert_line_contain_substring_style(
output: &str,
line_number: usize,
expected_prefix: &str,
expected_substring: &str,
expected_style: &str,
config: &Config,
) {
assert_eq!(
expected_substring,
_line_get_substring_matching_style(
output,
line_number,
expected_prefix,
expected_style,
config,
)
.unwrap()
);
}
pub fn assert_line_does_not_contain_substring_style(
output: &str,
line_number: usize,
expected_prefix: &str,
expected_style: &str,
config: &Config,
) {
assert!(_line_get_substring_matching_style(
output,
line_number,
expected_prefix,
expected_style,
config,
)
.is_none());
}
pub fn assert_line_does_not_have_style(
output: &str,
line_number: usize,
expected_prefix: &str,
expected_style: &str,
config: &Config,
) {
assert!(!_line_has_style(
output,
line_number,
expected_prefix,
expected_style,
config,
false,
));
}
pub fn assert_line_has_4_bit_color_style(
output: &str,
line_number: usize,
expected_prefix: &str,
expected_style: &str,
config: &Config,
) {
assert!(_line_has_style(
output,
line_number,
expected_prefix,
expected_style,
config,
true,
));
}
pub fn assert_line_has_no_color(output: &str, line_number: usize, expected_prefix: &str) {
let line = output.lines().nth(line_number).unwrap();
let stripped_line = ansi::strip_ansi_codes(line);
assert!(stripped_line.starts_with(expected_prefix));
assert_eq!(line, stripped_line);
}
pub fn assert_line_has_syntax_highlighted_substring(
output: &str,
line_number: usize,
substring_begin: usize,
expected_substring: &str,
filename_for_highlighting: &str,
state: State,
config: &Config,
) {
assert!(
filename_for_highlighting.contains('.'),
"expecting filename, not just a file extension"
);
let line = output.lines().nth(line_number).unwrap();
let substring_end = substring_begin + expected_substring.len();
let substring = &ansi::strip_ansi_codes(line)[substring_begin..substring_end];
assert_eq!(substring, expected_substring);
let painted_substring = paint_line(substring, filename_for_highlighting, state, config);
assert!(line.contains(painted_substring.trim_end()));
}
pub fn assert_has_color_other_than_plus_color(string: &str, config: &Config) {
let (string_without_any_color, string_with_plus_color_only) =
get_color_variants(string, config);
assert_ne!(string, string_without_any_color);
assert_ne!(string, string_with_plus_color_only);
}
pub fn assert_has_plus_color_only(string: &str, config: &Config) {
let (string_without_any_color, string_with_plus_color_only) =
get_color_variants(string, config);
assert_ne!(string, string_without_any_color);
assert_eq!(string, string_with_plus_color_only);
}
pub fn get_color_variants(string: &str, config: &Config) -> (String, String) {
let string_without_any_color = ansi::strip_ansi_codes(string);
let string_with_plus_color_only = config
.plus_style
.ansi_term_style
.paint(&string_without_any_color);
(
string_without_any_color.to_string(),
string_with_plus_color_only.to_string(),
)
}
pub fn paint_line(
line: &str,
filename_for_highlighting: &str,
state: State,
config: &Config,
) -> String {
let mut output_buffer = String::new();
let mut unused_writer = Vec::<u8>::new();
let mut painter = paint::Painter::new(&mut unused_writer, config);
let syntax_highlighted_style = Style {
is_syntax_highlighted: true,
..Style::new()
};
painter.set_syntax(Some(filename_for_highlighting));
painter.set_highlighter();
let lines = vec![(line.to_string(), state)];
let syntax_style_sections = paint::get_syntax_style_sections_for_lines(
&lines,
painter.highlighter.as_mut(),
config,
);
let diff_style_sections = vec![vec![(syntax_highlighted_style, lines[0].0.as_str())]];
paint::Painter::paint_lines(
&lines,
&syntax_style_sections,
&diff_style_sections,
&[false],
&mut output_buffer,
config,
&mut None,
None,
paint::BgShouldFill::default(),
);
output_buffer
}
fn _line_extract<'a>(output: &'a str, line_number: usize, expected_prefix: &str) -> &'a str {
let line = output.lines().nth(line_number).unwrap();
assert!(ansi::strip_ansi_codes(line).starts_with(expected_prefix));
line
}
fn _line_get_substring_matching_style<'a>(
output: &'a str,
line_number: usize,
expected_prefix: &str,
expected_style: &str,
config: &Config,
) -> Option<&'a str> {
let line = _line_extract(output, line_number, expected_prefix);
let style = Style::from_str(
expected_style,
None,
None,
config.true_color,
config.git_config.as_ref(),
);
style.get_matching_substring(line)
}
fn _line_has_style(
output: &str,
line_number: usize,
expected_prefix: &str,
expected_style: &str,
config: &Config,
_4_bit_color: bool,
) -> bool {
let line = _line_extract(output, line_number, expected_prefix);
let mut style = Style::from_str(
expected_style,
None,
None,
config.true_color,
config.git_config(),
);
if _4_bit_color {
style.ansi_term_style.foreground = style
.ansi_term_style
.foreground
.map(ansi_term_fixed_foreground_to_4_bit_color);
}
style.is_applied_to(line)
}
fn ansi_term_fixed_foreground_to_4_bit_color(color: ansi_term::Color) -> ansi_term::Color {
match color {
ansi_term::Color::Fixed(30) => ansi_term::Color::Black,
ansi_term::Color::Fixed(31) => ansi_term::Color::Red,
ansi_term::Color::Fixed(32) => ansi_term::Color::Green,
ansi_term::Color::Fixed(33) => ansi_term::Color::Yellow,
ansi_term::Color::Fixed(34) => ansi_term::Color::Blue,
ansi_term::Color::Fixed(35) => ansi_term::Color::Purple,
ansi_term::Color::Fixed(36) => ansi_term::Color::Cyan,
ansi_term::Color::Fixed(37) => ansi_term::Color::White,
color => panic!(
"Invalid 4-bit color: {:?}. \
(Add bright color entries to this map if needed for tests.",
color
),
}
}
}