formatters:
  enable:
    - gci
    - gofumpt
    - goimports
  settings:
    gci:
      sections:
        - standard
        - default
        - prefix(github.com/prometheus/prometheus)
    gofumpt:
      extra-rules: true
    goimports:
      local-prefixes:
        - github.com/prometheus/prometheus

issues:
  max-issues-per-linter: 0
  max-same-issues: 0

linters:
  # Keep this list sorted alphabetically
  enable:
    - depguard
    - errorlint
    - exptostd
    - fatcontext
    - gocritic
    - godot
    - govet
    - loggercheck
    - misspell
    - nilnesserr
    # TODO(bwplotka): Enable once https://github.com/golangci/golangci-lint/issues/3228 is fixed.
    # - nolintlint
    - perfsprint
    - predeclared
    - revive
    - sloglint
    - testifylint
    - unconvert
    - unused
    - usestdlibvars
    - whitespace

  exclusions:
    paths:
      # Skip autogenerated files.
      - ^.*\.(pb|y)\.go$
    rules:
      - linters:
          - errcheck
        # Taken from the default exclusions in v1.
        text: Error return value of .((os\.)?std(out|err)\..*|.*Close|.*Flush|os\.Remove(All)?|.*print(f|ln)?|os\.(Un)?Setenv). is not checked
      - linters:
          - govet
        # We use many Seek methods that do not follow the usual pattern.
        text: "stdmethods: method Seek.* should have signature Seek"
      - linters:
          - revive
        # We have stopped at some point to write doc comments on exported symbols.
        # TODO(beorn7): Maybe we should enforce this again? There are ~500 offenders right now.
        text: exported (.+) should have comment( \(or a comment on this block\))? or be unexported
      - linters:
          - gocritic
        text: "appendAssign"
      - linters:
          - errcheck
        path: _test.go
      - linters:
          - errorlint
        path: "tsdb/head_wal.go"
      - linters:
          - godot
        source: "^// ==="
      - linters:
          - staticcheck
        text: 'v1\.(Endpoints|EndpointSubset|EndpointPort|EndpointAddress) is deprecated: This API is deprecated in v1.33+'
    warn-unused: true
  settings:
    depguard:
      rules:
        main:
          deny:
            - pkg: "sync/atomic"
              desc: "Use go.uber.org/atomic instead of sync/atomic"
            - pkg: "github.com/stretchr/testify/assert"
              desc: "Use github.com/stretchr/testify/require instead of github.com/stretchr/testify/assert"
            - pkg: "github.com/go-kit/kit/log"
              desc: "Use github.com/go-kit/log instead of github.com/go-kit/kit/log"
            - pkg: "io/ioutil"
              desc: "Use corresponding 'os' or 'io' functions instead."
            - pkg: "regexp"
              desc: "Use github.com/grafana/regexp instead of regexp"
            - pkg: "github.com/pkg/errors"
              desc: "Use 'errors' or 'fmt' instead of github.com/pkg/errors"
            - pkg: "gzip"
              desc: "Use github.com/klauspost/compress instead of gzip"
            - pkg: "zlib"
              desc: "Use github.com/klauspost/compress instead of zlib"
            - pkg: "golang.org/x/exp/slices"
              desc: "Use 'slices' instead."
    errcheck:
      exclude-functions:
        # Don't flag lines such as "io.Copy(io.Discard, resp.Body)".
        - io.Copy
        # The next two are used in HTTP handlers, any error is handled by the server itself.
        - io.WriteString
        - (net/http.ResponseWriter).Write
        # No need to check for errors on server's shutdown.
        - (*net/http.Server).Shutdown
        # Never check for rollback errors as Rollback() is called when a previous error was detected.
        - (github.com/prometheus/prometheus/storage.Appender).Rollback
    govet:
      disable:
        - shadow
        - fieldalignment
      enable-all: true
    perfsprint:
      # Optimizes even if it requires an int or uint type cast.
      int-conversion: true
      # Optimizes into `err.Error()` even if it is only equivalent for non-nil errors.
      err-error: true
      # Optimizes `fmt.Errorf`.
      errorf: true
      # Optimizes `fmt.Sprintf` with only one argument.
      sprintf1: true
      # Optimizes into strings concatenation.
      strconcat: false
    revive:
      # By default, revive will enable only the linting rules that are named in the configuration file.
      # So, it's needed to explicitly enable all required rules here.
      rules:
        # https://github.com/mgechev/revive/blob/master/RULES_DESCRIPTIONS.md
        - name: blank-imports
        - name: comment-spacings
        - name: context-as-argument
          arguments:
            # Allow functions with test or bench signatures.
            - allowTypesBefore: '*testing.T,testing.TB'
        - name: context-keys-type
        - name: dot-imports
        - name: early-return
          arguments:
            - "preserveScope"
        # A lot of false positives: incorrectly identifies channel draining as "empty code block".
        # See https://github.com/mgechev/revive/issues/386
        - name: empty-block
          disabled: true
        - name: error-naming
        - name: error-return
        - name: error-strings
        - name: errorf
        - name: exported
        - name: increment-decrement
        - name: indent-error-flow
          arguments:
            - "preserveScope"
        - name: package-comments
          # TODO(beorn7): Currently, we have a lot of missing package doc comments. Maybe we should have them.
          disabled: true
        - name: range
        - name: receiver-naming
        - name: redefines-builtin-id
        - name: superfluous-else
          arguments:
            - "preserveScope"
        - name: time-naming
        - name: unexported-return
        - name: unreachable-code
        - name: unused-parameter
        - name: unused-receiver
        - name: var-declaration
        - name: var-naming
    testifylint:
      disable:
        - float-compare
        - go-require
      enable-all: true

output:
  show-stats: false

run:
  timeout: 15m

version: "2"
