vortex_flatbuffers/
lib.rs

1//! A contiguously serialized Vortex array.
2//!
3//! See the `vortex-file` crate for non-contiguous serialization.
4
5#[cfg(feature = "array")]
6#[allow(clippy::all)]
7#[allow(clippy::derive_partial_eq_without_eq)]
8#[allow(clippy::many_single_char_names)]
9#[allow(clippy::unwrap_used)]
10#[allow(clippy::borrow_as_ptr)]
11#[allow(dead_code)]
12// TODO(robert): Remove once we can update toolchain
13#[allow(unknown_lints)]
14#[allow(mismatched_lifetime_syntaxes)]
15#[allow(non_snake_case)]
16#[allow(non_camel_case_types)]
17#[allow(unsafe_op_in_unsafe_fn)]
18#[allow(unused_imports)]
19#[allow(unused_lifetimes)]
20#[allow(unused_qualifications)]
21#[rustfmt::skip]
22#[path = "./generated/array.rs"]
23/// A serialized array without its buffer (i.e. data).
24///
25/// `array.fbs`:
26/// ```flatbuffers
27#[doc = include_str!("../flatbuffers/vortex-array/array.fbs")]
28/// ```
29pub mod array;
30
31#[cfg(feature = "dtype")]
32#[allow(clippy::all)]
33#[allow(clippy::derive_partial_eq_without_eq)]
34#[allow(clippy::many_single_char_names)]
35#[allow(clippy::unwrap_used)]
36#[allow(clippy::borrow_as_ptr)]
37#[allow(dead_code)]
38// TODO(robert): Remove once we can update toolchain
39#[allow(unknown_lints)]
40#[allow(mismatched_lifetime_syntaxes)]
41#[allow(non_snake_case)]
42#[allow(non_camel_case_types)]
43#[allow(unsafe_op_in_unsafe_fn)]
44#[allow(unused_imports)]
45#[allow(unused_lifetimes)]
46#[allow(unused_qualifications)]
47#[rustfmt::skip]
48#[path = "./generated/dtype.rs"]
49/// A serialized data type.
50///
51/// `dtype.fbs`:
52/// ```flatbuffers
53#[doc = include_str!("../flatbuffers/vortex-dtype/dtype.fbs")]
54/// ```
55pub mod dtype;
56
57#[cfg(feature = "file")]
58#[allow(clippy::all)]
59#[allow(clippy::derive_partial_eq_without_eq)]
60#[allow(clippy::many_single_char_names)]
61#[allow(clippy::unwrap_used)]
62#[allow(clippy::borrow_as_ptr)]
63#[allow(dead_code)]
64// TODO(robert): Remove once we can update toolchain
65#[allow(unknown_lints)]
66#[allow(mismatched_lifetime_syntaxes)]
67#[allow(non_snake_case)]
68#[allow(non_camel_case_types)]
69#[allow(unsafe_op_in_unsafe_fn)]
70#[allow(unused_imports)]
71#[allow(unused_lifetimes)]
72#[allow(unused_qualifications)]
73#[rustfmt::skip]
74#[path = "./generated/footer.rs"]
75/// A file format footer containing a serialized `vortex-file` Layout.
76///
77/// `footer.fbs`:
78/// ```flatbuffers
79#[doc = include_str!("../flatbuffers/vortex-file/footer.fbs")]
80/// ```
81pub mod footer;
82
83#[cfg(feature = "layout")]
84#[allow(clippy::all)]
85#[allow(clippy::derive_partial_eq_without_eq)]
86#[allow(clippy::many_single_char_names)]
87#[allow(clippy::unwrap_used)]
88#[allow(clippy::borrow_as_ptr)]
89#[allow(dead_code)]
90// TODO(robert): Remove once we can update toolchain
91#[allow(unknown_lints)]
92#[allow(mismatched_lifetime_syntaxes)]
93#[allow(non_snake_case)]
94#[allow(non_camel_case_types)]
95#[allow(unsafe_op_in_unsafe_fn)]
96#[allow(unused_imports)]
97#[allow(unused_lifetimes)]
98#[allow(unused_qualifications)]
99#[rustfmt::skip]
100#[path = "./generated/layout.rs"]
101/// A serialized sequence of arrays, each with its buffers.
102///
103/// `layout.fbs`:
104/// ```flatbuffers
105#[doc = include_str!("../flatbuffers/vortex-layout/layout.fbs")]
106/// ```
107pub mod layout;
108
109#[cfg(feature = "ipc")]
110#[allow(clippy::all)]
111#[allow(clippy::derive_partial_eq_without_eq)]
112#[allow(clippy::many_single_char_names)]
113#[allow(clippy::unwrap_used)]
114#[allow(clippy::borrow_as_ptr)]
115#[allow(dead_code)]
116// TODO(robert): Remove once we can update toolchain
117#[allow(unknown_lints)]
118#[allow(mismatched_lifetime_syntaxes)]
119#[allow(non_snake_case)]
120#[allow(non_camel_case_types)]
121#[allow(unsafe_op_in_unsafe_fn)]
122#[allow(unused_imports)]
123#[allow(unused_lifetimes)]
124#[allow(unused_qualifications)]
125#[rustfmt::skip]
126#[path = "./generated/message.rs"]
127/// A serialized sequence of arrays, each with its buffers.
128///
129/// `message.fbs`:
130/// ```flatbuffers
131#[doc = include_str!("../flatbuffers/vortex-serde/message.fbs")]
132/// ```
133pub mod message;
134
135use flatbuffers::{FlatBufferBuilder, Follow, InvalidFlatbuffer, Verifiable, WIPOffset, root};
136use vortex_buffer::{ByteBuffer, ConstByteBuffer};
137
138/// We define a const-aligned byte buffer for flatbuffers with 8-byte alignment.
139///
140/// This is based on the assumption that the maximum primitive type is 8 bytes.
141/// See: <https://groups.google.com/g/flatbuffers/c/PSgQeWeTx_g>
142pub type FlatBuffer = ConstByteBuffer<8>;
143
144pub trait FlatBufferRoot {}
145
146pub trait ReadFlatBuffer: Sized {
147    type Source<'a>: Verifiable + Follow<'a>;
148    type Error: From<InvalidFlatbuffer>;
149
150    fn read_flatbuffer<'buf>(
151        fb: &<Self::Source<'buf> as Follow<'buf>>::Inner,
152    ) -> Result<Self, Self::Error>;
153
154    fn read_flatbuffer_bytes<'buf>(bytes: &'buf [u8]) -> Result<Self, Self::Error>
155    where
156        <Self as ReadFlatBuffer>::Source<'buf>: 'buf,
157    {
158        let fb = root::<Self::Source<'buf>>(bytes)?;
159        Self::read_flatbuffer(&fb)
160    }
161}
162
163pub trait WriteFlatBuffer {
164    type Target<'a>;
165
166    fn write_flatbuffer<'fb>(
167        &self,
168        fbb: &mut FlatBufferBuilder<'fb>,
169    ) -> WIPOffset<Self::Target<'fb>>;
170}
171
172pub trait WriteFlatBufferExt: WriteFlatBuffer + FlatBufferRoot {
173    /// Write the flatbuffer into a [`FlatBuffer`].
174    fn write_flatbuffer_bytes(&self) -> FlatBuffer;
175}
176
177impl<F: WriteFlatBuffer + FlatBufferRoot> WriteFlatBufferExt for F {
178    fn write_flatbuffer_bytes(&self) -> FlatBuffer {
179        let mut fbb = FlatBufferBuilder::new();
180        let root_offset = self.write_flatbuffer(&mut fbb);
181        fbb.finish_minimal(root_offset);
182        let (vec, start) = fbb.collapse();
183        let end = vec.len();
184        FlatBuffer::align_from(ByteBuffer::from(vec).slice(start..end))
185    }
186}