Skip to main content

FrameDecoder

Struct FrameDecoder 

Source
pub struct FrameDecoder { /* private fields */ }
Expand description

Reassembles newline-delimited frames from arbitrarily chopped-up bytes.

Feed it whatever a read returned with push, then take complete frames out with next_frame until it says None, which means “not yet” rather than “nothing more”.

The cursor (buffered) matters for reading these two in order. A caller that pushes without draining accumulates complete frames as well as the partial one, and the buffer is then bounded by the limit plus the chunk it was given — never by the peer’s frame size. The stdio adapter reads a chunk, pushes it, and drains it before reading again.

§Examples

use protocol_droid::domain::{FrameDecoder, MaxFrameSize};

let mut decoder = FrameDecoder::new(MaxFrameSize::new(1024)?);
decoder.push(b"first\nsecond\n")?;

assert_eq!(decoder.next_frame()?, Some("first"));
assert_eq!(decoder.next_frame()?, Some("second"));
assert_eq!(decoder.next_frame()?, None);
assert!(decoder.is_empty());

Implementations§

Source§

impl FrameDecoder

Source

pub const fn new(limit: MaxFrameSize) -> Self

A decoder that refuses frames larger than limit.

No default: see the module docs.

Source

pub const fn limit(&self) -> MaxFrameSize

The limit this decoder was built with.

Source

pub const fn buffered(&self) -> usize

Bytes read and not yet handed out, including a partially-read frame.

Exposed so a caller — or a test — can see the decoder’s own footprint. It is bounded by the limit plus the size of the last chunk pushed, and is not a function of how large a frame the peer chose to send.

Source

pub const fn is_empty(&self) -> bool

Whether every frame pushed so far has been taken.

Source

pub fn push(&mut self, bytes: &[u8]) -> Result<(), FramingError>

Adds bytes read from the peer.

The frame in progress may be split anywhere, including inside a multi-byte UTF-8 sequence — nothing here decodes until a frame is complete, so a character is never truncated by a read boundary.

§Errors

FramingError::FrameTooLarge when the bytes after the last terminator would push the frame in progress past the limit. The check runs before those bytes are buffered, so the decoder’s footprint is unaffected and the decoder is left exactly as it was.

Source

pub fn next_frame(&mut self) -> Result<Option<&str>, FramingError>

Takes the next complete frame, or None if the terminator has not arrived.

The returned &str borrows the read buffer and is valid until the next push or next_frame. A caller that needs to keep a frame past that point copies it; the copy is then at the call site, where it is visible, rather than hidden inside a type that allocates for everyone.

§Errors

FramingError::NotUtf8 when the frame’s bytes are not UTF-8. The offending frame is dropped, so a caller that chooses to carry on reads the next frame instead of being handed the same bad one for ever. A transport will normally close on this error, because a peer that emits a non-UTF-8 frame has said something about itself; the discard is here so that a caller which decides to continue is not trapped in a loop.

Trait Implementations§

Source§

impl Clone for FrameDecoder

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 Debug for FrameDecoder

Source§

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

Formats the value using the given formatter. Read more

Auto Trait Implementations§

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<ST, DT> CastableFrom<ST, Initialized, Initialized> for DT
where ST: ?Sized, DT: ?Sized,

Source§

impl<ST, DT> CastableFrom<ST, Uninit, Uninit> for DT
where ST: ?Sized, DT: ?Sized,

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> DynClone for T
where T: Clone,

Source§

fn __clone_box(&self, _: Private) -> *mut ()

Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

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

Source§

fn from_ref(input: &T) -> T

Converts to this type from a reference to the input type.
Source§

impl<A, B, T> HttpServerConnExec<A, B> for T
where B: Body,

Source§

impl<T> Instrument for T

Source§

fn instrument(self, span: Span) -> Instrumented<Self> ⓘ

Instruments this type with the provided Span, returning an Instrumented wrapper. Read more
Source§

fn in_current_span(self) -> Instrumented<Self> ⓘ

Instruments this type with the current Span, returning an Instrumented wrapper. Read more
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<T> PolicyExt for T
where T: ?Sized,

Source§

fn and<P, B, E>(self, other: P) -> And<T, P>
where T: Sized + Policy<B, E>, P: Policy<B, E>,

Create a new Policy that returns Action::Follow only if self and other return Action::Follow. Read more
Source§

fn or<P, B, E>(self, other: P) -> Or<T, P>
where T: Sized + Policy<B, E>, P: Policy<B, E>,

Create a new Policy that returns Action::Follow if either self or other returns Action::Follow. Read more
Source§

impl<T> Read<Exclusive, BecauseExclusive> for T
where T: ?Sized,

Source§

impl<T> Same for T

Source§

type Output = T

Should always be Self
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 = !

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

fn try_from(value: U) -> Result<T, !>

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.
Source§

impl<V, T> VZip<V> for T
where V: MultiLane<T>,

Source§

fn vzip(self) -> V

Source§

impl<T> WithSubscriber for T

Source§

fn with_subscriber<S>(self, subscriber: S) -> WithDispatch<Self> ⓘ
where S: Into<Dispatch>,

Attaches the provided Subscriber to this type, returning a WithDispatch wrapper. Read more
Source§

fn with_current_subscriber(self) -> WithDispatch<Self> ⓘ

Attaches the current default Subscriber to this type, returning a WithDispatch wrapper. Read more