x/tools/go/analysis <https://pkg.go.dev/golang.org/x/tools/go/analysis> 
states "[a]n analysis reports mistakes is informally called a 'checker'". 
While checkers are extensional - and Go is tangibly not sine qua non about 
extensions - the foundations are there and they seem appropriate in the 
right circumstances. Analyses employed by `go vet` or `gopls` demonstrate 
the utility of checkers within the standard Go distribution.

It seems like, while there are enough options out there, there's no really 
immediate way to run a checker from a third party from the standard 
distribution. One reasonable question is whether this really is a gap in 
the ecosystem, or if it's fine to leave alone. Static analyzers don't have 
to be checkers, and the ones that aren't that sharp don't make sense here. 
Another question, though: for well-formulated checkers, could `go test` be 
a platform for running them? I'm wondering if it'd be plausible to run a 
checker very much like a test function. Or if I'm missing something that 
makes the notion obviously implausible. As a very crude illustration:

```
-- local_test.go --
package local

import (
    "testing"

    "github.com/some/checker"
)

func TestChecker() {
    testing.Analyze(checker.Check()
}
```

The details would be a bit magic, with a fair amount of implicit behavior:
- There'd be no *testing.T argument (not sure about this, but just for 
illustration...)
- `checker.Check()` would not be an `analysis.Analyzer`, but eventually 
serves to partially initialize one with analysis logic. Roughly, I think 
the type of `checker.Check()` could be some interface. Indirection and 
assertions behind the scenes could be employed such that `analysis` isn't 
an explicit dependency in `local` or `testing`; `analysis` would likely be 
a dependency in `checker`.
- the `analysis.Analyzer` is employed by an `analysis.Pass` populated by 
`testing` - the set of files it examines are naturally described by the 
invocation of `testing`
- `testing` would arrange for this `analysis.Pass` to run once before other 
tests, aggregating all `testing.Analyze` inputs to run with that pass
- problems detected by checkers would manifest like other fatal `testing` 
outcomes: halting, failing, and logging a relevant message
- a really very, very magic thing would be for `gopls` to detect 
`testing.Analyze` calls ...

The closest prior art here I've found is https://github.com/surullabs/lint, 
it has a stated purpose of having "lint checks to be part of a regular go 
build + go test workflow". But it's also using `os/exec` to run linters - 
that seems like a red flag. It also doesn't stress checkers versus linting 
for style, etc. Also in terms of prior art, I don't think it's entirely 
unnatural to end up with something ad-hoc along the same lines when 
developing around code generation or reflection.

I should note I'm definitely seeing this because of discussion around 
struct tags on https://github.com/golang/go/issues/73787, 
https://github.com/golang/go/issues/74472#issuecomment-3061802569. 
https://github.com/golang/go/issues/74376 seems like an example of using 
static analysis over json tags in a way that would be possible to `go 
test`. It's not necessary with `go vet` and `gopls` coverage, but I think 
that putting equivalent pieces together isn't really convenient for third 
party solutions ... maybe it could be?

-- 
You received this message because you are subscribed to the Google Groups 
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to golang-nuts+unsubscr...@googlegroups.com.
To view this discussion visit 
https://groups.google.com/d/msgid/golang-nuts/8f68ed1a-1664-4db7-9773-d80ba1febc5bn%40googlegroups.com.

Reply via email to