Skip to content

Commit

Permalink
Check function literals during unused-param
Browse files Browse the repository at this point in the history
  • Loading branch information
StephenButtolph committed Jan 22, 2024
1 parent 64dda06 commit 682925b
Show file tree
Hide file tree
Showing 2 changed files with 56 additions and 34 deletions.
78 changes: 44 additions & 34 deletions rule/unused-param.go
Original file line number Diff line number Diff line change
Expand Up @@ -87,54 +87,64 @@ type lintUnusedParamRule struct {
}

func (w lintUnusedParamRule) Visit(node ast.Node) ast.Visitor {
var (
funcType *ast.FuncType
funcBody *ast.BlockStmt
)
switch n := node.(type) {
case *ast.FuncLit:
funcType = n.Type
funcBody = n.Body
case *ast.FuncDecl:
params := retrieveNamedParams(n.Type.Params)
if len(params) < 1 {
return nil // skip, func without parameters
}

if n.Body == nil {
return nil // skip, is a function prototype
return w // skip, is a function prototype
}

// inspect the func body looking for references to parameters
fselect := func(n ast.Node) bool {
ident, isAnID := n.(*ast.Ident)
funcType = n.Type
funcBody = n.Body
default:
return w // skip, not a function
}

if !isAnID {
return false
}
params := retrieveNamedParams(funcType.Params)
if len(params) < 1 {
return w // skip, func without parameters
}

_, isAParam := params[ident.Obj]
if isAParam {
params[ident.Obj] = false // mark as used
}
// inspect the func body looking for references to parameters
fselect := func(n ast.Node) bool {
ident, isAnID := n.(*ast.Ident)

if !isAnID {
return false
}
_ = pick(n.Body, fselect)

for _, p := range n.Type.Params.List {
for _, n := range p.Names {
if w.allowRegex.FindStringIndex(n.Name) != nil {
continue
}
if params[n.Obj] {
w.onFailure(lint.Failure{
Confidence: 1,
Node: n,
Category: "bad practice",
Failure: fmt.Sprintf(w.failureMsg, n.Name),
})
}
}

_, isAParam := params[ident.Obj]
if isAParam {
params[ident.Obj] = false // mark as used
}

return nil // full method body already inspected
return false
}
_ = pick(funcBody, fselect)

for _, p := range funcType.Params.List {
for _, n := range p.Names {
if w.allowRegex.FindStringIndex(n.Name) != nil {
continue
}
if params[n.Obj] {
w.onFailure(lint.Failure{
Confidence: 1,
Node: n,
Category: "bad practice",
Failure: fmt.Sprintf(w.failureMsg, n.Name),
})
}
}
}

return w
return w // full method body was inspected
}

func retrieveNamedParams(params *ast.FieldList) map[*ast.Object]bool {
Expand Down
12 changes: 12 additions & 0 deletions testdata/unused-param.go
Original file line number Diff line number Diff line change
Expand Up @@ -166,3 +166,15 @@ func encodeFixed64Rpc(dAtA []byte, offset int, v uint64, i int) int {

return 8
}

func innerAnonymousFunctionWithoutUsage() {
innerFunc := func(a int) {} // MATCH /parameter 'a' seems to be unused, consider removing or renaming it as _/
innerFunc(1)
}

func innerAnonymousFunctionWithUsage() {
innerFunc := func(a int) {
a += 1
}
innerFunc(1)
}

0 comments on commit 682925b

Please sign in to comment.