mirror of
https://github.com/NixOS/nix.git
synced 2025-11-08 19:46:02 +01:00
libexpr: improve error messages for builtins.genericClosure
Show which element(s) are involved at each error point: - When an element is missing the "key" attribute, show the element - When an element is not an attribute set, show the element - When comparing keys fails, show both elements being compared - When calling operator fails, show which element was being processed This provides concrete context using ValuePrinter with errorPrintOptions. Note: errorPrintOptions uses maxDepth=10 by default, which may print quite deeply nested structures in error messages. This could potentially be overwhelming, but follows the existing default for error contexts.
This commit is contained in:
parent
ca787bc3e0
commit
d262efc240
10 changed files with 188 additions and 46 deletions
|
|
@ -165,35 +165,48 @@ TEST_F(ErrorTraceTest, genericClosure)
|
|||
HintFmt("expected a function but found %s: %s", "a Boolean", Uncolored(ANSI_CYAN "true" ANSI_NORMAL)),
|
||||
HintFmt("while evaluating the 'operator' attribute passed as argument to builtins.genericClosure"));
|
||||
|
||||
ASSERT_TRACE2(
|
||||
ASSERT_TRACE3(
|
||||
"genericClosure { startSet = [{ key = 1;}]; operator = item: true; }",
|
||||
TypeError,
|
||||
HintFmt("expected a list but found %s: %s", "a Boolean", Uncolored(ANSI_CYAN "true" ANSI_NORMAL)),
|
||||
HintFmt("while evaluating the return value of the `operator` passed to builtins.genericClosure"));
|
||||
HintFmt("while evaluating the return value of the `operator` passed to builtins.genericClosure"),
|
||||
HintFmt(
|
||||
"while calling %s on genericClosure element %s",
|
||||
"operator",
|
||||
Uncolored("{ key = " ANSI_CYAN "1" ANSI_NORMAL "; }")));
|
||||
|
||||
ASSERT_TRACE2(
|
||||
ASSERT_TRACE3(
|
||||
"genericClosure { startSet = [{ key = 1;}]; operator = item: [ true ]; }",
|
||||
TypeError,
|
||||
HintFmt("expected a set but found %s: %s", "a Boolean", Uncolored(ANSI_CYAN "true" ANSI_NORMAL)),
|
||||
HintFmt("while evaluating one of the elements generated by (or initially passed to) builtins.genericClosure"));
|
||||
HintFmt(""),
|
||||
HintFmt("in genericClosure element %s", Uncolored(ANSI_CYAN "true" ANSI_NORMAL)));
|
||||
|
||||
ASSERT_TRACE2(
|
||||
ASSERT_TRACE3(
|
||||
"genericClosure { startSet = [{ key = 1;}]; operator = item: [ {} ]; }",
|
||||
TypeError,
|
||||
HintFmt("attribute '%s' missing", "key"),
|
||||
HintFmt("in one of the attrsets generated by (or initially passed to) builtins.genericClosure"));
|
||||
HintFmt(""),
|
||||
HintFmt("in genericClosure element %s", Uncolored("{ }")));
|
||||
|
||||
ASSERT_TRACE2(
|
||||
ASSERT_TRACE3(
|
||||
"genericClosure { startSet = [{ key = 1;}]; operator = item: [{ key = ''a''; }]; }",
|
||||
EvalError,
|
||||
HintFmt("cannot compare %s with %s", "a string", "an integer"),
|
||||
HintFmt("while comparing the `key` attributes of two genericClosure elements"));
|
||||
HintFmt(
|
||||
"cannot compare %s with %s; values are %s and %s",
|
||||
"a string",
|
||||
"an integer",
|
||||
Uncolored(ANSI_MAGENTA "\"a\"" ANSI_NORMAL),
|
||||
Uncolored(ANSI_CYAN "1" ANSI_NORMAL)),
|
||||
HintFmt("with element %s", Uncolored("{ key = " ANSI_CYAN "1" ANSI_NORMAL "; }")),
|
||||
HintFmt("while comparing element %s", Uncolored("{ key = " ANSI_MAGENTA "\"a\"" ANSI_NORMAL "; }")));
|
||||
|
||||
ASSERT_TRACE2(
|
||||
ASSERT_TRACE3(
|
||||
"genericClosure { startSet = [ true ]; operator = item: [{ key = ''a''; }]; }",
|
||||
TypeError,
|
||||
HintFmt("expected a set but found %s: %s", "a Boolean", Uncolored(ANSI_CYAN "true" ANSI_NORMAL)),
|
||||
HintFmt("while evaluating one of the elements generated by (or initially passed to) builtins.genericClosure"));
|
||||
HintFmt(""),
|
||||
HintFmt("in genericClosure element %s", Uncolored(ANSI_CYAN "true" ANSI_NORMAL)));
|
||||
}
|
||||
|
||||
TEST_F(ErrorTraceTest, replaceStrings)
|
||||
|
|
@ -1050,17 +1063,35 @@ TEST_F(ErrorTraceTest, bitXor)
|
|||
|
||||
TEST_F(ErrorTraceTest, lessThan)
|
||||
{
|
||||
ASSERT_TRACE1("lessThan 1 \"foo\"", EvalError, HintFmt("cannot compare %s with %s", "an integer", "a string"));
|
||||
ASSERT_TRACE1(
|
||||
"lessThan 1 \"foo\"",
|
||||
EvalError,
|
||||
HintFmt(
|
||||
"cannot compare %s with %s; values are %s and %s",
|
||||
"an integer",
|
||||
"a string",
|
||||
Uncolored(ANSI_CYAN "1" ANSI_NORMAL),
|
||||
Uncolored(ANSI_MAGENTA "\"foo\"" ANSI_NORMAL)));
|
||||
|
||||
ASSERT_TRACE1(
|
||||
"lessThan {} {}",
|
||||
EvalError,
|
||||
HintFmt("cannot compare %s with %s; values of that type are incomparable", "a set", "a set"));
|
||||
HintFmt(
|
||||
"cannot compare %s with %s; values of that type are incomparable (values are %s and %s)",
|
||||
"a set",
|
||||
"a set",
|
||||
Uncolored("{ }"),
|
||||
Uncolored("{ }")));
|
||||
|
||||
ASSERT_TRACE2(
|
||||
"lessThan [ 1 2 ] [ \"foo\" ]",
|
||||
EvalError,
|
||||
HintFmt("cannot compare %s with %s", "an integer", "a string"),
|
||||
HintFmt(
|
||||
"cannot compare %s with %s; values are %s and %s",
|
||||
"an integer",
|
||||
"a string",
|
||||
Uncolored(ANSI_CYAN "1" ANSI_NORMAL),
|
||||
Uncolored(ANSI_MAGENTA "\"foo\"" ANSI_NORMAL)),
|
||||
HintFmt("while comparing two list elements"));
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue