Skip to content

Commit

Permalink
cli: Better filenames in errors
Browse files Browse the repository at this point in the history
  • Loading branch information
wader committed Sep 12, 2021
1 parent 394e2b3 commit 0dd848d
Show file tree
Hide file tree
Showing 8 changed files with 44 additions and 31 deletions.
12 changes: 10 additions & 2 deletions pkg/interp/funcs.go
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ func (i *Interp) makeFunctions(registry *registry.Registry) []Function {
{[]string{"tty"}, 0, 0, i.tty, nil},

{[]string{"readline"}, 0, 2, i.readline, nil},
{[]string{"eval"}, 1, 1, nil, i.eval},
{[]string{"eval"}, 1, 2, nil, i.eval},
{[]string{"stdout"}, 0, 0, nil, i.stdout},
{[]string{"stderr"}, 0, 0, nil, i.stderr},

Expand Down Expand Up @@ -246,12 +246,20 @@ func (i *Interp) readline(c interface{}, a []interface{}) interface{} {
}

func (i *Interp) eval(c interface{}, a []interface{}) gojq.Iter {
var err error
src, err := toString(a[0])
if err != nil {
return gojq.NewIter(fmt.Errorf("src: %w", err))
}
var filenameHint string
if len(a) >= 2 {
filenameHint, err = toString(a[1])
if err != nil {
return gojq.NewIter(fmt.Errorf("filename hint: %w", err))
}
}

iter, err := i.Eval(i.evalContext.ctx, ScriptMode, c, src, i.evalContext.stdout)
iter, err := i.Eval(i.evalContext.ctx, ScriptMode, c, src, filenameHint, i.evalContext.stdout)
if err != nil {
return gojq.NewIter(err)
}
Expand Down
29 changes: 16 additions & 13 deletions pkg/interp/interp.go
Original file line number Diff line number Diff line change
Expand Up @@ -54,10 +54,11 @@ type compileError struct {

func (ce compileError) Value() interface{} {
return map[string]interface{}{
"error": ce.err.Error(),
"what": ce.what,
"line": ce.pos.Line,
"column": ce.pos.Column,
"error": ce.err.Error(),
"what": ce.what,
"filename": ce.filename,
"line": ce.pos.Line,
"column": ce.pos.Column,
}
}
func (ee compileError) Error() string {
Expand Down Expand Up @@ -540,7 +541,7 @@ func (i *Interp) Main(ctx context.Context, stdout io.Writer, version string) err
return nil
}

func (i *Interp) Eval(ctx context.Context, mode RunMode, c interface{}, src string, stdout Output) (gojq.Iter, error) {
func (i *Interp) Eval(ctx context.Context, mode RunMode, c interface{}, src string, filename string, stdout Output) (gojq.Iter, error) {
var err error
// TODO: did not work
// nq := &(*q)
Expand All @@ -549,9 +550,10 @@ func (i *Interp) Eval(ctx context.Context, mode RunMode, c interface{}, src stri
if err != nil {
p := queryErrorPosition(err)
return nil, compileError{
err: err,
what: "parse",
pos: p,
err: err,
what: "parse",
filename: filename,
pos: p,
}
}

Expand Down Expand Up @@ -692,7 +694,7 @@ func (i *Interp) Eval(ctx context.Context, mode RunMode, c interface{}, src stri
return nil, compileError{
err: err,
what: "parse",
filename: filename,
filename: filenamePart,
pos: p,
}
}
Expand All @@ -712,9 +714,10 @@ func (i *Interp) Eval(ctx context.Context, mode RunMode, c interface{}, src stri
if err != nil {
p := queryErrorPosition(err)
return nil, compileError{
err: err,
what: "compile",
pos: p,
err: err,
what: "compile",
filename: filename,
pos: p,
}
}

Expand Down Expand Up @@ -752,7 +755,7 @@ func (i *Interp) EvalFunc(ctx context.Context, mode RunMode, c interface{}, name
/// _args to mark variable as internal and hide it from completion
// {input: ..., args: [...]} | .args as {args: $_args} | .input | name[($_args[0]; ...)]
trampolineExpr := fmt.Sprintf(". as {args: $_args} | .input | %s%s", name, argExpr)
iter, err := i.Eval(ctx, mode, trampolineInput, trampolineExpr, stdout)
iter, err := i.Eval(ctx, mode, trampolineInput, trampolineExpr, "", stdout)
if err != nil {
return nil, err
}
Expand Down
18 changes: 10 additions & 8 deletions pkg/interp/interp.jq
Original file line number Diff line number Diff line change
Expand Up @@ -169,9 +169,9 @@ def _eval_is_compile_error: type == "object" and .error != null and .what != nul
def _eval_compile_error_tostring:
"\(.filename // "src"):\(.line):\(.column): \(.error)";

def _eval($e; f; on_error; on_compile_error):
def _eval($e; $filename; f; on_error; on_compile_error):
( _default_options(_build_default_options) as $_
| try eval($e) | f
| try eval($e; $filename) | f
catch
if _eval_is_compile_error then on_compile_error
else on_error
Expand All @@ -184,7 +184,7 @@ def _repl_on_error:
| (_error_str | println)
);
def _repl_on_compile_error: _repl_on_error;
def _repl_eval($e): _eval($e; _repl_display; _repl_on_error; _repl_on_compile_error);
def _repl_eval($e): _eval($e; "repl"; _repl_display; _repl_on_error; _repl_on_compile_error);

# run read-eval-print-loop
def repl($opts; iter): #:: a|(Opts) => @
Expand Down Expand Up @@ -231,8 +231,8 @@ def _cli_expr_on_compile_error:
| halt_error(_exit_code_compile_error)
);
# _cli_expr_eval halts on compile errors
def _cli_expr_eval($e; f): _eval($e; f; _cli_expr_on_error; _cli_expr_on_compile_error);
def _cli_expr_eval($e): _eval($e; .; _cli_expr_on_error; _cli_expr_on_compile_error);
def _cli_expr_eval($e; $filename; f): _eval($e; $filename; f; _cli_expr_on_error; _cli_expr_on_compile_error);
def _cli_expr_eval($e; $filename): _eval($e; $filename; .; _cli_expr_on_error; _cli_expr_on_compile_error);

# next valid input
def input:
Expand Down Expand Up @@ -450,10 +450,12 @@ def _main:
( { null_input: ($parsed_args.null_input == true) }
| if $parsed_args.file then
( .expr = ($parsed_args.file | open | string)
| .expr_filename = $parsed_args.file
| .filenames = $rest
)
else
( .expr = ($rest[0] // ".")
| .expr_filename = "arg"
| .filenames = $rest[1:]
)
end
Expand All @@ -462,7 +464,7 @@ def _main:
elif .filenames == [] then
.filenames = ["-"]
end
| . as {$expr, $filenames, $null_input}
| . as {$expr, $expr_filename, $filenames, $null_input}
| _include_paths([
$parsed_args.include_path // empty
]) as $_
Expand All @@ -472,10 +474,10 @@ def _main:
else inputs
end
# will iterate zero or more inputs
| if $parsed_args.repl then [_cli_expr_eval($expr)] | repl({}; .[])
| if $parsed_args.repl then [_cli_expr_eval($expr; $expr_filename)] | repl({}; .[])
else
( _cli_last_expr_error(null) as $_
| _cli_expr_eval($expr; _repl_display)
| _cli_expr_eval($expr; $expr_filename; _repl_display)
)
end
)
Expand Down
4 changes: 2 additions & 2 deletions pkg/interp/testdata/exitcode.fqtest
Original file line number Diff line number Diff line change
Expand Up @@ -15,11 +15,11 @@ exitcode: 123
$ fq -n invalid
exitcode: 3
stderr:
error: src:1:0: function not defined: invalid/0
error: arg:1:0: function not defined: invalid/0
$ fq -n "("
exitcode: 3
stderr:
error: src:1:2: unexpected token <EOF>
error: arg:1:2: unexpected token <EOF>
$ fq . non-existing
exitcode: 2
stderr:
Expand Down
2 changes: 1 addition & 1 deletion pkg/interp/testdata/incudepath.fqtest
Original file line number Diff line number Diff line change
Expand Up @@ -5,4 +5,4 @@ $ fq -L /library -n 'include "a"; a'
$ fq -L /wrong -n 'include "a"; a'
exitcode: 3
stderr:
error: src:1:0: open a.jq: file does not exist
error: arg:1:0: open a.jq: file does not exist
4 changes: 2 additions & 2 deletions pkg/interp/testdata/inputs.fqtest
Original file line number Diff line number Diff line change
Expand Up @@ -54,11 +54,11 @@ error: /non-existing: file not found
$ fq -d raw '(' /a /b /c
exitcode: 3
stderr:
error: src:1:2: unexpected token <EOF>
error: arg:1:2: unexpected token <EOF>
$ fq -d raw bla /a /b /c
exitcode: 3
stderr:
error: src:1:0: function not defined: bla/0
error: arg:1:0: function not defined: bla/0
$ fq -d raw '1+"a"' /a /b /c
exitcode: 5
stderr:
Expand Down
4 changes: 2 additions & 2 deletions pkg/interp/testdata/repl.fqtest
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,9 @@ $ fq -i
null> 1+1
2
null> (
error: src:1:2: unexpected token <EOF>
error: repl:1:2: unexpected token <EOF>
null> abc
error: src:1:0: function not defined: abc/0
error: repl:1:0: function not defined: abc/0
null> 1+"a"
error: cannot add: number (1) and string ("a")
null> 1 | repl
Expand Down
2 changes: 1 addition & 1 deletion pkg/interp/testdata/var.fqtest
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ null> $a
"aa"
null> var("a"; empty)
null> $a
error: src:1:0: variable not defined: $a
error: repl:1:0: variable not defined: $a
null> var
{
"bb": "bb"
Expand Down

0 comments on commit 0dd848d

Please sign in to comment.