use flatbuffers::FlatBufferBuilder;
use flatbuffers::Follow;
use flatbuffers::InvalidFlatbuffer;
use flatbuffers::Verifiable;
use flatbuffers::WIPOffset;
use flatbuffers::root;
use vortex_buffer::ByteBuffer;
use vortex_buffer::ConstByteBuffer;
use vortex_error::VortexResult;
pub type FlatBuffer = ConstByteBuffer<8>;
pub trait FlatBufferRoot {}
pub trait ReadFlatBuffer: Sized {
type Source<'a>: Verifiable + Follow<'a>;
type Error: From<InvalidFlatbuffer>;
fn read_flatbuffer<'buf>(
fb: &<Self::Source<'buf> as Follow<'buf>>::Inner,
) -> Result<Self, Self::Error>;
fn read_flatbuffer_bytes<'buf>(bytes: &'buf [u8]) -> Result<Self, Self::Error>
where
<Self as ReadFlatBuffer>::Source<'buf>: 'buf,
{
let fb = root::<Self::Source<'buf>>(bytes)?;
Self::read_flatbuffer(&fb)
}
}
pub trait WriteFlatBuffer {
type Target<'a>;
fn write_flatbuffer<'fb>(
&self,
fbb: &mut FlatBufferBuilder<'fb>,
) -> VortexResult<WIPOffset<Self::Target<'fb>>>;
}
pub trait WriteFlatBufferExt: WriteFlatBuffer + FlatBufferRoot {
fn write_flatbuffer_bytes(&self) -> VortexResult<FlatBuffer>;
}
impl<F: WriteFlatBuffer + FlatBufferRoot> WriteFlatBufferExt for F {
fn write_flatbuffer_bytes(&self) -> VortexResult<FlatBuffer> {
let mut fbb = FlatBufferBuilder::new();
let root_offset = self.write_flatbuffer(&mut fbb)?;
fbb.finish_minimal(root_offset);
let (vec, start) = fbb.collapse();
let end = vec.len();
Ok(FlatBuffer::align_from(
ByteBuffer::from(vec).slice(start..end),
))
}
}