Skip to main content

MessageField

Struct MessageField 

Source
pub struct MessageField<T: Default, P = Box<T>> { /* private fields */ }
Expand description

A wrapper for optional message fields that provides transparent access to a default instance when the field is not set.

This type is used for singular message fields in generated code. The pointer type P is pluggable; see ProtoBox. Codegen emits Inline<T> by default — the message is stored directly in the parent struct (laid out as Option<T>), so size_of::<T>() is reserved whether set or not and there is no per-field heap allocation. Recursive fields and explicit opt-outs use Box<T> instead, which heap-allocates only when set. The struct’s own P = Box<T> type-parameter default applies only to a hand-written MessageField<T> (e.g. in tests), not to generated fields. Because P has a default, a standalone construction with no pinning context needs a type annotation — write let f: MessageField<Foo> = MessageField::some(x); (or MessageField::<Foo>::some(x)). In the common cases — a struct-literal field (Outer { inner: MessageField::some(x), .. }) or an assignment to a typed field — P is inferred from the target and no annotation is needed.

§Access patterns

// Reading through an unset field gives the default:
let msg = Outer::default();
assert_eq!(msg.inner.name, "");  // No unwrap needed, derefs to default

// Check if set:
if msg.inner.is_set() { ... }

// Set a value:
msg.inner = MessageField::some(Inner { name: "hello".into(), ..Default::default() });

// Clear:
msg.inner = MessageField::none();

§Construction and conversion

From conversions are the idiomatic way to populate a generated message field. They accept both a message value and an Option of one. Reading goes the other way through Deref, so a field whose message type implements DefaultInstance needs no unwrapping at all.

use buffa::MessageField;

// A value converts straight into a set field.
let field: MessageField<Person> = Person { name: "Ada".into(), id: 1 }.into();
// Reading goes through `Deref`, so no unwrapping ceremony.
assert_eq!(field.name, "Ada");

// An `Option` converts too, so `map` chains land directly in the field.
let field: MessageField<Person> = Some("Grace")
    .map(|name| Person { name: name.into(), id: 2 })
    .into();
assert_eq!(field.id, 2);

// An unset field derefs to the default instance rather than panicking.
let empty: MessageField<Person> = None.into();
assert!(empty.is_unset());
assert_eq!(empty.name, "");

Implementations§

Source§

impl<T: Default, P: ProtoBox<T>> MessageField<T, P>

Source

pub const fn none() -> Self

Create a MessageField with no value set.

Source

pub fn some(value: T) -> Self

Create a MessageField with a value.

Source

pub fn from_pointer(value: P) -> Self

Create a MessageField from an already-constructed pointer, without unwrapping and re-boxing the value.

Prefer this over MessageField::some(p.into_inner()) when you already hold a P — for an inline pointer (e.g. SmallBox) the latter would move the value out and re-store it, defeating the point. The generic counterpart to from_box (which is Box-only).

Source

pub fn is_set(&self) -> bool

Returns true if the field has a value set.

Source

pub fn is_unset(&self) -> bool

Returns true if the field has no value set.

Source

pub fn as_option(&self) -> Option<&T>

Get a reference to the inner value, or None if unset.

Source

pub fn as_option_mut(&mut self) -> Option<&mut T>

Get a mutable reference to the inner value, or None if unset.

Source

pub fn take(&mut self) -> Option<T>

Take the inner value, leaving the field unset.

Source

pub fn get_or_insert_default(&mut self) -> &mut T

Get a mutable reference to the value, initializing to the default if unset.

Source

pub fn modify<F: FnOnce(&mut T)>(&mut self, f: F)

Call f with a mutable reference to the inner value, initializing to the default if the field is currently unset.

This is the ergonomic write counterpart to the transparent read provided by Deref. Instead of calling get_or_insert_default once per assignment:

msg.address.get_or_insert_default().street = "123 Main St".into();
msg.address.get_or_insert_default().city   = "Springfield".into();

use modify to initialize the field once and set all sub-fields in the closure:

msg.address.modify(|a| {
    a.street = "123 Main St".into();
    a.city   = "Springfield".into();
});
Source

pub fn into_option(self) -> Option<T>

Consume the field, returning Some(T) if set or None if unset.

This unboxes the inner value. For in-place extraction that leaves the field unset without consuming the enclosing struct, see take.

Source

pub fn map<U, F: FnOnce(T) -> U>(self, f: F) -> Option<U>

Consume the field, applying f to the inner value if set.

Mirrors Option::map. Equivalent in effect to into_option.map(f), but reads as if the field were a plain Option. The motivating case is converting an optional submessage into a differently-typed Option when mapping a generated struct to a domain type:

// Before: value.shoulder_entity_left.into_option().map(Into::into)
shoulder_entity_left: value.shoulder_entity_left.map(Into::into),

With map(Into::into) the target type must be inferable from context (a typed struct field, annotated let, or function return); otherwise name the conversion (map(Domain::from)). To map without consuming the field, use as_option.map(...).

Source

pub fn unwrap(self) -> T

Consume the field, returning the inner value.

Equivalent in effect to into_option().unwrap(), with a clearer panic message. Prefer ok_or / ok_or_else when an unset field should produce an error rather than a panic.

§Panics

Panics if the field is unset.

Source

pub fn expect(self, msg: &str) -> T

Consume the field, returning the inner value, with a custom panic message if unset.

Mirrors Option::expect. Prefer ok_or / ok_or_else when an unset field should produce an error rather than a panic.

§Panics

Panics with msg if the field is unset.

Source

pub fn ok_or<E>(self, err: E) -> Result<T, E>

Consume the field, returning Ok(T) if set or Err(err) if unset.

Mirrors Option::ok_or. Useful for enforcing presence of semantically-required fields that the proto schema leaves optional:

let cmd = request.normalized_command.ok_or(Error::MissingCommand)?;
Source

pub fn ok_or_else<E, F: FnOnce() -> E>(self, err: F) -> Result<T, E>

Consume the field, returning Ok(T) if set or Err(err()) if unset.

Mirrors Option::ok_or_else. The closure is only called if the field is unset, so use this over ok_or when constructing the error is non-trivial:

let cmd = request.normalized_command.ok_or_else(|| {
    ConnectError::invalid_argument("missing normalized_command in request")
})?;
Source§

impl<T: Default> MessageField<T, Box<T>>

Source

pub fn from_box(value: Box<T>) -> Self

Create a MessageField from a boxed value.

Specific to Box<T> (the struct’s P = Box<T> type-parameter default, used for recursive fields and explicit opt-outs); inline-backed generated fields use some or from_pointer instead.

Trait Implementations§

Source§

impl<'a, T: Default + Arbitrary<'a>, P: ProtoBox<T>> Arbitrary<'a> for MessageField<T, P>

Available on crate feature arbitrary only.
Source§

fn arbitrary(u: &mut Unstructured<'a>) -> Result<Self>

Generate an arbitrary value of Self from the given unstructured data. Read more
Source§

fn arbitrary_take_rest(u: Unstructured<'a>) -> Result<Self, Error>

Generate an arbitrary value of Self from the entirety of the given unstructured data. Read more
Source§

fn size_hint(depth: usize) -> (usize, Option<usize>)

Get a size hint for how many bytes out of an Unstructured this type needs to construct itself. Read more
Source§

fn try_size_hint( depth: usize, ) -> Result<(usize, Option<usize>), MaxRecursionReached>

Get a size hint for how many bytes out of an Unstructured this type needs to construct itself. Read more
Source§

impl<T: Default + Clone, P: ProtoBox<T> + Clone> Clone for MessageField<T, P>

Source§

fn clone(&self) -> Self

Returns a duplicate of the value. Read more
1.0.0 (const: unstable) · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl<T: Default + Debug, P: ProtoBox<T>> Debug for MessageField<T, P>

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl<T: Default, P: ProtoBox<T>> Default for MessageField<T, P>

Source§

fn default() -> Self

Returns the “default value” for a type. Read more
Source§

impl<T: DefaultInstance, P: ProtoBox<T>> Deref for MessageField<T, P>

Source§

type Target = T

The resulting type after dereferencing.
Source§

fn deref(&self) -> &T

Dereferences the value.
Source§

impl<'de, T: Default + Deserialize<'de>, P: ProtoBox<T>> Deserialize<'de> for MessageField<T, P>

Available on crate feature json only.
Source§

fn deserialize<D: Deserializer<'de>>(d: D) -> Result<Self, D::Error>

Deserialize this value from the given Serde deserializer. Read more
Source§

impl<T: DefaultInstance + Eq + PartialEq, P: ProtoBox<T>> Eq for MessageField<T, P>

Source§

impl<T: Default, P: ProtoBox<T>> From<MessageField<T, P>> for Option<T>

Source§

fn from(field: MessageField<T, P>) -> Self

Unbox a MessageField into an Option<T>; equivalent to MessageField::into_option.

Source§

impl<T: Default, P: ProtoBox<T>> From<Option<T>> for MessageField<T, P>

Source§

fn from(opt: Option<T>) -> Self

Converts to this type from the input type.
Source§

impl<T: Default, P: ProtoBox<T>> From<T> for MessageField<T, P>

Source§

fn from(value: T) -> Self

Converts to this type from the input type.
Source§

impl<T: DefaultInstance + PartialEq, P: ProtoBox<T>> PartialEq for MessageField<T, P>

Source§

fn eq(&self, other: &Self) -> bool

Equality operator ==. Read more
1.0.0 (const: unstable) · Source§

fn ne(&self, other: &Rhs) -> bool

Inequality operator !=. Read more
Source§

impl<T: Default + Serialize, P: ProtoBox<T>> Serialize for MessageField<T, P>

Available on crate feature json only.
Source§

fn serialize<S: Serializer>(&self, s: S) -> Result<S::Ok, S::Error>

Serialize this value into the given Serde serializer. Read more

Auto Trait Implementations§

§

impl<T, P> Freeze for MessageField<T, P>
where P: Freeze,

§

impl<T, P> RefUnwindSafe for MessageField<T, P>

§

impl<T, P> Send for MessageField<T, P>
where P: Send, T: Send,

§

impl<T, P> Sync for MessageField<T, P>
where P: Sync, T: Sync,

§

impl<T, P> Unpin for MessageField<T, P>
where P: Unpin, T: Unpin,

§

impl<T, P> UnsafeUnpin for MessageField<T, P>
where P: UnsafeUnpin,

§

impl<T, P> UnwindSafe for MessageField<T, P>
where P: UnwindSafe, T: UnwindSafe,

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> DeserializeOwned for T
where T: for<'de> Deserialize<'de>,

Source§

impl<Q, K> Equivalent<K> for Q
where Q: Eq + ?Sized, K: Borrow<Q> + ?Sized,

Source§

fn equivalent(&self, key: &K) -> bool

Checks if this value is equivalent to the given key. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<P, T> Receiver for P
where P: Deref<Target = T> + ?Sized, T: ?Sized,

Source§

type Target = T

🔬This is a nightly-only experimental API. (arbitrary_self_types)
The target type on which the method may be called.
Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.