Go

What does go vet catch? What does it report for the code below?

Question 431MediumGo 1.22 to 1.25
package main

import (
    "context"
    "fmt"
    "sync"
    "time"
)

type Counter struct {
    mu sync.Mutex
    n  int
}

func (c Counter) Inc() { c.mu.Lock(); c.n++; c.mu.Unlock() }   // (1)

func main() {
    ctx, _ := context.WithTimeout(context.Background(), time.Second) // (2)
    _ = ctx
    fmt.Printf("%d items\n", "three")                               // (3)
}

go vet reports three problems:

  1. copylocks: Inc passes lock by value. The value receiver copies the mutex, and the increment is lost. Use func (c *Counter).
  2. lostcancel: the cancel function is discarded, so the context and its timer leak until the timeout fires.
  3. printf: %d with a string argument.

Other default analyzers include structtag (malformed json:"x,omitempty" tags), unreachable, unusedresult, atomic (x = atomic.AddInt64(&x, 1)), httpresponse (using resp before checking err), tests (malformed Test/Example names), stdversion (1.23: API newer than the go line), waitgroup (1.25: wg.Add inside the goroutine), and buildtag.

go test automatically runs a high-confidence subset (atomic, bool, buildtags, directive, errorsas, ifaceassert, nilfunc, printf, stringintconv, tests). Vet's analyzers are chosen to have very few false positives, so it belongs in CI as a hard gate. shadow is not included by default.

More on Modules, Packages & Tooling

All 36 Modules, Packages & Tooling questions