Skip to content

Conversation

T-Sh
Copy link

@T-Sh T-Sh commented Sep 10, 2025

Adding gocheckerrbeforeuse linter.

The linter checks whether the error is handled before using the other returned values.

For example, the linter should catch the following situation, when print is called before err handling:

func wrongCustom2Func() {
	res, err := returns2Values()

	print(res)

	if err != nil {
	}
}

Copy link

boring-cyborg bot commented Sep 10, 2025

Hey, thank you for opening your first Pull Request !

@CLAassistant
Copy link

CLAassistant commented Sep 10, 2025

CLA assistant check
All committers have signed the CLA.

@ldez
Copy link
Member

ldez commented Sep 10, 2025

In order for a pull request adding a linter to be reviewed, the linter and the PR must follow some requirements.

  • The CLA must be signed

Pull Request Description

  • It must have a link to the linter repository.
  • It must provide a short description of the linter.

Base Requirements

These requirements are not declarative; the team will verify them.

  • It must not be a duplicate of another linter or a rule of a linter.
  • It must not have false positives/negatives.

Linter

  • It must have a valid license (AGPL is not allowed), and the file must contain the required information by the license, ex: author, year, etc.
  • It must use Go version <= 1.24.0
  • The linter repository must have a CI and tests.
  • It must use go/analysis.
  • It must have a valid semver tag, ex: v1.0.0, v0.1.0 (0.0.x are not valid).
  • It must not contain init().
  • It must not contain panic().
  • It must not contain log.Fatal(), os.Exit(), or similar.
  • It must not modify the AST.
  • It must have tests inside golangci-lint.

The Linter Tests Inside Golangci-lint

  • They must have at least one std lib import.
  • They must have integration tests without configuration (default).
  • They must have integration tests with configuration (if the linter has a configuration).

.golangci.next.reference.yml

  • The file .golangci.next.reference.yml must be updated.
  • The file .golangci.reference.yml must NOT be edited.
  • The linter must be added to the lists of available linters (alphabetical case-insensitive order).
    • enable and disable options
  • If the linter has a configuration, the exhaustive configuration of the linter must be added (alphabetical case-insensitive order)
    • The values must be different from the default ones.
    • The default values must be defined in a comment.
    • The option must have a short description.

Other Requirements

  • The files (tests and linter) inside golangci-lint must have the same name as the linter.
  • The .golangci.yml of golangci-lint itself must not be edited, and the linter must not be added to this file.
  • The linters must be sorted in alphabetical order (case-insensitive) in the lintersdb/builder_linter.go and .golangci.next.reference.yml.
  • The load mode (WithLoadMode(...)):
    • if the linter uses goanalysis.LoadModeSyntax -> no WithLoadForGoAnalysis() in lintersdb/builder_linter.go
    • if the linter uses goanalysis.LoadModeTypesInfo, it requires WithLoadForGoAnalysis() in lintersdb/builder_linter.go
  • The version in WithSince(...) must be the next minor version (v2.X.0) of golangci-lint.
  • WithURL() must contain the URL of the repository.

Recommendations

  • The file jsonschema/golangci.next.jsonschema.json should be updated.
  • The file jsonschema/golangci.jsonschema.json must NOT be edited.
  • The linter repository should have a readme and linting.
  • The linter should be published as a binary (useful for diagnosing bug origins).
  • The linter repository should have a .gitignore (IDE files, binaries, OS files, etc. should not be committed)
  • Use main as the default branch name.

Workflow

  • A tag should never be recreated.
  • The reviews or changes should be addressed as commits (no squash).

The golangci-lint team will edit this comment to check the boxes before and during the review.

The code review will start after the completion of those checkboxes (except for the specific items that the team will help to verify).

If the author of the PR is a member of the golangci-lint team, he should not edit this message.

This checklist does not imply that we will accept the linter.

@T-Sh T-Sh force-pushed the add_gocheckerrbeforeuse branch from b62e05a to 7c856d8 Compare September 10, 2025 11:02
@ldez ldez added the linter: new Support new linter label Sep 10, 2025
@ldez ldez self-requested a review September 10, 2025 11:03
@ldez ldez added the waiting for: contributor feedback Requires additional feedback label Sep 10, 2025
@T-Sh T-Sh force-pushed the add_gocheckerrbeforeuse branch from 7c856d8 to da2eea5 Compare September 10, 2025 12:01
@ldez
Copy link
Member

ldez commented Sep 10, 2025

The reviews should be addressed as commits (no squash).

#6070 (comment)

@T-Sh
Copy link
Author

T-Sh commented Sep 10, 2025

@ldez sorry for force push, i didnt expect you'd be so fast with review)

Fixes:

  • updates for .golangci.next.reference.yml, add linter and settings
  • extended tests, add test with configuration
  • linter replacement in builder_linter for sorting

@ldez ldez added waiting for: contributor feedback Requires additional feedback and removed waiting for: contributor feedback Requires additional feedback labels Sep 10, 2025
@ldez ldez changed the title feat: add linter gocheckerrbeforeuse feat: add gocheckerrbeforeuse linter Sep 10, 2025
@ldez ldez added declined and removed waiting for: contributor feedback Requires additional feedback labels Sep 10, 2025
@ldez
Copy link
Member

ldez commented Sep 10, 2025

  1. The detection is based on names: this is too naive, and it will lead to false negatives.
  2. The rule itself is too strict: there are valid use cases where errors are not checked right after the instantiation. This will lead to false positives.
  3. The distance option, as it's a "global" option, is "all or nothing". This will result in either false positives or false negatives, depending on the value of the option.
  4. The real problem is not the distance between the error and the check of the error, but the usage of the result(s) of a function that also emits the error before checking the error.

My conclusion, even if I understand the need behind this linter, is not to accept this linter because the problems are related to the approach of the linter.
Some points can be improved, but the linter cannot be improved easily to handle all of the previous points.

I recommend creating a plugin: https://golangci-lint.run/plugins/module-plugins/

Thank you anyway for suggesting the addition of your linter.


Some extra notes:

The linter implementation is overusing inlined if and nested if.
In 90% of the cases, this can be simplified by using "quick return" or switch.
We recommend reading this article: https://medium.com/@matryer/line-of-sight-in-code-186dd7cdea88

The licence file has been copied from another linter, and so the file is not right.

The linter name is explicit, maybe too explicit: it's almost a complete sentence.

  • The prefix go doesn't seem useful.
  • Module names that contain characters other than lower-case ASCII letters should be avoided.
  • The name needs to be rethought.

@ldez ldez closed this Sep 10, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
declined linter: new Support new linter
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants