diff options
| author | Xe Iaso <me@xeiaso.net> | 2023-06-24 07:05:36 -0400 |
|---|---|---|
| committer | Xe Iaso <me@xeiaso.net> | 2023-06-24 07:05:36 -0400 |
| commit | 0381ae5a1970d69712d698c48da50f95294deb37 (patch) | |
| tree | e12cf1967ffb0f6ab32ddcf56f5c1e96ce2b6a1c /linters/documentfunctions/documentfunctions.go | |
| parent | d2707e0d8dbf6ef5e8bce57e7a9f42899c829475 (diff) | |
| download | x-0381ae5a1970d69712d698c48da50f95294deb37.tar.xz x-0381ae5a1970d69712d698c48da50f95294deb37.zip | |
linters: introduce a few linters for catching pathological behavior
Signed-off-by: Xe Iaso <me@xeiaso.net>
Diffstat (limited to 'linters/documentfunctions/documentfunctions.go')
| -rw-r--r-- | linters/documentfunctions/documentfunctions.go | 61 |
1 files changed, 61 insertions, 0 deletions
diff --git a/linters/documentfunctions/documentfunctions.go b/linters/documentfunctions/documentfunctions.go new file mode 100644 index 0000000..0d05410 --- /dev/null +++ b/linters/documentfunctions/documentfunctions.go @@ -0,0 +1,61 @@ +// Package documentfunctions implements a linter that forces you to document functions. +// +// When you are dealing with code that requires multiple people to collaborate, your +// code is not going to be "immediately obvious based on the implementation". You need +// to document all functions that you make. This can help find untested invariants that +// can lead to customers having a bad time. +// +// To disable this behavior, document your code. +package documentfunctions + +import ( + "go/ast" + "strings" + + "golang.org/x/tools/go/analysis" +) + +var Analyzer = &analysis.Analyzer{ + Name: "documentfunctions", + Doc: "Prevent the use of time.Sleep in test functions", + Run: run, +} + +var ignoreFunctions = []string{ + "main", // main functions are probably okay +} + +// run runs the analysis pass for documentfunctions. It performs a depth-first +// traversal of all AST nodes in a file, looks for function definitions, and +// then ensures all of them have comments. +func run(pass *analysis.Pass) (interface{}, error) { + for _, file := range pass.Files { + pos := pass.Fset.Position(file.Pos()) + if !strings.HasSuffix(".go", pos.Filename) { + continue + } + ast.Inspect(file, func(n ast.Node) bool { + fe, ok := n.(*ast.FuncDecl) + if !ok { + return true + } + + for _, ignoreName := range ignoreFunctions { + if fe.Name.Name == ignoreName { + return true + } + } + + if fe.Doc == nil { + if fe.Name.Name == "init" { + pass.Reportf(fe.Pos(), "init functions must have side effects documented") + return true + } + pass.Reportf(fe.Pos(), "function %s must have documentation", fe.Name.Name) + } + + return true + }) + } + return nil, nil +} |
