google / flatbuffers

FlatBuffers: Memory Efficient Serialization Library

Home Page:https://flatbuffers.dev/

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

[Rust] Make table builders chainable

IovoslavIovchev opened this issue · comments

The current way of using the generated builder structures in Rust does not allow for chaining the calls for setting the struct's fields and requires slightly more boilerplate. Here's a small example to illustrate my point:

let mut fbb = flatbuffers::FlatBufferBuilder::new();

let name = fbb.create_string("name");

// currently one would need to write
let mut builder = MonsterBuilder::new(&mut fbb);
builder.add_mana(1);
builder.add_hp(2);
builder.add_name(name);
// ...

let monster_1 = builder.finish();

// alternatively, what I propose is
let monster_2 = MonsterBuilderNew::new(&mut fbb)
    .mana(1)
    .hp(2)
    .name(name)
    // ...
    .finish();

I am not sure if this is by design, but it is an easy enough change, if accepted. To preserve backwards-compatibility with existing code I propose to retain the current implementation of the builders (add_*-prefixed setters) and to add new field setters, which are named as the field verbatim (e.g. mana). Here's what the new setters implementation could look like:

impl<'a: 'b, 'b> MonsterBuilderNew<'a, 'b> {
  #[inline]
  pub fn mana(mut self, mana: i16) -> Self {
    self.fbb_.push_slot::<i16>(Monster::VT_MANA, mana, 150);
    self
  }
  #[inline]
  pub fn hp(mut self, hp: i16) -> Self {
    self.fbb_.push_slot::<i16>(Monster::VT_HP, hp, 100);
    self
  }
  #[inline]
  pub fn name(mut self, name: flatbuffers::WIPOffset<&'b  str>) -> Self {
    self.fbb_.push_slot_always::<flatbuffers::WIPOffset<_>>(Monster::VT_NAME, name);
    self
  }