# protolint lints proto files without needing protoc

> protolint is a pluggable linter and fixer for Protocol Buffer files that parses proto2 and proto3 sources directly, follows the official style guide rule for rule, and can auto-fix or auto-disable findings in place. It suits teams generating .proto files across languages, and it is not a compiler.

**yoheimuta/protolint** — A pluggable linter and fixer to enforce Protocol Buffer style and conventions. 

- Repository: https://github.com/yoheimuta/protolint
- Stars: 697 · Forks: 65
- Language: Go
- License: MIT
- Published: 2026-10-21 · Updated: 2026-10-21 · Language: en
- Canonical page: https://hysenlabs.com/projects/yoheimuta-protolint

## The parser runs on its own, with no protoc in the loop

The first thing the project lists is that it runs fast because this works without compiler, and that single decision shapes everything else. A linter that needs protoc has to generate descriptors, which means the toolchain, the include paths and the plugins all have to line up, and a style check becomes dependent on a working build. protolint instead parses .proto files itself, and the repository layout shows how that is arranged. The go.mod pulls in github.com/yoheimuta/go-protoparser/v4 at v4.14.2, a dedicated parser, alongside google.golang.org/protobuf at v1.36.11 and github.com/golang/protobuf at v1.5.4, the protobuf runtime libraries. The internal/ directory holds the implementation and the linter/ directory sits at the top level, so the rule set and the checking engine are separated from the parsing. For a team whose protos are checked in and whose generated code is produced elsewhere, that separation is the whole value.

## The rule list maps onto the official style guide one to one

The second listed property is that it is easy to follow the official style guide, because the rules and the style guide correspond to each other exactly, and the fixer automatically fixes all the possible official style guide violations. That correspondence is the promise, and it is the one to test when you adopt the tool. A linter whose rules are the author's preferences gives you an argument to have on every pull request. A linter whose rules are numbered the same way as the published guide gives you a shared reference to point at. The project also states that all rules have undergone testing, which is a claim you can partly check yourself by running the tool over your own files and seeing whether the reported items match the guide. The rules are not limited to formatting either, since the topics list a style linter for proto3 and protocol buffers, and the file naming and indentation findings in the demo output show the tool reporting on file names as well as on the contents.

## Findings can be suppressed with a comment when the API cannot change

The third listed property is the one that decides whether a team can live with the tool. It allows disabling rules with a comment in a Protocol Buffer file, and the stated use is projects which must keep API compatibility while enforce the style guide as much as possible. The reason is obvious once stated. A message field name is part of the wire contract, so renaming it to satisfy a style rule is not a formatting change, it is a breaking change for every consumer. A comment that disables the rule locally, at the point of the violation, is the only workable answer, and the documentation notes that some rules can be automatically disabled by inserting comments to the spotted violations. The command line has a matching flag, -auto_disable=next, so a script can insert those suppressions for you rather than making an engineer retype them. That combination of a fixer and an auto-disabler is unusual and useful.

## Installing it covers Homebrew, GitHub releases, Docker, Go, npm and PyPI

The distribution story is unusually wide, which tells you the tool is used from several toolchains. On Mac or Linux, Homebrew serves it through a tap:

```bash
brew tap yoheimuta/protolint
brew install protolint
```

The author notes that homebrew-core already includes protolint, so a plain brew install protolint works, but that default tap is not maintained by the same author and recommends tapping the author's repository first to keep it updated. Pre-built binaries in .tar.gz packages are on the release page. There is a maintained Docker image, yoheimuta/protolint, whose entrypoint is the binary itself. From source, if Go is available, the install is one command, though the author recommends a pre-built binary instead because the source build does not include the version info. For JavaScript and TypeScript projects, an npm package installs a development dependency whose postinstall script downloads the matching binary from GitHub. For Python projects, a wheel called protolint-bin on PyPI ships the pre-compiled binaries and adds the linter configuration to the tools.protolint package in pyproject.toml.

## The npm package can be pointed at an internal mirror

The npm route has a wrinkle worth knowing about if you run builds behind a proxy or on a network that cannot reach GitHub. During install, a postinstall.js script is called which downloads the matching protolint from GitHub, and the documentation compares this to the @electron/get package. The download can be redirected with environment variables, and the table lists them with their defaults. PROTOLINT_MIRROR_HOST defaults to https://github.com and is the HTTP or web server base url hosting the binaries. PROTOLINT_MIRROR_REMOTE_PATH defaults to yoheimuta/protolint/releases/download and is the path to the archives on the remote host, and the archives from the releases page must be mirrored there. PROTOLINT_MIRROR_USERNAME and PROTOLINT_MIRROR_PASSWORD supply HTTP Basic auth credentials, and PROTOLINT_PROXY sets an HTTP or HTTPS proxy with optional auth data. After installation the command is invoked as npx protolint with all supplied protolint arguments within your dev-scripts.

## The command surface covers files, directories, stdin and config discovery

The usage block shows how many entry points the tool has:

```bash
protolint lint example.proto example2.proto # file mode, specify multiple specific files
protolint lint .                            # directory mode, search for all .proto files recursively
protolint .                                 # same as "protolint lint ."
protolint lint -stdin_filename=v1/f.proto - # read from stdin and assume its path is v1/f.proto
protolint lint -config_path=path/to/your_protolint.yaml . # use path/to/your_protolint.yaml
protolint lint -config_dir_path=path/to .   # search path/to for .protolint.yaml
protolint lint -fix .                       # automatically fix some of the problems reported by some rules
```

The stdin mode with a filename is the one to note, because it is what makes editor integration work, since the editor hands the buffer over with the path it would have on disk so that path-dependent rules fire correctly. Configuration is discovered in two ways, an explicit path with -config_path and a directory search with -config_dir_path for a .protolint.yaml file. The -fix flag applies the automatic fixes, and the documentation is careful to say it fixes some of the problems reported by some rules, so the fixer is partial by design rather than complete.

## Plugins and an MCP server extend the tool in two directions

Two extension points define what protolint has become. The first is plugin loading, listed as loads plugins to contain your custom lint rules, and the go.mod shows the mechanism, github.com/hashicorp/go-plugin at v1.8.0, the standard Go plugin RPC framework, with google.golang.org/grpc at v1.83.2 underneath it. That means a custom rule can live in a separate process and be loaded at runtime, so a team can hold house style rules outside the tool's own repository and version them independently. The second is newer. protolint now includes support for the Model Context Protocol, which allows AI models to interact with protolint directly, and the server is started with a single flag:

```bash
protolint --mcp
```

The detailed integration notes live in a dedicated mcp/ directory, which also has its own README, and the project shows a demo of asking an MCP client such as Claude Desktop to lint and fix Protocol Buffer files. The integration list is broad as well, with a protoc plugin, editor integration including a vim plugin, a GitHub Action and CI integration. The repository ships a .pre-commit-hooks.yaml so the hook can be installed directly, and the CI workflow badge points at a go.yml workflow.

## Where protolint is the wrong tool

Three cases argue against it. The first is a project whose protos are generated rather than hand written. If the .proto files are produced by another tool, linting them after generation fights the generator, and the right place for the rules is inside the generator. The second is a team that wants semantic checking rather than style. protolint deliberately avoids the compiler, which is what makes it fast, and the trade is that it does not know whether a field type is legal, whether an import resolves, or whether a message is used. For that you want protoc in the build. The third is a project that cannot tolerate a fixer in the loop at all, because the auto-fix mode rewrites files and the auto-disable mode inserts comments, and both change files that someone else owns. The project handles this with -fix being opt in per run and with a reporter option, tsc, that produces output matching the TSC compiler, which suggests a reasonable compromise: run the linter as a report in CI and apply fixes locally. One more practical detail is worth checking. The npm and PyPI routes download binaries at install time, so a locked build environment without network access to the release host needs the mirror variables or a different install route.

## Conclusion

Adopt protolint when your repository generates .proto files for several languages and you want the official style guide enforced with the option to fix or suppress findings per file, and keep the compiler in the loop for anything that needs type checking. Verify first which rules your version enables by default, because the fixer covers only some violations and the documentation states the correspondence between rules and the style guide, then read the pre-commit hook configuration before wiring it into CI so that the auto-fix step does not surprise anyone.

## FAQ

### Does protolint need protoc to be installed?

No. It runs fast because it works without a compiler, and it parses proto2 and proto3 files itself through the go-protoparser library listed in go.mod. That means style checking does not depend on a working protoc toolchain.

### How do I install protolint?

The documented routes are a Homebrew tap with brew tap yoheimuta/protolint followed by brew install protolint, pre-built binaries from the GitHub release page, the maintained Docker image yoheimuta/protolint, go install github.com/yoheimuta/protolint/cmd/protolint@latest, an npm package that downloads the binary at install time, and a protolint-bin wheel on PyPI.

### Can protolint fix violations automatically?

Yes. The fixer automatically fixes all the possible official style guide violations, and the -fix flag applies it. The command line documentation is careful to say it fixes some of the problems reported by some rules, and the -auto_disable=next option can insert rule-disabling comments at the spotted violations.

### How does protolint read configuration?

You can pass an explicit file with -config_path=path/to/your_protolint.yaml, or let the tool search a directory with -config_dir_path=path/to for a .protolint.yaml file. In JavaScript projects a protolint node in package.json may hold the content of protolint.yml, and in Python projects the configuration goes in the tools.protolint package in pyproject.toml.

### What is the protolint MCP server for?

protolint includes support for the Model Context Protocol, which allows AI models to interact with protolint directly. You start it with protolint --mcp, and the demo shows asking an MCP client such as Claude Desktop to lint and fix Protocol Buffer files.

## Sources

- [Issues](https://github.com/yoheimuta/protolint/issues)
- [License: MIT](https://github.com/yoheimuta/protolint/blob/master/LICENSE)
- [README](https://github.com/yoheimuta/protolint/blob/master/README.md)
- [Releases](https://github.com/yoheimuta/protolint/releases)
- [yoheimuta/protolint on GitHub](https://github.com/yoheimuta/protolint)

---

Hysen Labs editorial analysis, written from the project's own repository and release notes. Cite the canonical page: https://hysenlabs.com/projects/yoheimuta-protolint
