Merge pull request #6525 from roc-lang/fix_text_contrast

less colors and more contrast in terminal
This commit is contained in:
Anton-4 2024-02-20 15:46:13 +01:00 committed by GitHub
commit b5f68bc020
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
14 changed files with 99 additions and 104 deletions

1
Cargo.lock generated
View file

@ -2196,6 +2196,7 @@ version = "0.0.1"
dependencies = [
"bumpalo",
"indoc",
"regex",
"roc_build",
"roc_cli",
"roc_repl_cli",

View file

@ -440,6 +440,7 @@ pub fn test(matches: &ArgMatches, triple: Triple) -> io::Result<i32> {
use roc_build::program::report_problems_monomorphized;
use roc_load::{ExecutionMode, FunctionKind, LoadConfig, LoadMonomorphizedError};
use roc_packaging::cache;
use roc_reporting::report::ANSI_STYLE_CODES;
use roc_target::TargetInfo;
let start_time = Instant::now();
@ -541,7 +542,7 @@ pub fn test(matches: &ArgMatches, triple: Triple) -> io::Result<i32> {
let mut writer = std::io::stdout();
let (failed, passed) = roc_repl_expect::run::run_toplevel_expects(
let (failed_count, passed_count) = roc_repl_expect::run::run_toplevel_expects(
&mut writer,
roc_reporting::report::RenderTarget::ColorTerminal,
arena,
@ -555,7 +556,7 @@ pub fn test(matches: &ArgMatches, triple: Triple) -> io::Result<i32> {
let total_time = start_time.elapsed();
if failed == 0 && passed == 0 {
if failed_count == 0 && passed_count == 0 {
// TODO print this in a more nicely formatted way!
println!("No expectations were found.");
@ -566,18 +567,20 @@ pub fn test(matches: &ArgMatches, triple: Triple) -> io::Result<i32> {
// running tests altogether!
Ok(2)
} else {
let failed_color = if failed == 0 {
32 // green
let failed_color = if failed_count == 0 {
ANSI_STYLE_CODES.green
} else {
31 // red
ANSI_STYLE_CODES.red
};
let passed_color = ANSI_STYLE_CODES.green;
println!(
"\n\x1B[{failed_color}m{failed}\x1B[39m failed and \x1B[32m{passed}\x1B[39m passed in {} ms.\n",
"\n{failed_color}{failed_count}\x1B[39m failed and {passed_color}{passed_count}\x1B[39m passed in {} ms.\n",
total_time.as_millis(),
);
Ok((failed > 0) as i32)
Ok((failed_count > 0) as i32)
}
}

View file

@ -210,33 +210,7 @@ fn main() -> io::Result<()> {
threading,
) {
Ok((problems, total_time)) => {
println!(
"\x1B[{}m{}\x1B[39m {} and \x1B[{}m{}\x1B[39m {} found in {} ms.",
if problems.errors == 0 {
32 // green
} else {
33 // yellow
},
problems.errors,
if problems.errors == 1 {
"error"
} else {
"errors"
},
if problems.warnings == 0 {
32 // green
} else {
33 // yellow
},
problems.warnings,
if problems.warnings == 1 {
"warning"
} else {
"warnings"
},
total_time.as_millis(),
);
problems.print_to_stdout(total_time);
Ok(problems.exit_code())
}

View file

@ -11,12 +11,13 @@ extern crate roc_module;
mod cli_run {
use cli_utils::helpers::{
extract_valgrind_errors, file_path_from_root, fixture_file, fixtures_dir, has_error,
known_bad_file, run_cmd, run_roc, run_with_valgrind, strip_colors, Out, ValgrindError,
known_bad_file, run_cmd, run_roc, run_with_valgrind, Out, ValgrindError,
ValgrindErrorXWhat,
};
use const_format::concatcp;
use indoc::indoc;
use roc_cli::{CMD_BUILD, CMD_CHECK, CMD_DEV, CMD_FORMAT, CMD_RUN, CMD_TEST};
use roc_reporting::report::strip_colors;
use roc_test_utils::assert_multiline_str_eq;
use serial_test::serial;
use std::iter;

View file

@ -98,22 +98,6 @@ pub fn path_to_binary(binary_name: &str) -> PathBuf {
path
}
pub fn strip_colors(str: &str) -> String {
use roc_reporting::report::ANSI_STYLE_CODES;
str.replace(ANSI_STYLE_CODES.red, "")
.replace(ANSI_STYLE_CODES.green, "")
.replace(ANSI_STYLE_CODES.yellow, "")
.replace(ANSI_STYLE_CODES.blue, "")
.replace(ANSI_STYLE_CODES.magenta, "")
.replace(ANSI_STYLE_CODES.cyan, "")
.replace(ANSI_STYLE_CODES.white, "")
.replace(ANSI_STYLE_CODES.bold, "")
.replace(ANSI_STYLE_CODES.underline, "")
.replace(ANSI_STYLE_CODES.reset, "")
.replace(ANSI_STYLE_CODES.color_reset, "")
}
pub fn run_roc_with_stdin<I, S>(args: I, stdin_vals: &[&str]) -> Out
where
I: IntoIterator<Item = S>,

View file

@ -462,11 +462,9 @@ mod test_reporting {
fn human_readable(str: &str) -> String {
str.replace(ANSI_STYLE_CODES.red, "<red>")
.replace(ANSI_STYLE_CODES.white, "<white>")
.replace(ANSI_STYLE_CODES.blue, "<blue>")
.replace(ANSI_STYLE_CODES.yellow, "<yellow>")
.replace(ANSI_STYLE_CODES.green, "<green>")
.replace(ANSI_STYLE_CODES.cyan, "<cyan>")
.replace(ANSI_STYLE_CODES.magenta, "<magenta>")
.replace(ANSI_STYLE_CODES.reset, "<reset>")
.replace(ANSI_STYLE_CODES.bold, "<bold>")
.replace(ANSI_STYLE_CODES.underline, "<underline>")
@ -759,7 +757,7 @@ mod test_reporting {
&DEFAULT_PALETTE,
);
assert_eq!(human_readable(&buf), "<blue>activityIndicatorLarge<reset>");
assert_eq!(human_readable(&buf), "<cyan>activityIndicatorLarge<reset>");
}
#[test]

View file

@ -26,9 +26,9 @@ use roc_module::symbol::{Interns, ModuleId};
use roc_packaging::cache::RocCacheDir;
use roc_problem::can::Problem;
use roc_region::all::LineInfo;
use roc_reporting::report::RenderTarget;
use roc_reporting::report::RocDocAllocator;
use roc_reporting::report::{can_problem, DEFAULT_PALETTE};
use roc_reporting::report::{strip_colors, RenderTarget};
use roc_solve::FunctionKind;
use roc_target::TargetInfo;
use roc_types::pretty_print::name_and_print_var;
@ -1218,11 +1218,9 @@ fn non_roc_file_extension() {
I expected a file with extension `.roc` or without extension.
Instead I received a file with extension `.md`."
);
let color_start = String::from_utf8(vec![27, 91, 51, 54, 109]).unwrap();
let color_end = String::from_utf8(vec![27, 91, 48, 109]).unwrap();
let err = multiple_modules("non_roc_file_extension", modules).unwrap_err();
let err = err.replace(&color_start, "");
let err = err.replace(&color_end, "");
let err = strip_colors(&multiple_modules("non_roc_file_extension", modules).unwrap_err());
assert_eq!(err, expected, "\n{}", err);
}
@ -1255,10 +1253,8 @@ fn roc_file_no_extension() {
The provided file did not start with a shebang `#!` containing the
string `roc`. Is tmp/roc_file_no_extension/main a Roc file?"
);
let color_start = String::from_utf8(vec![27, 91, 51, 54, 109]).unwrap();
let color_end = String::from_utf8(vec![27, 91, 48, 109]).unwrap();
let err = multiple_modules("roc_file_no_extension", modules).unwrap_err();
let err = err.replace(&color_start, "");
let err = err.replace(&color_end, "");
let err = strip_colors(&multiple_modules("roc_file_no_extension", modules).unwrap_err());
assert_eq!(err, expected, "\n{}", err);
}

View file

@ -6,7 +6,7 @@ use const_format::concatcp;
use roc_load::MonomorphizedModule;
use roc_mono::ir::OptLevel;
use roc_repl_eval::gen::Problems;
use roc_repl_ui::colors::{BLUE, END_COL, PINK};
use roc_repl_ui::colors::{CYAN, END_COL};
use roc_repl_ui::repl_state::{ReplAction, ReplState};
use roc_repl_ui::{format_output, is_incomplete, CONT_PROMPT, PROMPT, SHORT_INSTRUCTIONS, TIPS};
use roc_reporting::report::{ANSI_STYLE_CODES, DEFAULT_PALETTE};
@ -21,11 +21,8 @@ use crate::cli_gen::eval_llvm;
pub const WELCOME_MESSAGE: &str = concatcp!(
"\n The rockin' ",
BLUE,
"roc repl",
END_COL,
"\n",
PINK,
CYAN,
"roc repl\n",
"────────────────────────",
END_COL,
"\n\n"

View file

@ -23,6 +23,7 @@ bumpalo.workspace = true
indoc.workspace = true
strip-ansi-escapes.workspace = true
target-lexicon.workspace = true
regex.workspace = true
rustyline.workspace = true
[features]

View file

@ -1,4 +1,5 @@
use bumpalo::Bump;
use regex::Regex;
use roc_wasm_interp::{
wasi, DefaultImportDispatcher, ImportDispatcher, Instance, Value, WasiDispatcher,
};
@ -158,11 +159,11 @@ pub fn expect_failure(input: &'static str, expected: &str) {
pub fn expect(input: &'static str, expected: &str) {
let raw_output = run(input);
// We need to get rid of HTML tags, and we can be quite specific about it!
// If we ever write more complex test cases, we might need regex here.
let without_html = raw_output.replace("<span class='color-magenta'> : </span>", " : ");
// remove color HTML tags
let regx = Regex::new("<span class='color-(.*?)'> : </span>").unwrap();
let without_html = regx.replace_all(&raw_output, " : ");
let clean_output = without_html.trim();
let trimmed_output = without_html.trim();
assert_eq!(clean_output, expected);
assert_eq!(trimmed_output, expected);
}

View file

@ -6,7 +6,6 @@ const STYLE_CODES: StyleCodes = if cfg!(target_family = "wasm") {
ANSI_STYLE_CODES
};
pub const BLUE: &str = STYLE_CODES.blue;
pub const PINK: &str = STYLE_CODES.magenta;
pub const GREEN: &str = STYLE_CODES.green;
pub const CYAN: &str = STYLE_CODES.cyan;
pub const END_COL: &str = STYLE_CODES.reset;

View file

@ -4,19 +4,17 @@ pub mod colors;
pub mod repl_state;
use bumpalo::Bump;
use colors::{BLUE, END_COL, PINK};
use colors::{CYAN, END_COL, GREEN};
use const_format::concatcp;
use repl_state::{parse_src, ParseOutcome};
use roc_parse::ast::{Expr, ValueDef};
use roc_repl_eval::gen::{Problems, ReplOutput};
use roc_reporting::report::StyleCodes;
use crate::colors::GREEN;
// TODO add link to repl tutorial (does not yet exist).
pub const TIPS: &str = concatcp!(
"\nEnter an expression to evaluate, or a definition (like ",
BLUE,
CYAN,
"x = 1",
END_COL,
") to use later.\n\n",
@ -25,25 +23,25 @@ pub const TIPS: &str = concatcp!(
} else {
// We use ctrl-v + ctrl-j for newlines because on Unix, terminals cannot distinguish between Shift-Enter and Enter
concatcp!(
BLUE,
CYAN,
" - ",
END_COL,
PINK,
GREEN,
"ctrl-v",
END_COL,
" + ",
PINK,
GREEN,
"ctrl-j",
END_COL,
" makes a newline\n",
BLUE,
CYAN,
" - ",
END_COL,
GREEN,
":q",
END_COL,
" quits\n",
BLUE,
CYAN,
" - ",
END_COL,
GREEN,
@ -57,8 +55,8 @@ pub const TIPS: &str = concatcp!(
// For when nothing is entered in the repl
// TODO add link to repl tutorial(does not yet exist).
pub const SHORT_INSTRUCTIONS: &str = "Enter an expression, or :help, or :q to quit.\n\n";
pub const PROMPT: &str = concatcp!(BLUE, "»", END_COL, " ");
pub const CONT_PROMPT: &str = concatcp!(BLUE, "", END_COL, " ");
pub const PROMPT: &str = concatcp!(CYAN, "»", END_COL, " ");
pub const CONT_PROMPT: &str = concatcp!(CYAN, "", END_COL, " ");
pub fn is_incomplete(input: &str) -> bool {
let arena = Bump::new();
@ -116,7 +114,7 @@ pub fn format_output(
{
buf.push('\n');
buf.push_str(&expr);
buf.push_str(style_codes.magenta); // Color for the type separator
buf.push_str(style_codes.green); // Color for the type separator
buf.push_str(EXPR_TYPE_SEPARATOR);
buf.push_str(style_codes.reset);
buf.push_str(&expr_type);

View file

@ -6,6 +6,8 @@ use roc_problem::can::Problem;
use roc_region::all::LineInfo;
use roc_solve_problem::TypeError;
use crate::report::ANSI_STYLE_CODES;
#[derive(Copy, Clone, Debug, Default, PartialEq, Eq)]
pub struct Problems {
pub fatally_errored: bool,
@ -26,11 +28,11 @@ impl Problems {
}
pub fn print_to_stdout(&self, total_time: std::time::Duration) {
const GREEN: usize = 32;
const YELLOW: usize = 33;
const GREEN: &str = ANSI_STYLE_CODES.green;
const YELLOW: &str = ANSI_STYLE_CODES.yellow;
print!(
"\x1B[{}m{}\x1B[39m {} and \x1B[{}m{}\x1B[39m {} found in {} ms",
"{}{}\x1B[39m {} and {}{}\x1B[39m {} found in {} ms",
match self.errors {
0 => GREEN,
_ => YELLOW,
@ -54,6 +56,39 @@ impl Problems {
}
}
// prints e.g. `1 error and 0 warnings found in 63 ms.`
pub fn print_error_warning_count(
error_count: usize,
warning_count: usize,
total_time: std::time::Duration,
) {
const GREEN: &str = ANSI_STYLE_CODES.green;
const YELLOW: &str = ANSI_STYLE_CODES.yellow;
print!(
"{}{}\x1B[39m {} and {}{}\x1B[39m {} found in {} ms",
match error_count {
0 => GREEN,
_ => YELLOW,
},
error_count,
match error_count {
1 => "error",
_ => "errors",
},
match warning_count {
0 => GREEN,
_ => YELLOW,
},
warning_count,
match warning_count {
1 => "warning",
_ => "warnings",
},
total_time.as_millis()
);
}
pub fn report_problems(
sources: &MutMap<ModuleId, (PathBuf, Box<str>)>,
interns: &Interns,

View file

@ -219,7 +219,7 @@ const fn default_palette_from_style_codes(codes: StyleCodes) -> Palette {
code_block: codes.white,
keyword: codes.green,
ellipsis: codes.green,
variable: codes.blue,
variable: codes.cyan,
type_variable: codes.yellow,
structure: codes.green,
alias: codes.yellow,
@ -249,8 +249,6 @@ pub struct StyleCodes {
pub red: &'static str,
pub green: &'static str,
pub yellow: &'static str,
pub blue: &'static str,
pub magenta: &'static str,
pub cyan: &'static str,
pub white: &'static str,
pub bold: &'static str,
@ -260,12 +258,10 @@ pub struct StyleCodes {
}
pub const ANSI_STYLE_CODES: StyleCodes = StyleCodes {
red: "\u{001b}[31m",
green: "\u{001b}[32m",
yellow: "\u{001b}[33m",
blue: "\u{001b}[34m",
magenta: "\u{001b}[35m",
cyan: "\u{001b}[36m",
red: "\u{001b}[1;31m",
green: "\u{001b}[1;32m",
yellow: "\u{001b}[1;33m",
cyan: "\u{001b}[1;36m",
white: "\u{001b}[37m",
bold: "\u{001b}[1m",
underline: "\u{001b}[4m",
@ -283,8 +279,6 @@ pub const HTML_STYLE_CODES: StyleCodes = StyleCodes {
red: html_color!("red"),
green: html_color!("green"),
yellow: html_color!("yellow"),
blue: html_color!("blue"),
magenta: html_color!("magenta"),
cyan: html_color!("cyan"),
white: html_color!("white"),
bold: "<span class='bold'>",
@ -293,6 +287,19 @@ pub const HTML_STYLE_CODES: StyleCodes = StyleCodes {
color_reset: "</span>",
};
// useful for tests
pub fn strip_colors(str: &str) -> String {
str.replace(ANSI_STYLE_CODES.red, "")
.replace(ANSI_STYLE_CODES.green, "")
.replace(ANSI_STYLE_CODES.yellow, "")
.replace(ANSI_STYLE_CODES.cyan, "")
.replace(ANSI_STYLE_CODES.white, "")
.replace(ANSI_STYLE_CODES.bold, "")
.replace(ANSI_STYLE_CODES.underline, "")
.replace(ANSI_STYLE_CODES.reset, "")
.replace(ANSI_STYLE_CODES.color_reset, "")
}
// define custom allocator struct so we can `impl RocDocAllocator` custom helpers
pub struct RocDocAllocator<'a> {
upstream: BoxAllocator,