From 0214569f3a6d1284c42bc83c5fc3d79fd3e7fa1b Mon Sep 17 00:00:00 2001 From: Laurenz Date: Mon, 22 May 2023 15:15:38 +0200 Subject: [PATCH] Set exit code for CLI errors Fixes #1241 --- cli/src/main.rs | 23 ++++++++++++++++------- 1 file changed, 16 insertions(+), 7 deletions(-) diff --git a/cli/src/main.rs b/cli/src/main.rs index eb11cfc67..df5c5c82c 100644 --- a/cli/src/main.rs +++ b/cli/src/main.rs @@ -1,12 +1,13 @@ mod args; mod trace; -use std::cell::{RefCell, RefMut}; +use std::cell::{Cell, RefCell, RefMut}; use std::collections::HashMap; use std::fs::{self, File}; use std::hash::Hash; use std::io::{self, Write}; use std::path::{Path, PathBuf}; +use std::process::ExitCode; use atty::Stream; use clap::Parser; @@ -33,8 +34,12 @@ use crate::args::{CliArguments, Command, CompileCommand}; type CodespanResult = Result; type CodespanError = codespan_reporting::files::Error; +thread_local! { + static EXIT: Cell = Cell::new(ExitCode::SUCCESS); +} + /// Entry point. -fn main() { +fn main() -> ExitCode { let arguments = CliArguments::parse(); let _guard = match crate::trace::init_tracing(&arguments) { Ok(guard) => guard, @@ -52,8 +57,16 @@ fn main() { }; if let Err(msg) = res { + set_failed(); print_error(&msg).expect("failed to print error"); } + + EXIT.with(|cell| cell.get()) +} + +/// Ensure a failure exit code. +fn set_failed() { + EXIT.with(|cell| cell.set(ExitCode::FAILURE)); } /// Print an application-level error (independent from a source file). @@ -183,11 +196,6 @@ fn compile(mut command: CompileSettings) -> StrResult<()> { } if !command.watch { - // Return with non-zero exit code in case of error. - if !ok { - std::process::exit(1); - } - return Ok(()); } @@ -262,6 +270,7 @@ fn compile_once(world: &mut SystemWorld, command: &CompileSettings) -> StrResult // Print diagnostics. Err(errors) => { + set_failed(); status(command, Status::Error).unwrap(); print_diagnostics(world, *errors) .map_err(|_| "failed to print diagnostics")?;