Skip to content

codegen: top-level message named Option shadows Rust prelude #64

@th0114nd

Description

@th0114nd

Summary

When a proto file defines a top-level message Option, the generated pub struct Option shadows the Rust prelude Option<T>. Other generated code in the same package that uses Option<T> for oneof fields fails to compile:

error[E0107]: struct takes 0 generic arguments but 1 generic argument was supplied
  --> session.rs:517:26
    |
517 |     pub session_context: Option<__buffa::oneof::session_context::SessionContext>,
    |                          ^^^^^^ expected 0 generic arguments
    |
note: struct defined here, with 0 generic parameters
  --> message.rs:4427:12
    |
4427 | pub struct Option {
    |            ^^^^^^

Relation to #32 and #39

This is distinct from #32 (ancillary type name collisions, fixed by __buffa:: namespacing in #62) and #39 (qualifying Option in nested scopes). The __buffa:: fix in #62 handles collisions between generated ancillary names and user proto names. This bug is about a user proto name (message Option) shadowing a Rust prelude name, which affects the generated field type annotations for sibling messages in the same package.

Possible fix

The generated field types could use ::core::option::Option<T> instead of bare Option<T> unconditionally (or when a prelude-shadowing name is detected in the file set).

Reproduction

// option.proto
syntax = "proto3";
package example;

message Option {
  string label = 1;
}

message Container {
  oneof choice {
    string a = 1;
    int32 b = 2;
  }
}
// build.rs
fn main() {
    buffa_build::Config::new()
        .files(&["option.proto"])
        .includes(&["."])
        .out_dir("src/generated")
        .include_file("mod.rs")
        .compile()
        .unwrap();
}

The Container struct's oneof field will reference Option<...> which resolves to the generated Option struct instead of core::option::Option.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions