1#![cfg_attr(docsrs, doc(cfg(feature = "bincode")))]
2#![cfg(feature = "bincode")]
3
4pub extern crate bincode as original;
7
8use bincode::{Decode, Encode};
9use bincode::config::{Configuration, Config, BigEndian, LittleEndian, Varint, Fixint, Limit, NoLimit};
10use bincode::error::{DecodeError, EncodeError};
11#[cfg(feature = "bincode-serde")]
12use serde::ser::Serialize;
13#[cfg(feature = "bincode-serde")]
14use serde::de::DeserializeOwned;
15use singlefile::FileFormat;
16use thiserror::Error;
17
18use std::io::{Read, Write};
19
20#[derive(Debug, Error)]
22pub enum BincodeError {
23 #[error(transparent)]
25 EncodeError(#[from] EncodeError),
26 #[error(transparent)]
28 DecodeError(#[from] DecodeError)
29}
30
31#[derive(Debug, Clone, Copy, Default)]
35pub struct Bincode<E = LittleEndian, I = Varint, L = NoLimit> {
36 pub configuration: Configuration<E, I, L>
38}
39
40impl<T, E, I, L> FileFormat<T> for Bincode<E, I, L>
41where T: Decode<()> + Encode, Configuration<E, I, L>: Config {
42 type FormatError = BincodeError;
43
44 #[inline]
45 fn from_reader<R: Read>(&self, mut reader: R) -> Result<T, Self::FormatError> {
46 Ok(bincode::decode_from_std_read(&mut reader, self.configuration)?)
47 }
48
49 #[inline]
50 fn from_buffer(&self, buf: &[u8]) -> Result<T, Self::FormatError> {
51 Ok(bincode::decode_from_slice(buf, self.configuration)?.0)
52 }
53
54 #[inline]
55 fn to_writer<W: Write>(&self, mut writer: W, value: &T) -> Result<(), Self::FormatError> {
56 bincode::encode_into_std_write(value, &mut writer, self.configuration)?;
57 Ok(())
58 }
59
60 #[inline]
61 fn to_buffer(&self, value: &T) -> Result<Vec<u8>, Self::FormatError> {
62 Ok(bincode::encode_to_vec(value, self.configuration)?)
63 }
64}
65
66impl<E, I, L> Bincode<E, I, L> {
67 #[inline]
69 pub const fn new(configuration: Configuration<E, I, L>) -> Self {
70 Bincode { configuration }
71 }
72
73 #[inline]
77 pub const fn with_big_endian(self) -> Bincode<BigEndian, I, L> {
78 Bincode { configuration: self.configuration.with_big_endian() }
79 }
80
81 #[inline]
85 pub const fn with_little_endian(self) -> Bincode<LittleEndian, I, L> {
86 Bincode { configuration: self.configuration.with_little_endian() }
87 }
88
89 #[inline]
93 pub const fn with_variable_int_encoding(self) -> Bincode<E, Varint, L> {
94 Bincode { configuration: self.configuration.with_variable_int_encoding() }
95 }
96
97 #[inline]
101 pub const fn with_fixed_int_encoding(self) -> Bincode<E, Fixint, L> {
102 Bincode { configuration: self.configuration.with_fixed_int_encoding() }
103 }
104
105 #[inline]
109 pub const fn with_limit<const N: usize>(self) -> Bincode<E, I, Limit<N>> {
110 Bincode { configuration: self.configuration.with_limit() }
111 }
112
113 #[inline]
117 pub const fn with_no_limit(self) -> Bincode<E, I, NoLimit> {
118 Bincode { configuration: self.configuration.with_no_limit() }
119 }
120}
121
122#[cfg(feature = "bincode-serde")]
126#[derive(Debug, Clone, Copy, Default)]
127pub struct BincodeSerde<E = LittleEndian, I = Varint, L = NoLimit> {
128 pub configuration: Configuration<E, I, L>
130}
131
132#[cfg(feature = "bincode-serde")]
133impl<T, E, I, L> FileFormat<T> for BincodeSerde<E, I, L>
134where T: DeserializeOwned + Serialize, Configuration<E, I, L>: Config {
135 type FormatError = BincodeError;
136
137 #[inline]
138 fn from_reader<R: Read>(&self, mut reader: R) -> Result<T, Self::FormatError> {
139 Ok(bincode::serde::decode_from_std_read(&mut reader, self.configuration)?)
140 }
141
142 #[inline]
143 fn from_buffer(&self, buf: &[u8]) -> Result<T, Self::FormatError> {
144 Ok(bincode::serde::decode_from_slice(buf, self.configuration)?.0)
145 }
146
147 #[inline]
148 fn to_writer<W: Write>(&self, mut writer: W, value: &T) -> Result<(), Self::FormatError> {
149 bincode::serde::encode_into_std_write(value, &mut writer, self.configuration)?;
150 Ok(())
151 }
152
153 #[inline]
154 fn to_buffer(&self, value: &T) -> Result<Vec<u8>, Self::FormatError> {
155 Ok(bincode::serde::encode_to_vec(value, self.configuration)?)
156 }
157}
158
159#[cfg(feature = "bincode-serde")]
160impl<E, I, L> BincodeSerde<E, I, L> {
161 #[inline]
163 pub const fn new(configuration: Configuration<E, I, L>) -> Self {
164 BincodeSerde { configuration }
165 }
166
167 #[inline]
171 pub const fn with_big_endian(self) -> BincodeSerde<BigEndian, I, L> {
172 BincodeSerde { configuration: self.configuration.with_big_endian() }
173 }
174
175 #[inline]
179 pub const fn with_little_endian(self) -> BincodeSerde<LittleEndian, I, L> {
180 BincodeSerde { configuration: self.configuration.with_little_endian() }
181 }
182
183 #[inline]
187 pub const fn with_variable_int_encoding(self) -> BincodeSerde<E, Varint, L> {
188 BincodeSerde { configuration: self.configuration.with_variable_int_encoding() }
189 }
190
191 #[inline]
195 pub const fn with_fixed_int_encoding(self) -> BincodeSerde<E, Fixint, L> {
196 BincodeSerde { configuration: self.configuration.with_fixed_int_encoding() }
197 }
198
199 #[inline]
203 pub const fn with_limit<const N: usize>(self) -> BincodeSerde<E, I, Limit<N>> {
204 BincodeSerde { configuration: self.configuration.with_limit() }
205 }
206
207 #[inline]
211 pub const fn with_no_limit(self) -> BincodeSerde<E, I, NoLimit> {
212 BincodeSerde { configuration: self.configuration.with_no_limit() }
213 }
214}
215
216#[cfg_attr(docsrs, doc(cfg(feature = "compression")))]
219#[cfg(feature = "compression")]
220pub type CompressedBincode<C, E = LittleEndian, I = Varint, L = NoLimit>
221 = crate::compression::Compressed<C, Bincode<E, I, L>>;
222
223#[cfg_attr(docsrs, doc(cfg(all(feature = "compression", feature = "bincode-serde"))))]
226#[cfg(all(feature = "compression", feature = "bincode-serde"))]
227pub type CompressedBincodeSerde<C, E = LittleEndian, I = Varint, L = NoLimit>
228 = crate::compression::Compressed<C, Bincode<E, I, L>>;