github.com/nozzle/golangci-lint@v1.49.0-nz3/pkg/golinters/gomodguard.go (about)

     1  package golinters
     2  
     3  import (
     4  	"sync"
     5  
     6  	"github.com/ryancurrah/gomodguard"
     7  	"golang.org/x/tools/go/analysis"
     8  
     9  	"github.com/golangci/golangci-lint/pkg/config"
    10  	"github.com/golangci/golangci-lint/pkg/golinters/goanalysis"
    11  	"github.com/golangci/golangci-lint/pkg/lint/linter"
    12  	"github.com/golangci/golangci-lint/pkg/result"
    13  )
    14  
    15  const (
    16  	gomodguardName = "gomodguard"
    17  	gomodguardDesc = "Allow and block list linter for direct Go module dependencies. " +
    18  		"This is different from depguard where there are different block " +
    19  		"types for example version constraints and module recommendations."
    20  )
    21  
    22  // NewGomodguard returns a new Gomodguard linter.
    23  func NewGomodguard(settings *config.GoModGuardSettings) *goanalysis.Linter {
    24  	var issues []goanalysis.Issue
    25  	var mu sync.Mutex
    26  
    27  	processorCfg := &gomodguard.Configuration{}
    28  	if settings != nil {
    29  		processorCfg.Allowed.Modules = settings.Allowed.Modules
    30  		processorCfg.Allowed.Domains = settings.Allowed.Domains
    31  		processorCfg.Blocked.LocalReplaceDirectives = settings.Blocked.LocalReplaceDirectives
    32  
    33  		for n := range settings.Blocked.Modules {
    34  			for k, v := range settings.Blocked.Modules[n] {
    35  				m := map[string]gomodguard.BlockedModule{k: {
    36  					Recommendations: v.Recommendations,
    37  					Reason:          v.Reason,
    38  				}}
    39  				processorCfg.Blocked.Modules = append(processorCfg.Blocked.Modules, m)
    40  				break
    41  			}
    42  		}
    43  
    44  		for n := range settings.Blocked.Versions {
    45  			for k, v := range settings.Blocked.Versions[n] {
    46  				m := map[string]gomodguard.BlockedVersion{k: {
    47  					Version: v.Version,
    48  					Reason:  v.Reason,
    49  				}}
    50  				processorCfg.Blocked.Versions = append(processorCfg.Blocked.Versions, m)
    51  				break
    52  			}
    53  		}
    54  	}
    55  
    56  	analyzer := &analysis.Analyzer{
    57  		Name: goanalysis.TheOnlyAnalyzerName,
    58  		Doc:  goanalysis.TheOnlyanalyzerDoc,
    59  		Run:  goanalysis.DummyRun,
    60  	}
    61  
    62  	return goanalysis.NewLinter(
    63  		gomodguardName,
    64  		gomodguardDesc,
    65  		[]*analysis.Analyzer{analyzer},
    66  		nil,
    67  	).WithContextSetter(func(lintCtx *linter.Context) {
    68  		processor, err := gomodguard.NewProcessor(processorCfg)
    69  		if err != nil {
    70  			lintCtx.Log.Warnf("running gomodguard failed: %s: if you are not using go modules "+
    71  				"it is suggested to disable this linter", err)
    72  			return
    73  		}
    74  
    75  		analyzer.Run = func(pass *analysis.Pass) (interface{}, error) {
    76  			gomodguardIssues := processor.ProcessFiles(getFileNames(pass))
    77  
    78  			mu.Lock()
    79  			defer mu.Unlock()
    80  
    81  			for _, gomodguardIssue := range gomodguardIssues {
    82  				issues = append(issues, goanalysis.NewIssue(&result.Issue{
    83  					FromLinter: gomodguardName,
    84  					Pos:        gomodguardIssue.Position,
    85  					Text:       gomodguardIssue.Reason,
    86  				}, pass))
    87  			}
    88  
    89  			return nil, nil
    90  		}
    91  	}).WithIssuesReporter(func(*linter.Context) []goanalysis.Issue {
    92  		return issues
    93  	}).WithLoadMode(goanalysis.LoadModeSyntax)
    94  }