Skip to content

Commit

Permalink
empty-block: Fix false positive on select {} (#805)
Browse files Browse the repository at this point in the history
This fixes a false positive reported by revive on the following:

    select {}

This is a way to block the program indefinitely.
It is used in cases like:

- Running a long-running server in a background thread
  and blocking `main` from exiting until the application dies.
  This is something you might do if your process has
  multiple servers/listeners in the same process.

  ```go
  go grpcListenAndServe()
  go httpListenAndServe()
  go logFlusher()

  select {}
  ```

- In programs compiled to WASM to prevent the application from exiting,
  so that the Javascript components may interact with it.

  ```go
  func main() {
    js.Global().Set("foo", foo)
    select {}
  }
  ```

  Without this, one may see an error like,
  "Error: Go program has already exited"

As a workaround, these programs can block forever
by receiving from a throwaway channel (`<-make(chan struct{})`),
but `select {}` is still a completely valid way of doing this,
so supporting it makes sense.

The issue was previously reported in #698 but was closed
because the author was satisfied with a `//nolint` comment.

Now that this rule is part of the default rule set (#799)
the case for addressing the false positive is stronger.

Resolves #804
  • Loading branch information
abhinav authored Mar 16, 2023
1 parent 5db07b5 commit b03e54f
Show file tree
Hide file tree
Showing 2 changed files with 16 additions and 0 deletions.
3 changes: 3 additions & 0 deletions rule/empty-block.go
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,9 @@ func (w lintEmptyBlock) Visit(node ast.Node) ast.Visitor {
case *ast.FuncLit:
w.ignore[n.Body] = true
return w
case *ast.SelectStmt:
w.ignore[n.Body] = true
return w
case *ast.RangeStmt:
if len(n.Body.List) == 0 {
w.onFailure(lint.Failure{
Expand Down
13 changes: 13 additions & 0 deletions testdata/empty-block.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,21 @@

package fixtures

import "net/http"

func f(x int) {} // Must not match

type foo struct{}

func (f foo) f(x *int) {} // Must not match
func (f *foo) g(y *int) {} // Must not match


func h() {
go http.ListenAndServe()
select {} // Must not match
}

func g(f func() bool) {
{ // MATCH /this block is empty, you can remove it/
}
Expand Down Expand Up @@ -44,4 +52,9 @@ func g(f func() bool) {
for range s { // MATCH /this block is empty, you can remove it/
}

select {
case _, ok := <-c:
if ok { // MATCH /this block is empty, you can remove it/
}
}
}

0 comments on commit b03e54f

Please sign in to comment.