rustbinary 0.1.1

A bounded Serde binary codec with adaptive frames, zero-allocation paths, schema evolution, and authenticated pipelines
Documentation
use rustbinary::{Error, Fingerprint as _, Reflect as _, StaticSize as _, TypeShape};
use serde::{Deserialize, Serialize};

#[derive(
    Debug,
    PartialEq,
    Serialize,
    Deserialize,
    rustbinary::Fingerprint,
    rustbinary::Reflect,
    rustbinary::StaticSize,
)]
struct Header {
    online: bool,
    partition: u16,
    coordinates: [i32; 2],
}

#[derive(Serialize, Deserialize, rustbinary::Fingerprint)]
struct ReorderedHeader {
    partition: u16,
    online: bool,
    coordinates: [i32; 2],
}

#[derive(Debug, PartialEq, rustbinary::BitPacked)]
struct PackedFlags {
    online: bool,
    #[bits = 3]
    priority: u8,
    #[bits = 12]
    sequence: u16,
}

fn main() -> rustbinary::Result<()> {
    let value = Header {
        online: true,
        partition: 17,
        coordinates: [-4, 9],
    };
    let base = rustbinary::options().with_limit(4096);

    assert!(base.serialize(&value)?.len() <= Header::MAX_SIZE);
    assert_ne!(
        Header::fingerprint(base),
        ReorderedHeader::fingerprint(base)
    );
    if let TypeShape::Struct(fields) = Header::SHAPE {
        assert_eq!(fields.len(), 3);
        assert_eq!(fields[1].name, "partition");
        assert_eq!(fields[1].type_name, "u16");
    }

    let framed = base.with_fingerprint().serialize(&value)?;
    assert_eq!(
        base.with_fingerprint().deserialize::<Header>(&framed)?,
        value
    );
    assert!(matches!(
        base.with_fingerprint()
            .deserialize::<ReorderedHeader>(&framed),
        Err(Error::SchemaMismatch { .. })
    ));

    let flags = PackedFlags {
        online: true,
        priority: 5,
        sequence: 2047,
    };
    let packed = base.with_bit_packing().serialize(&flags)?;
    assert_eq!(packed.len(), 2);
    assert_eq!(
        base.with_bit_packing()
            .deserialize::<PackedFlags>(&packed)?,
        flags
    );

    Ok(())
}