{"id":37101721,"url":"https://github.com/adambrianbright/errstack","last_synced_at":"2026-01-14T12:20:49.425Z","repository":{"id":271393724,"uuid":"913294177","full_name":"AdamBrianBright/errstack","owner":"AdamBrianBright","description":"ErrStack is a linter for Go that checks for unnecessary error wrapping using `errors.Wrap`, `errors.Wrapf`, and `errors.WithStack`.","archived":false,"fork":false,"pushed_at":"2025-09-04T07:06:59.000Z","size":111,"stargazers_count":1,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-10-04T14:21:19.232Z","etag":null,"topics":["errors","go","go-linter","golang","linter","stacktrace"],"latest_commit_sha":null,"homepage":"https://pkg.go.dev/github.com/AdamBrianBright/errstack","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/AdamBrianBright.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2025-01-07T12:05:07.000Z","updated_at":"2025-09-04T07:07:04.000Z","dependencies_parsed_at":null,"dependency_job_id":"8d68a25b-3fe9-4ba7-9817-cb3c77f01c5a","html_url":"https://github.com/AdamBrianBright/errstack","commit_stats":null,"previous_names":["adambrianbright/errstack"],"tags_count":9,"template":false,"template_full_name":null,"purl":"pkg:github/AdamBrianBright/errstack","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/AdamBrianBright%2Ferrstack","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/AdamBrianBright%2Ferrstack/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/AdamBrianBright%2Ferrstack/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/AdamBrianBright%2Ferrstack/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/AdamBrianBright","download_url":"https://codeload.github.com/AdamBrianBright/errstack/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/AdamBrianBright%2Ferrstack/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":28420417,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-01-14T10:47:48.104Z","status":"ssl_error","status_checked_at":"2026-01-14T10:46:19.031Z","response_time":107,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.6:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["errors","go","go-linter","golang","linter","stacktrace"],"created_at":"2026-01-14T12:20:48.609Z","updated_at":"2026-01-14T12:20:49.417Z","avatar_url":"https://github.com/AdamBrianBright.png","language":"Go","funding_links":[],"categories":[],"sub_categories":[],"readme":"# 🛡️ ErrStack\n\n**ErrStack** is a powerful Go linter that detects unnecessary error wrapping using `errors.Wrap`, `errors.Wrapf`, and\n`errors.WithStack`, helping you maintain clean and efficient error handling in your codebase.\n\nCreated as the perfect complement to the [wrapcheck](https://github.com/tomarrell/wrapcheck) linter.\n\n## 📦 Installation\n\n### Requirements\n\n- Go `\u003e= v1.23.12`\n\n### Standalone Installation\n\n```bash\ngo install github.com/AdamBrianBright/errstack/cmd/errstack@latest\n```\n\n### 🔧 golangci-lint Integration\n\nErrStack can be used as a module for [golangci-lint](https://golangci-lint.run/usage/linters/#modules).\n\n`.custom-gcl.yml`\n\n```yaml .custom-gcl.yml\nversion: v1.64.8\n\ndestination: ./testdata/src\n\nplugins:\n  - module: 'github.com/AdamBrianBright/errstack'\n    import: 'github.com/AdamBrianBright/errstack/cmd/gclplugin'\n    version: v0.4.0\n```\n\n`.golangci.yml`\n\n```yaml .golangci.yml\nlinters-settings:\n  custom:\n    errstack:\n      type: \"module\"\n      description: Finds unnecessary error wraps with stacktraces.\n      settings:\n        wrapperFunctions:\n          - pkg: github.com/pkg/errors\n            names: [ New, Errorf, Wrap, Wrapf, WithStack ]\n            replaceWith: WithMessage\n            replaceWithFormat: WithMessagef\n        cleanFunctions:\n          - pkg: errors\n            names: [ New ]\n          - pkg: fmt\n            names: [ Errorf ]\n          - pkg: github.com/pkg/errors\n            names: [ WithMessage, WithMessagef ]\n\nlinters:\n  disable-all: true\n  enable:\n    - errstack\n```\n\n## ⚙️ Configuration\n\nYou can configure ErrStack using the `.errstack.yaml` file in your project root, or in your home directory.\n\n```yaml\n# List of functions that are considered to wrap errors.\n# If you're using some fancy error wrapping library like github.com/pkg/errors,\n# you may want to add it to this list.\n# If you want to ignore some functions, simply don't add them to the list.\nwrapperFunctions:\n  - pkg: github.com/pkg/errors\n    names: [ New, Errorf, Wrap, Wrapf, WithStack ]\n    replaceWith: WithMessage     # Optional. Attempts to replace errors.Wrap like functions with errors.WithMessage.\n    replaceWithFormat: WithMessagef  # Optional. Attempts to replace errors.Wrapf like functions with errors.WithMessagef.\n\n# List of functions that are considered to clean errors without stacktrace.\ncleanFunctions:\n  - pkg: errors\n    names: [ New ]\n  - pkg: fmt\n    names: [ Errorf ]\n  - pkg: github.com/pkg/errors\n    names: [ WithMessage, WithMessagef ]\n\n# Performance tuning options\nincludeVendor: true      # Whether to include vendor packages in analysis\nmaxDepth: 100           # Maximum depth for analysis to prevent infinite loops\nexcludePatterns: [ ]     # Patterns to exclude from analysis (e.g., [\"test\", \"mock\"])\n```\n\n## 🚀 Usage\n\nTo lint all the packages in your project, run:\n\n```bash\nerrstack ./...\n```\n\nYou can also target specific packages:\n\n```bash\nerrstack ./internal/...\nerrstack ./pkg/mypackage\n```\n\n## 🧪 Testing\n\nThis linter is thoroughly tested using `analysistest`. You can view all the test cases under the `testdata` directory to\nunderstand various scenarios and edge cases.\n\n## 🤔 Why ErrStack?\n\nIf you're using some fancy error wrapping library\nlike [github.com/pkg/errors](https://pkg.go.dev/github.com/pkg/errors), you may have stumbled upon doubling or tripling\nthe amount of stacktrace duplicates in your logs.\n\nThis happens because the library wraps errors in context style, hiding stacktraces from the user in unexported structs\nand fields like russian dolls.\n\nWhen doing so, libraries don't check for stacktraces already present in the error, since it is usually not necessary and\nonly slows down your code.\n\nHowever, if you're using libraries out of your control, you may not be able to easily identify whether some functions\nmay return wrapped errors or not, and just wrap errors from external packages\nlike [wrapcheck](https://github.com/tomarrell/wrapcheck) suggests anyways.\n\nThis linter helps you identify such cases and remove unnecessary wrapping, keeping your error handling clean and\nefficient.\n\n## 🔍 How Does It Work?\n\nErrStack uses advanced static analysis to detect redundant error wrapping:\n\n1. **📦 Package Analysis** - Preloads all packages and parses their ASTs\n2. **🎯 Function Discovery** - Finds all functions that return errors\n3. **📞 Call Tracking** - Identifies all calls to error-returning functions\n4. **🏷️ Wrapping Detection** - Marks functions that return wrapped errors\n5. **🔬 Flow Analysis** - Analyzes control flow graphs and reports unnecessary wrapping\n\n### 💡 Example\n\n```go\npackage main\n\nimport (\n\t\"github.com/pkg/errors\"\n)\n\nfunc main() {\n\t_ = testDoubleReturnWrapStack()\n}\n\nfunc testDoubleReturnWrapStack() error {\n\treturn errors.Wrap(errors.WithStack(nil), \"wrapped\") // want `Wrap call unnecessarily wraps error with stacktrace\\. Replace with errors\\.WithMessage\\(\\) or fmt\\.Errorf\\(\\)`\n}\n```","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fadambrianbright%2Ferrstack","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fadambrianbright%2Ferrstack","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fadambrianbright%2Ferrstack/lists"}