pub struct StreamMessage<M: HasMessageView> { /* private fields */ }Expand description
One received message on a streaming RPC, owning its decoded buffer.
StreamMessage dereferences to the buffa-generated FooOwnedView
wrapper, so message fields are read zero-copy through accessor methods
(msg.name(), msg.id()); view() gives the full view for
struct patterns and iteration, and
to_owned_message() converts for data that must
be mutated or stored. Received items can also be forwarded as-is —
StreamMessage<M> implements Encodable<M>, so an echo/relay handler
can yield them directly without re-encoding (the retained wire bytes are
reused on the proto path).
The wrapper is Send + Sync + 'static, so items can be moved into
spawned tasks or buffered freely.
§Field-name collisions
StreamMessage’s own methods (view, to_owned_message, bytes) and
the wrapper’s reserved methods take precedence over generated field
accessors. A proto field with one of those names has no accessor (buffa
emits a build warning for it); read it through the view instead:
msg.view().bytes.
Implementations§
Source§impl<M: HasMessageView> StreamMessage<M>
impl<M: HasMessageView> StreamMessage<M>
Sourcepub fn view<'b>(&'b self) -> &'b M::View<'b>
pub fn view<'b>(&'b self) -> &'b M::View<'b>
The zero-copy view of this message, borrowed from the retained buffer.
Sourcepub fn to_owned_message(&self) -> M
pub fn to_owned_message(&self) -> M
Convert to the owned message.
bytes fields are sliced zero-copy out of the retained buffer where
possible; string and repeated fields are allocated.
Trait Implementations§
Source§impl<M: HasMessageView> Clone for StreamMessage<M>where
M::ViewHandle: Clone,
impl<M: HasMessageView> Clone for StreamMessage<M>where
M::ViewHandle: Clone,
Source§impl<M: HasMessageView> Debug for StreamMessage<M>where
M::ViewHandle: Debug,
impl<M: HasMessageView> Debug for StreamMessage<M>where
M::ViewHandle: Debug,
Source§impl<M: HasMessageView> Deref for StreamMessage<M>
Per-field accessor methods (msg.name(), msg.id(), …) come from the
buffa-generated FooOwnedView wrapper via Deref.
impl<M: HasMessageView> Deref for StreamMessage<M>
Per-field accessor methods (msg.name(), msg.id(), …) come from the
buffa-generated FooOwnedView wrapper via Deref.
Source§type Target = <M as HasMessageView>::ViewHandle
type Target = <M as HasMessageView>::ViewHandle
Source§fn deref(&self) -> &M::ViewHandle
fn deref(&self) -> &M::ViewHandle
Source§impl<M> Encodable<M> for StreamMessage<M>where
M: HasMessageView + Serialize,
Forward a received message without re-encoding.
impl<M> Encodable<M> for StreamMessage<M>where
M: HasMessageView + Serialize,
Forward a received message without re-encoding.
The proto path reuses the retained wire bytes (a cheap Bytes clone); the
JSON path converts to the owned message and serializes it, matching the
owned-message Encodable impl.
§Codec asymmetry
The two codecs are deliberately not byte-for-byte symmetric. On the proto path the original wire bytes are forwarded, so unknown fields and any non-canonical encoding the peer produced are preserved. On the JSON path the message is re-serialized from the decoded form, so unknown fields are dropped and the output is canonical — the original JSON text is not retained after decoding (keeping it would mean buffering every inbound message twice), so byte-preserving JSON forwarding is not possible. Handlers that need exact relay semantics for both codecs should forward at the byte/HTTP layer instead.
Source§fn encode(&self, codec: CodecFormat) -> Result<Bytes, ConnectError>
fn encode(&self, codec: CodecFormat) -> Result<Bytes, ConnectError>
self as wire bytes for M in the requested format.