Add FieldDescriptor, EnumValueDescriptor, OneofDescriptor, and comment access#14
Merged
Conversation
Introduce a FieldDescriptor wrapper around FieldDescriptorProto with type-resolution (#type_descriptor via the context), type predicates (#message?/#enum?/#group?/#scalar?), and cardinality helpers (#repeated?/#required?/#optional?/#proto3_optional?). MessageDescriptor now exposes #fields and threads the Context through its initializer so fields can resolve their referenced types.
Introduce EnumValueDescriptor (name/number/#full_name) exposed via EnumDescriptor#values, and OneofDescriptor (#name/#index/#fields) exposed via MessageDescriptor#oneofs. FieldDescriptor gains #oneof? and #oneof to correlate a field with its containing oneof, excluding proto3 synthetic optional oneofs. Add a CommentEvent message with a oneof to the blog fixtures (and regenerate blog.cgr/blog.fds) to exercise oneof handling.
Add a Commentable mixin exposing #leading_comments, #trailing_comments, and #leading_detached_comments on every descriptor wrapper (file, message, field, enum, enum value, oneof, service, method). FileDescriptor builds an identity-keyed index from each raw descriptor proto to its SourceCodeInfo::Location by reconstructing the numeric paths protoc emits; wrappers reach their file via a uniform #file accessor. Empty comments normalize to nil. Add comments to the blog fixtures (and regenerate) to exercise comment resolution for each descriptor type.
Returns detached blocks, the leading comment, and the trailing comment as a single array in source order, omitting empties.
Per protoc, leading_detached_comments appear before but are "not connected to" the element (separated by a blank line), so they are section headers or notes rather than documentation of the element. #comments now returns only the attached leading and trailing comments; detached blocks remain available via #leading_detached_comments. Add a detached comment to the fixtures to cover the distinction.
Detached comments are proto file organization (section headers, notes) rather than documentation attached to any element, and their placement is awkward to reason about. Remove the accessor and the fixture that exercised it; #comments already surfaces only attached leading/trailing comments.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Fills out the descriptor-wrapper layer so plugins can work with the parts of a generation request that previously required dropping down to the raw
google-protobufAPI — most importantly fields, plus enum values, oneofs, and comments.What's new
FieldDescriptor(MessageDescriptor#fields) — wrapsFieldDescriptorProtowith:#type_descriptor— resolves message/enum fields to theirMessageDescriptor/EnumDescriptorvia the context (nil for scalars / types not in the request)#message?,#enum?,#group?,#scalar?#repeated?,#required?,#optional?,#proto3_optional?#oneof?,#oneof(proto3 synthetic optionals excluded)EnumValueDescriptor(EnumDescriptor#values) —#name,#number,#full_name.OneofDescriptor(MessageDescriptor#oneofs) —#name,#index,#fields(its member fields).Commentablemixin on every wrapper —#leading_comments,#trailing_comments,#comments,#source_location.How comments work
Comments live in
FileDescriptorProto.source_code_info, keyed by a numeric path into the descriptor tree, not on the descriptors.FileDescriptorwalks that tree once and builds an identity-keyed map from each raw descriptor proto to itsSourceCodeInfo::Location; wrappers reach their file via a uniform#fileaccessor and look themselves up. Empty comments normalize tonil.Detached comments are intentionally not exposed: per protoc they appear before "but [are] not connected to" the element (the author separated them with a blank line), so they are file organization (section headers/notes) rather than documentation of any element.
Notes / minor breaking changes
Internal constructor signatures gained a
contextargument (MessageDescriptor.new(descriptor, parent, context)). These wrappers are constructed internally, not part of the documented plugin API, but flagging it since this is pre-1.0.Testing
CommentEventmessage with a oneof, plus comments) and regenerated viabin/fixtures.bin/rake(test + rubocop): 69 runs, 172 assertions, 0 failures, rubocop clean.