reifydb_compression/strategy/
none.rs1use postcard::{from_bytes, to_stdvec};
5use reifydb_core::value::column::{
6 compressed::{CompressedColumn, CompressionType},
7 data::ColumnData,
8};
9use reifydb_type::{
10 Result,
11 error::{Error, TypeError},
12};
13
14use crate::ColumnCompressor;
15
16pub struct NoneCompressor {}
17
18impl ColumnCompressor for NoneCompressor {
19 fn compress(&self, data: &ColumnData) -> Result<CompressedColumn> {
20 let serialized = to_stdvec(data).map_err(|e| -> Error {
21 TypeError::SerdeSerialize {
22 message: e.to_string(),
23 }
24 .into()
25 })?;
26
27 let uncompressed_size = serialized.len();
28
29 Ok(CompressedColumn {
30 data: serialized,
31 compression: CompressionType::None,
32 uncompressed_size,
33 none_count: data.none_count(),
34 row_count: data.len(),
35 })
36 }
37
38 fn decompress(&self, compressed: &CompressedColumn) -> Result<ColumnData> {
39 assert_eq!(compressed.compression, CompressionType::None);
40
41 let result: ColumnData = from_bytes(&compressed.data).map_err(|e| -> Error {
42 TypeError::SerdeDeserialize {
43 message: e.to_string(),
44 }
45 .into()
46 })?;
47
48 Ok(result)
49 }
50}
51
52#[cfg(test)]
53pub mod tests {
54 use reifydb_core::value::column::{compressed::CompressionType, data::ColumnData};
55
56 use super::*;
57
58 #[test]
59 fn test_compress_decompress_bool() {
60 let compressor = NoneCompressor {};
61
62 let data = ColumnData::bool_optional([Some(true), Some(false), None, Some(true), None]);
63
64 let compressed = compressor.compress(&data).unwrap();
65 assert_eq!(compressed.compression, CompressionType::None);
66 assert_eq!(compressed.row_count, 5);
67 assert_eq!(compressed.none_count, 2);
68 assert_eq!(compressed.uncompressed_size, compressed.data.len());
69
70 let decompressed = compressor.decompress(&compressed).unwrap();
71 assert_eq!(data, decompressed);
72 }
73
74 #[test]
75 fn test_compress_decompress_int() {
76 let compressor = NoneCompressor {};
77
78 let data = ColumnData::int4_optional([
79 Some(42),
80 Some(-100),
81 None,
82 Some(0),
83 Some(i32::MAX),
84 Some(i32::MIN),
85 ]);
86
87 let compressed = compressor.compress(&data).unwrap();
88 assert_eq!(compressed.compression, CompressionType::None);
89 assert_eq!(compressed.row_count, 6);
90 assert_eq!(compressed.none_count, 1);
91
92 let decompressed = compressor.decompress(&compressed).unwrap();
93 assert_eq!(data, decompressed);
94 }
95
96 #[test]
97 fn test_compress_decompress_string() {
98 let compressor = NoneCompressor {};
99
100 let data = ColumnData::utf8_optional([
101 Some("hello".to_string()),
102 Some("world".to_string()),
103 None,
104 Some("".to_string()),
105 Some("a very long string with special chars: çšćŽćĺ đ".to_string()),
106 ]);
107
108 let compressed = compressor.compress(&data).unwrap();
109 assert_eq!(compressed.compression, CompressionType::None);
110 assert_eq!(compressed.row_count, 5);
111 assert_eq!(compressed.none_count, 1);
112
113 let decompressed = compressor.decompress(&compressed).unwrap();
114 assert_eq!(data, decompressed);
115 }
116
117 #[test]
118 fn test_empty_column() {
119 let compressor = NoneCompressor {};
120
121 let data = ColumnData::int4_with_capacity(0);
122
123 let compressed = compressor.compress(&data).unwrap();
124 assert_eq!(compressed.row_count, 0);
125 assert_eq!(compressed.none_count, 0);
126
127 let decompressed = compressor.decompress(&compressed).unwrap();
128 assert_eq!(data, decompressed);
129 }
130
131 #[test]
132 fn test_all_undefined() {
133 let compressor = NoneCompressor {};
134
135 let data = ColumnData::float8_optional([None, None, None, None]);
136
137 let compressed = compressor.compress(&data).unwrap();
138 assert_eq!(compressed.row_count, 4);
139 assert_eq!(compressed.none_count, 4);
140
141 let decompressed = compressor.decompress(&compressed).unwrap();
142 assert_eq!(data, decompressed);
143 }
144
145 #[test]
146 fn test_various_numeric_types() {
147 let compressor = NoneCompressor {};
148
149 let data_i8 = ColumnData::int8_optional([Some(i64::MAX), Some(i64::MIN), None]);
150 let compressed = compressor.compress(&data_i8).unwrap();
151 let decompressed = compressor.decompress(&compressed).unwrap();
152 assert_eq!(data_i8, decompressed);
153
154 let data_u4 = ColumnData::uint4_optional([Some(u32::MAX), Some(0), None]);
155 let compressed = compressor.compress(&data_u4).unwrap();
156 let decompressed = compressor.decompress(&compressed).unwrap();
157 assert_eq!(data_u4, decompressed);
158
159 let data_f4 = ColumnData::float4_optional([Some(3.14), Some(-0.0), None, Some(f32::INFINITY)]);
160 let compressed = compressor.compress(&data_f4).unwrap();
161 let decompressed = compressor.decompress(&compressed).unwrap();
162 assert_eq!(data_f4, decompressed);
163 }
164
165 #[test]
166 fn test_round_trip_preserves_data() {
167 let compressor = NoneCompressor {};
168
169 let bool_data = ColumnData::bool([true, false, true]);
170 let compressed = compressor.compress(&bool_data).unwrap();
171 let decompressed = compressor.decompress(&compressed).unwrap();
172 assert_eq!(bool_data, decompressed);
173
174 let int_data = ColumnData::int4([1, 2, 3, 4, 5]);
175 let compressed = compressor.compress(&int_data).unwrap();
176 let decompressed = compressor.decompress(&compressed).unwrap();
177 assert_eq!(int_data, decompressed);
178
179 let string_data = ColumnData::utf8(["hello", "world", "test"]);
180 let compressed = compressor.compress(&string_data).unwrap();
181 let decompressed = compressor.decompress(&compressed).unwrap();
182 assert_eq!(string_data, decompressed);
183 }
184}