LoginSignup
6
1

More than 3 years have passed since last update.

golangci-lintを使いこなしたい。

Last updated at Posted at 2020-12-06

初めに

この記事はWanoグループ Advent Calendar 2020 の6日目の記事になります。

golangci-lintって?

Go言語には非常に多くのコード解析ツールがあります。例えば gofmt や goimports, govet などはgolangを書いている人なら知ってる人も多いと思います。
golangci-lintはGo言語のコード解析ツールを一つに集約したようなすごいやつです。

コードレビューをする時にまずこれを実行すると、機械的にまず直しておいたほうが良さそうな部分がわかって治安がよくなるかもしれないということですね。
そして解析結果はXMLだったりで出力することが出来るのでそこからさらにプログラムで使うのも簡単です。

インストールの方法などは上記リンクに記述してあるのでカットさせていただきます。

configファイルを晒してみる

golangci-lintではconfigファイルを用いて
* どの解析ツールを使うか
* 解析ツールの条件(変数の出現回数など)

などを設定することが出来ます。

自分が実際に使っているものを晒してみたいと思います(結構適当に設定してますが)。


run :
  issues-exit-code: 0

issues:
  max-issues-per-linter: 1000
  max-same-issues: 1000

output :
  format : checkstyle

linters:
  disable-all: true
  enable:
    - deadcode
    - errcheck
    - gosimple
    - govet
    - ineffassign
    - staticcheck
    - structcheck
    - typecheck
    - unused
    - varcheck
    - bodyclose
    - depguard
    - dogsled
    - gochecknoglobals
    - gochecknoinits
    # - goconst
    - gocritic
    - gofmt
    - goimports
    # - golint
    - gosec
    - interfacer
    - misspell
    - nakedret
    - prealloc
    - scopelint
    # - stylecheck
    - unconvert
    - unparam
    # - whitespace
    # - wsl

linters-settings:
  errcheck:
    ignore: '[rR]ead|[w|W]rite|[c|C]lose|[c|C]ommit|[r|R]ollback|[p|P]rintln'

  goconst:
    min-len : 5

  golint:
    min-confidence : 1.0

使い方としては

  1. まずgolangci-lint自体の設定を記述。
  2. 使うlinterを選ぶ。
  3. 各linterの設定を追加。

configファイルを呼んで解析する場合は

golangci-lint run -c .golang_review_config.yml <適当なpath>

とすれば良い感じに。なんでもかんでもぶち込むと「厳しすぎない?」となるので使うlinter類は各プロジェクトや開発者で選ぶと良いと思います。ちなみにymlファイルなのでコメントアウトも出来ます。

おすすめ

個人的に入れとくと良いやつを紹介してみます。
各linterの細かいconfigはカットです。

govet

これに関しては言うこともない気がします...が。
簡単に言うと「バグる可能性が高い部分を検知してくれる」やつです。なのでgovetでエラーが出る場合は「アウト」の認識だと良いと思います。例えばですが

type A struct {
    Num  int
    Text string
}

a := A{
    1,
    "aaa",
}

では「構造体を使う時に変数だけしか書いてない」ということで怒られます。

type A struct {
    Num  int
    Text string
}

a:=A{
    Num : 1,
    Text : "aaa",
}

こうしろということですね。

errcheck

個人的にgovetと並ぶと思っている強いやつです。エラーハンドリングし忘れたやつを教えてくれるので、これに引っかかる場合もアウトにして良いかもしれません(ただしデフォルトで Close() などでも引っかかる)。

func (db DB)insert(<hogehoge>)error

func main() {
    DB.insert(<hogehoge>) // エラー
    _ = DB.insert(<hogehoge>) // 明示するとlinterがスルーしてくれる
}

例えば「エラーを返す関数だけど確認してないよ!」というときに教えてくれます。もし確認する必要がなければ明示的に _ で受けるとlinterが確認しなくなります(こういうことは開発ルールとして明記したほうが良いのかも)。

他にも...

  • unconvert : 不要なキャストを知らせる
  • unparam : 不要な関数の引数を知らせる
  • unused : 使っていない変数を教えてくれる(自分の中でunparamと混じってるかも)

他にも不要な○○を教えてくれる、書き方が変または簡単に書ける(省略できる)、など色々なことを教えてくれます。

まとめ

色々なlinterを使って開発者ごとのブレを少なく出来るといいですね()。
書き方などはともかく、バグになる可能性がある解析ツールをONにしてコミットやpushするときに解析すると事前に確認が出来て良いと思います。

6
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
6
1