1
0
mirror of https://github.com/mgechev/revive.git synced 2024-11-30 08:57:07 +02:00
revive/rule/error-return.go
Dian 44eed7edb7 fix error return rule to allow multiple error return values (#110)
* fix error return rule to allow multiple error return values

please check golint related updates here: golang/lint@8379672

When returning multiple values with an error,
lint checks if the error is the last return value.
But the implementation actually is checking for all return values
except for the last one, and throw the alert if it found an error.

There is a (edge) case where some function returning more than one error
is getting a false positive even when the last return value is an error.

This patch adds an early check, to see if the last return value is an error
and if so, it will pass silently.

* Fix return error

* add test changes
2019-03-20 11:54:27 -07:00

68 lines
1.4 KiB
Go

package rule
import (
"go/ast"
"github.com/mgechev/revive/lint"
)
// ErrorReturnRule lints given else constructs.
type ErrorReturnRule struct{}
// Apply applies the rule to given file.
func (r *ErrorReturnRule) Apply(file *lint.File, _ lint.Arguments) []lint.Failure {
var failures []lint.Failure
fileAst := file.AST
walker := lintErrorReturn{
file: file,
fileAst: fileAst,
onFailure: func(failure lint.Failure) {
failures = append(failures, failure)
},
}
ast.Walk(walker, fileAst)
return failures
}
// Name returns the rule name.
func (r *ErrorReturnRule) Name() string {
return "error-return"
}
type lintErrorReturn struct {
file *lint.File
fileAst *ast.File
onFailure func(lint.Failure)
}
func (w lintErrorReturn) Visit(n ast.Node) ast.Visitor {
fn, ok := n.(*ast.FuncDecl)
if !ok || fn.Type.Results == nil {
return w
}
ret := fn.Type.Results.List
if len(ret) <= 1 {
return w
}
if isIdent(ret[len(ret)-1].Type, "error") {
return nil
}
// An error return parameter should be the last parameter.
// Flag any error parameters found before the last.
for _, r := range ret[:len(ret)-1] {
if isIdent(r.Type, "error") {
w.onFailure(lint.Failure{
Category: "arg-order",
Confidence: 0.9,
Node: fn,
Failure: "error should be the last type when returning multiple items",
})
break // only flag one
}
}
return w
}