github.com/chenfeining/golangci-lint@v1.0.2-0.20230730162517-14c6c67868df/pkg/golinters/funlen.go (about)

     1  package golinters
     2  
     3  import (
     4  	"go/token"
     5  	"strings"
     6  	"sync"
     7  
     8  	"github.com/ultraware/funlen"
     9  	"golang.org/x/tools/go/analysis"
    10  
    11  	"github.com/chenfeining/golangci-lint/pkg/config"
    12  	"github.com/chenfeining/golangci-lint/pkg/golinters/goanalysis"
    13  	"github.com/chenfeining/golangci-lint/pkg/lint/linter"
    14  	"github.com/chenfeining/golangci-lint/pkg/result"
    15  )
    16  
    17  const funlenName = "funlen"
    18  
    19  //nolint:dupl
    20  func NewFunlen(settings *config.FunlenSettings) *goanalysis.Linter {
    21  	var mu sync.Mutex
    22  	var resIssues []goanalysis.Issue
    23  
    24  	analyzer := &analysis.Analyzer{
    25  		Name: funlenName,
    26  		Doc:  goanalysis.TheOnlyanalyzerDoc,
    27  		Run: func(pass *analysis.Pass) (any, error) {
    28  			issues := runFunlen(pass, settings)
    29  
    30  			if len(issues) == 0 {
    31  				return nil, nil
    32  			}
    33  
    34  			mu.Lock()
    35  			resIssues = append(resIssues, issues...)
    36  			mu.Unlock()
    37  
    38  			return nil, nil
    39  		},
    40  	}
    41  
    42  	return goanalysis.NewLinter(
    43  		funlenName,
    44  		"Tool for detection of long functions",
    45  		[]*analysis.Analyzer{analyzer},
    46  		nil,
    47  	).WithIssuesReporter(func(*linter.Context) []goanalysis.Issue {
    48  		return resIssues
    49  	}).WithLoadMode(goanalysis.LoadModeSyntax)
    50  }
    51  
    52  func runFunlen(pass *analysis.Pass, settings *config.FunlenSettings) []goanalysis.Issue {
    53  	var lintIssues []funlen.Message
    54  	for _, file := range pass.Files {
    55  		fileIssues := funlen.Run(file, pass.Fset, settings.Lines, settings.Statements)
    56  		lintIssues = append(lintIssues, fileIssues...)
    57  	}
    58  
    59  	if len(lintIssues) == 0 {
    60  		return nil
    61  	}
    62  
    63  	issues := make([]goanalysis.Issue, len(lintIssues))
    64  	for k, i := range lintIssues {
    65  		issues[k] = goanalysis.NewIssue(&result.Issue{
    66  			Pos: token.Position{
    67  				Filename: i.Pos.Filename,
    68  				Line:     i.Pos.Line,
    69  			},
    70  			Text:       strings.TrimRight(i.Message, "\n"),
    71  			FromLinter: funlenName,
    72  		}, pass)
    73  	}
    74  
    75  	return issues
    76  }