diff --git a/crates/nu-command/src/filters/each.rs b/crates/nu-command/src/filters/each.rs index f8162ddfdc..3bf75dd039 100644 --- a/crates/nu-command/src/filters/each.rs +++ b/crates/nu-command/src/filters/each.rs @@ -2,8 +2,8 @@ use nu_engine::{eval_block, CallExt}; use nu_protocol::ast::Call; use nu_protocol::engine::{CaptureBlock, Command, EngineState, Stack}; use nu_protocol::{ - Category, Example, IntoInterruptiblePipelineData, IntoPipelineData, PipelineData, Signature, - Span, SyntaxShape, Value, + Category, Example, IntoInterruptiblePipelineData, IntoPipelineData, PipelineData, ShellError, + Signature, Span, SyntaxShape, Value, }; #[derive(Clone)] @@ -161,6 +161,7 @@ impl Command for Each { } } + let input_span = x.span(); match eval_block( &engine_state, &mut stack, @@ -170,7 +171,10 @@ impl Command for Each { redirect_stderr, ) { Ok(v) => v.into_value(span), - Err(error) => Value::Error { error }, + Err(error) => { + let error = each_cmd_error(error, input_span); + Value::Error { error } + } } }) .into_pipeline_data(ctrlc)), @@ -212,6 +216,7 @@ impl Command for Each { } } + let input_span = x.span(); match eval_block( &engine_state, &mut stack, @@ -221,7 +226,10 @@ impl Command for Each { redirect_stderr, ) { Ok(v) => v.into_value(span), - Err(error) => Value::Error { error }, + Err(error) => { + let error = each_cmd_error(error, input_span); + Value::Error { error } + } } }) .into_pipeline_data(ctrlc)), @@ -252,6 +260,13 @@ impl Command for Each { } } +fn each_cmd_error(error_source: ShellError, input_span: Result) -> ShellError { + if let Ok(span) = input_span { + return ShellError::EvalBlockWithInput(span, vec![error_source]); + } + error_source +} + #[cfg(test)] mod test { use super::*; diff --git a/crates/nu-protocol/src/shell_error.rs b/crates/nu-protocol/src/shell_error.rs index cc3b4d6439..8e09ee76ee 100644 --- a/crates/nu-protocol/src/shell_error.rs +++ b/crates/nu-protocol/src/shell_error.rs @@ -765,6 +765,12 @@ Either make sure {0} is a string, or add a 'to_string' entry for it in ENV_CONVE #[error("Unexpected abbr component `{0}`.")] #[diagnostic(code(nu::shell::unexpected_path_abbreviateion), url(docsrs))] UnexpectedAbbrComponent(String), + + // It should be only used by commands accepts block, and accept inputs from pipeline. + /// Failed to eval block with specific pipeline input. + #[error("Eval block failed with pipeline input")] + #[diagnostic(code(nu::shell::eval_block_with_input), url(docsrs))] + EvalBlockWithInput(#[label("Invalid item")] Span, #[related] Vec), } impl From for ShellError {