Java Proto Names
This document contains information on what the fully-qualified Java name of a proto is, based on the different proto options. This name corresponds to the package you need to import to use that message.
Recommendation
Starting with Edition 2024, best practice is to:
- Set
option java_package = "com.example.package" - Do not set
java_outer_classnameorfeatures.(pb.java).nest_in_file_class = YES.
Starting with Edition 2024, the default behaviors have otherwise been improved so that now the default behavior is considered current best practice.
When using Proto2, Proto3, or Edition 2023, best practice is to:
- Set
option java_multiple_files = true; - Set
option java_outer_classname = "FileNameProto"; - Set
option java_package = "com.google.package";
Explanation
Multiple Files
With java_multiple_files = true, the generated Java class for each message
will be placed in a separate .java file. This makes it much easier to move
messages from one .proto file to another.
Starting in Edition 2024 this has been replaced by the feature
features.(pb.java).nest_in_file_class which has default value of NO,
matching the java_multiple_files = true behavior in older syntax.
Outer Classname
There is a Java class generated for the .proto file itself. The name of the
class for the file will be automatically generated if not specified. However,
the rules for how that name is generated are overly-complicated and non-obvious.
The best policy is to explicitly set the java_outer_classname option to the
.proto file name converted to PascalCase with the '.' removed. For example:
The file
student_record_request.protoshould set:option java_outer_classname = "StudentRecordRequestProto";
Starting in Edition 2024, java_outer_classname is still available, but the
default behavior has been changed to match this recommendation and so does not
need to be set.
Java Package
The Java package for generated bindings will be automatically set to the proto
package. However, this is usually not conformant with Java conventions. To
ensure a conventional Java package name, we recommend explicitly setting the
java_package option. For example, within Google, the convention is to prepend
com.google. to the proto package.
Immutable API Message Names
The Java plugin for protoc will generate names according to this table.
| java_multiple_files | java_package | java_outer_classname | Generated full message name |
|---|---|---|---|
| true | Not defined | ignored | com.google.protos.$package.$message |
| true | Defined | ignored | $java_package.$message |
| false | Not defined | Not defined | com.google.protos.$package.$derived_outer_class.$message |
| false | Not defined | Defined | com.google.protos.$package.$java_outer_classname.$message |
| false | Defined | Not defined | $java_package.$derived_outer_class.$message |
| false | Defined | Defined | $java_package.$java_outer_classname.$message |
Legend
$messageis the actual name of the proto message.$packageis the name of the proto package. This is the name specified by thepackagedirective in the proto file, which is usually at the top of the file.$derived_outer_classis a name generated from the proto file name. Generally it’s computed by removing punctuation from the file name and converting it to PascalCase. For example, if the proto isfoo_bar.proto, the$derived_outer_classvalue isFooBar.If the generated class name would be the same as one of the messages defined in the proto file,
derived_outer_classhasOuterClassappended to it. For example, if the proto isfoo_bar.protoand contains aFooBarmessage, the$derived_outer_classvalue isFooBarOuterClass. The same is true when using the v1 API, whether or not the class name would be the same as one of the messages defined.All other
$namesare the values of the corresponding file options defined in the.protofile.