The Buf CLI is a helpful tool for managing Protobuf schemas. It offers various features, including code generation, breaking change detection, linting, and formatting, to assist with Protobuf development and maintenance. It works with your choice of plugins and languages and gives you access to a vast library of certified plugins in the Buf Schema Registry.

Buf CLI commands

The links below go to detailed usage guides. See the Buf CLI reference for complete options and flags for each command.

  • build: Build Protobuf files into a Buf image (key to many other buf operations)
  • generate: Generate code stubs from Protobuf files using protoc plugins
  • breaking: Verify no breaking changes have been made, to guard against compatibility issues
  • lint and format: Lint and format your Protobuf files according to best practice and your org rules
  • curl: Test your APIs by invoking an RPC endpoint, similar to using cURL
  • convert: Convert a message from binary to JSON or vice versa—useful when debugging or testing
  • config, registry, push, and export: Manage your repositories in the Buf Schema Registry

Configuration files

The Buf CLI interacts with several configuration files, depending on the operation.


buf.yaml defines a workspace and the configurations for each module within it. It's the primary configuration file, and defines each module's directory, name, lint and breaking configurations, and any files to exclude, along with the workspace's shared dependencies.


buf.lock contains the workspace's dependency manifest, and represents a single, reproducible build of its dependencies.


buf.gen.yaml defines the set of code generation plugins, their options, and the inputs used by the buf generate command to generate code from your Protobuf files. It also allows you to enable and configure managed mode.

Default configuration

The default configuration location depends on the input. If the Buf CLI is executed with an input that contains a buf.yaml file, it's used for the given operation. Running buf lint, for example, would use the lint configuration for the workspace and (if specified) each module in the input's buf.yaml.

If the input doesn't contain a buf.yaml file, the Buf CLI operates as if there is a buf.yaml file with these default values:

buf.yaml default configuration if missing
version: v2
# This is the default behavior if the modules key isn't specified.
# Deleting the modules section here has no effect.
  - path: .

Configuration overrides

Specifying an alternative configuration location is an advanced feature and not necessary in most cases.

Many of the Buf CLI commands support a --config flag that's used to override the buf.yaml configuration with a file path or direct JSON or YAML data. This is useful for situations where you may want to specify all options via the command line, for example with Bazel integrations and/or when using the protoc plugins.

All commands have one or more --.*config flags that control this behavior. For example:

  • buf build --config specifies the config for the source input.
  • buf lint --config specifies the config for the source or Buf image input.
  • buf breaking --config specifies the config for the source or image input.
  • buf breaking --against-config specifies the config for the source or image input to compare against.

The value of this flag is interpreted as follows:

  • If the value ends in .json, this is interpreted to be a local path to a JSON file.
  • If the value ends in .yaml, this is interpreted to be a local path to a YAML file.
  • Otherwise, this is interpreted to be either JSON or YAML data, which is directly parsed.

For example:

Read the JSON file foo/bar.json
$ buf lint --config foo/bar.json
Read the YAML file foo/bar.yaml
$ buf lint --config foo/bar.yaml
Use the given JSON data
$ buf lint --config '{"version": "v2","modules": {"path": "/path/to/directory","lint": {"use": ["ENUM_NO_ALLOW_ALIAS"]}}}'
# This results in only using the ENUM_NO_ALLOW_ALIAS lint rule for linting.