Skip to content

Plugin Options

Options control how protoc-gen-pydantic generates Python output. They are passed via:

  • buf: opt: in buf.gen.yaml
  • protoc: --pydantic_opt= flag(s)

Summary

Option Default Description
preserving_proto_field_name true Use snake_case proto names instead of camelCase
auto_trim_enum_prefix true Remove enum type prefix from value names
use_integers_for_enums false Use integer values instead of string names
disable_field_description false Omit description= from field annotations
use_none_union_syntax_instead_of_optional true Use T \| None instead of Optional[T]
disable_validate false Omit all buf.validate constraints and CEL validators from generated models

preserving_proto_field_name

Controls whether field names use the proto snake_case name or the camelCase JSON name.

Default: true (snake_case)

message User {
  bool   is_active  = 1;
  string first_name = 2;
}
class User(_ProtoModel):
    is_active: "bool" = _Field(default=False)
    first_name: "str" = _Field(default="")
class User(_ProtoModel):
    isActive: "bool" = _Field(default=False)
    firstName: "str" = _Field(default="")

buf.gen.yaml:

opt:
  - preserving_proto_field_name=false

protoc:

--pydantic_opt=preserving_proto_field_name=false


auto_trim_enum_prefix

Removes the enum type name prefix (case-insensitive, with trailing _) from value names.

Default: true (trim prefix)

enum Status {
  STATUS_UNSPECIFIED = 0;
  STATUS_OK          = 1;
  STATUS_ERROR       = 2;
}
class Status(_ProtoEnum):
    UNSPECIFIED = ("UNSPECIFIED", 0)
    OK = ("OK", 1)
    ERROR = ("ERROR", 2)
class Status(_ProtoEnum):
    STATUS_UNSPECIFIED = ("STATUS_UNSPECIFIED", 0)
    STATUS_OK = ("STATUS_OK", 1)
    STATUS_ERROR = ("STATUS_ERROR", 2)

buf.gen.yaml:

opt:
  - auto_trim_enum_prefix=false


use_integers_for_enums

When enabled, enums use int as the mixin type and integer values instead of string names.

Default: false (string values)

enum Status {
  STATUS_UNSPECIFIED = 0;
  STATUS_OK          = 1;
  STATUS_ERROR       = 2;
}
class Status(_ProtoEnum):
    UNSPECIFIED = ("UNSPECIFIED", 0)
    OK = ("OK", 1)
    ERROR = ("ERROR", 2)
class Status(_ProtoEnum):
    UNSPECIFIED = 0
    OK = 1
    ERROR = 2

buf.gen.yaml:

opt:
  - use_integers_for_enums=true


disable_field_description

When enabled, omits description= from generated _Field() calls even when the proto field has a comment. The inline Python comment is still emitted.

Default: false (include descriptions)

message User {
  // The user's display name.
  string name = 1;
}
class User(_ProtoModel):
    # The user's display name.
    name: "str" = _Field(default="", description="The user's display name.")
class User(_ProtoModel):
    # The user's display name.
    name: "str" = _Field(default="")

buf.gen.yaml:

opt:
  - disable_field_description=true


use_none_union_syntax_instead_of_optional

Controls how nullable types are expressed in annotations.

Default: true (T | None union syntax)

message User {
  optional string nickname = 1;
}
class User(_ProtoModel):
    nickname: "str | None" = _Field(default=None)
from typing import Optional as _Optional


class User(_ProtoModel):
    nickname: "_Optional[str]" = _Field(default=None)

The T | None syntax requires Python 3.10+ for runtime evaluation. Generated files use string annotations ("T | None") so they are forward-compatible with Python 3.9.

buf.gen.yaml:

opt:
  - use_none_union_syntax_instead_of_optional=false


disable_validate

When enabled, all buf.validate constraints and CEL validators are omitted from the generated output. The result is identical to what would be produced if the proto files had no import "buf/validate/validate.proto" and no (buf.validate.field) or (buf.validate.message) options.

Fields that would otherwise be required due to constraints (e.g., a string.email field with no valid zero value) revert to their proto3 zero-value defaults ("", 0, false, etc.).

Default: false (include buf.validate constraints)

import "buf/validate/validate.proto";

message User {
  string email = 1 [(buf.validate.field).string.email = true];
}
class User(_ProtoModel):
    email: _Annotated[str, _AfterValidator(_validate_email)]
class User(_ProtoModel):
    email: str = _Field(default="")

buf.gen.yaml:

opt:
  - disable_validate=true

protoc:

--pydantic_opt=disable_validate=true


Combining options

Multiple options can be specified together:

# buf.gen.yaml
plugins:
  - local: protoc-gen-pydantic
    opt:
      - paths=source_relative
      - preserving_proto_field_name=false
      - auto_trim_enum_prefix=false
      - use_integers_for_enums=true
      - disable_field_description=true
    out: gen
# protoc
protoc --pydantic_opt=preserving_proto_field_name=false,auto_trim_enum_prefix=false \
       --pydantic_opt=use_integers_for_enums=true \
       ...