1use reifydb_codec::key::{
5 ByteSink, decode_u64_varint, deserializer::KeyDeserializer, encode_u64_varint, encoded::EncodedKeyBuilder,
6 serializer::KeySerializer,
7};
8use reifydb_value::{Result, value::dictionary::DictionaryId};
9
10use crate::{
11 interface::catalog::{
12 id::{IndexId, PrimaryKeyId, RingBufferId, SeriesId, TableId, ViewId},
13 shape::ShapeId,
14 vtable::VTableId,
15 },
16 return_internal_error,
17};
18
19pub fn serialize_shape_id<B: ByteSink>(shape: &ShapeId, out: &mut B) {
20 match shape {
21 ShapeId::Table(TableId(id)) => {
22 out.push(0x01);
23 encode_u64_varint(*id, out);
24 }
25 ShapeId::View(ViewId(id)) => {
26 out.push(0x02);
27 encode_u64_varint(*id, out);
28 }
29 ShapeId::TableVirtual(VTableId(id)) => {
30 out.push(0x03);
31 encode_u64_varint(*id, out);
32 }
33 ShapeId::RingBuffer(RingBufferId(id)) => {
34 out.push(0x04);
35 encode_u64_varint(*id, out);
36 }
37 ShapeId::Dictionary(DictionaryId(id)) => {
38 out.push(0x06);
39 encode_u64_varint(*id, out);
40 }
41 ShapeId::Series(SeriesId(id)) => {
42 out.push(0x07);
43 encode_u64_varint(*id, out);
44 }
45 }
46}
47
48pub fn deserialize_shape_id(input: &mut &[u8]) -> Result<ShapeId> {
49 if input.is_empty() {
50 return_internal_error!("Invalid ShapeId encoding: empty input");
51 }
52
53 let type_byte = input[0];
54 *input = &input[1..];
55 let id = decode_u64_varint(input)?;
56
57 match type_byte {
58 0x01 => Ok(ShapeId::Table(TableId(id))),
59 0x02 => Ok(ShapeId::View(ViewId(id))),
60 0x03 => Ok(ShapeId::TableVirtual(VTableId(id))),
61 0x04 => Ok(ShapeId::RingBuffer(RingBufferId(id))),
62 0x06 => Ok(ShapeId::Dictionary(DictionaryId(id))),
63 0x07 => Ok(ShapeId::Series(SeriesId(id))),
64 _ => return_internal_error!("Invalid ShapeId type byte: 0x{:02x}.", type_byte),
65 }
66}
67
68pub fn serialize_index_id<B: ByteSink>(index: &IndexId, out: &mut B) {
69 match index {
70 IndexId::Primary(PrimaryKeyId(id)) => {
71 out.push(0x01);
72 encode_u64_varint(*id, out);
73 }
74 }
75}
76
77pub fn deserialize_index_id(input: &mut &[u8]) -> Result<IndexId> {
78 if input.is_empty() {
79 return_internal_error!("Invalid IndexId encoding: empty input");
80 }
81
82 let type_byte = input[0];
83 *input = &input[1..];
84 let id = decode_u64_varint(input)?;
85
86 match type_byte {
87 0x01 => Ok(IndexId::Primary(PrimaryKeyId(id))),
88
89 _ => return_internal_error!("Invalid IndexId type byte: 0x{:02x}.", type_byte),
90 }
91}
92
93pub trait KeySerializerCatalogExt {
94 fn extend_shape_id(&mut self, shape: impl Into<ShapeId>) -> &mut Self;
95 fn extend_index_id(&mut self, index: impl Into<IndexId>) -> &mut Self;
96}
97
98impl KeySerializerCatalogExt for KeySerializer {
99 fn extend_shape_id(&mut self, shape: impl Into<ShapeId>) -> &mut Self {
100 let mut buf = Vec::new();
101 serialize_shape_id(&shape.into(), &mut buf);
102 self.extend_raw(&buf);
103 self
104 }
105
106 fn extend_index_id(&mut self, index: impl Into<IndexId>) -> &mut Self {
107 let mut buf = Vec::new();
108 serialize_index_id(&index.into(), &mut buf);
109 self.extend_raw(&buf);
110 self
111 }
112}
113
114pub trait KeyDeserializerCatalogExt {
115 fn read_shape_id(&mut self) -> Result<ShapeId>;
116 fn read_index_id(&mut self) -> Result<IndexId>;
117}
118
119impl KeyDeserializerCatalogExt for KeyDeserializer<'_> {
120 fn read_shape_id(&mut self) -> Result<ShapeId> {
121 let mut slice = self.remaining_bytes();
122 let before = slice.len();
123 let shape_id = deserialize_shape_id(&mut slice)?;
124 self.read_raw(before - slice.len())?;
125 Ok(shape_id)
126 }
127
128 fn read_index_id(&mut self) -> Result<IndexId> {
129 let mut slice = self.remaining_bytes();
130 let before = slice.len();
131 let index_id = deserialize_index_id(&mut slice)?;
132 self.read_raw(before - slice.len())?;
133 Ok(index_id)
134 }
135}
136
137pub trait EncodedKeyBuilderCatalogExt {
138 fn shape_id(self, shape: impl Into<ShapeId>) -> Self;
139 fn index_id(self, index: impl Into<IndexId>) -> Self;
140}
141
142impl EncodedKeyBuilderCatalogExt for EncodedKeyBuilder {
143 fn shape_id(self, shape: impl Into<ShapeId>) -> Self {
144 let mut buf = Vec::new();
145 serialize_shape_id(&shape.into(), &mut buf);
146 self.raw(&buf)
147 }
148
149 fn index_id(self, index: impl Into<IndexId>) -> Self {
150 let mut buf = Vec::new();
151 serialize_index_id(&index.into(), &mut buf);
152 self.raw(&buf)
153 }
154}
155
156#[cfg(test)]
157pub mod tests {
158 use reifydb_codec::key::serialize;
159
160 use super::{
161 serialize_index_id as serialize_index_id_inner, serialize_shape_id as serialize_shape_id_inner, *,
162 };
163
164 fn serialize_shape_id(shape: &ShapeId) -> Vec<u8> {
165 let mut out = Vec::new();
166 serialize_shape_id_inner(shape, &mut out);
167 out
168 }
169
170 fn serialize_index_id(index: &IndexId) -> Vec<u8> {
171 let mut out = Vec::new();
172 serialize_index_id_inner(index, &mut out);
173 out
174 }
175
176 #[test]
177 fn test_shape_id_ordering() {
178 let primitive1 = ShapeId::table(1);
179 let primitive2 = ShapeId::table(2);
180 let primitive100 = ShapeId::table(100);
181 let primitive200 = ShapeId::table(200);
182
183 let bytes1 = serialize_shape_id(&primitive1);
184 let bytes2 = serialize_shape_id(&primitive2);
185 let bytes100 = serialize_shape_id(&primitive100);
186 let bytes200 = serialize_shape_id(&primitive200);
187
188 assert!(bytes2 < bytes1, "shape(2) should be < shape(1) in bytes");
189 assert!(bytes200 < bytes100, "shape(200) should be < shape(100) in bytes");
190 assert!(bytes100 < bytes2, "shape(100) should be < shape(2) in bytes");
191 }
192
193 #[test]
194 fn test_range_boundaries() {
195 let primitive10 = ShapeId::table(10);
196 let primitive9 = primitive10.prev();
197
198 let bytes10 = serialize_shape_id(&primitive10);
199 let bytes9 = serialize_shape_id(&primitive9);
200
201 assert!(bytes9 > bytes10, "shape(9) should be > shape(10) in bytes");
202
203 let view10 = ShapeId::view(10);
204 let view9 = view10.prev();
205
206 let vbytes10 = serialize_shape_id(&view10);
207 let vbytes9 = serialize_shape_id(&view9);
208
209 assert!(vbytes9 > vbytes10, "view(9) should be > view(10) in bytes");
210
211 let virtual10 = ShapeId::vtable(10);
212 let virtual9 = virtual10.prev();
213
214 let tvbytes10 = serialize_shape_id(&virtual10);
215 let tvbytes9 = serialize_shape_id(&virtual9);
216
217 assert!(tvbytes9 > tvbytes10, "vtable(9) should be > vtable(10) in bytes");
218
219 assert_ne!(bytes10, vbytes10, "table(10) should != view(10)");
220 assert_ne!(bytes10, tvbytes10, "table(10) should != vtable(10)");
221 assert_ne!(vbytes10, tvbytes10, "view(10) should != vtable(10)");
222 assert_eq!(bytes10[0], 0x01, "table type byte should be 0x01");
223 assert_eq!(vbytes10[0], 0x02, "view type byte should be 0x02");
224 assert_eq!(tvbytes10[0], 0x03, "vtable type byte should be 0x03");
225
226 let row_key_10_100 = vec![0xFC];
227 let mut key1 = row_key_10_100.clone();
228 key1.extend(&bytes10);
229 key1.extend(&serialize(&100u64));
230
231 let mut key2 = row_key_10_100.clone();
232 key2.extend(&bytes10);
233 key2.extend(&serialize(&200u64));
234
235 let mut end_key = vec![0xFC];
236 end_key.extend(&bytes9);
237
238 assert!(key1 >= bytes10, "key1 should be >= start(primitive10)");
239 assert!(key1 < end_key, "key1 should be < end(primitive9)");
240 assert!(key2 >= bytes10, "key2 should be >= start(primitive10)");
241 assert!(key2 < end_key, "key2 should be < end(primitive9)");
242 }
243
244 #[test]
245 fn test_vtable_serialization() {
246 let virtual_primitive = ShapeId::vtable(42);
247 let bytes = serialize_shape_id(&virtual_primitive);
248 let mut slice = &bytes[..];
249 let deserialized = deserialize_shape_id(&mut slice).unwrap();
250 assert_eq!(virtual_primitive, deserialized);
251 assert!(slice.is_empty());
252
253 assert_eq!(bytes[0], 0x03);
254
255 let virtual_id = VTableId(123);
256 let primitive_from_id = ShapeId::from(virtual_id);
257 let bytes_from_id = serialize_shape_id(&primitive_from_id);
258 let mut slice = &bytes_from_id[..];
259 let deserialized_id = deserialize_shape_id(&mut slice).unwrap();
260 assert_eq!(primitive_from_id, deserialized_id);
261 assert!(slice.is_empty());
262
263 let virtual1 = ShapeId::vtable(1);
264 let virtual2 = ShapeId::vtable(2);
265 let bytes1 = serialize_shape_id(&virtual1);
266 let bytes2 = serialize_shape_id(&virtual2);
267
268 assert!(bytes2 < bytes1, "vtable(2) should be < vtable(1) in bytes");
269 }
270
271 #[test]
272 fn test_index_id_serialization() {
273 let index = IndexId::primary(42);
274 let bytes = serialize_index_id(&index);
275 let mut slice = &bytes[..];
276 let deserialized = deserialize_index_id(&mut slice).unwrap();
277 assert_eq!(index.as_u64(), deserialized.as_u64());
278 assert!(slice.is_empty());
279
280 assert_eq!(bytes[0], 0x01);
281
282 let primary_id = PrimaryKeyId(123);
283 let index_from_id = IndexId::Primary(primary_id);
284 let bytes_from_id = serialize_index_id(&index_from_id);
285 let mut slice = &bytes_from_id[..];
286 let deserialized_id = deserialize_index_id(&mut slice).unwrap();
287 assert_eq!(index_from_id.as_u64(), deserialized_id.as_u64());
288 assert!(slice.is_empty());
289 }
290
291 #[test]
292 fn test_index_id_ordering() {
293 let index1 = IndexId::primary(1);
294 let index2 = IndexId::primary(2);
295 let index100 = IndexId::primary(100);
296 let index200 = IndexId::primary(200);
297
298 let bytes1 = serialize_index_id(&index1);
299 let bytes2 = serialize_index_id(&index2);
300 let bytes100 = serialize_index_id(&index100);
301 let bytes200 = serialize_index_id(&index200);
302
303 assert!(bytes2 < bytes1, "index(2) should be < index(1) in bytes");
304 assert!(bytes200 < bytes100, "index(200) should be < index(100) in bytes");
305 assert!(bytes100 < bytes2, "index(100) should be < index(2) in bytes");
306 }
307
308 #[test]
309 fn test_index_id_range_boundaries() {
310 let index10 = IndexId::primary(10);
311 let index11 = IndexId::primary(11);
312
313 let bytes10 = serialize_index_id(&index10);
314 let bytes11 = serialize_index_id(&index11);
315
316 assert!(bytes11 < bytes10, "index(11) should be < index(10) in bytes");
317
318 assert_eq!(bytes10.len(), 2, "IndexId(10) should be 2 bytes");
319 assert_eq!(bytes10[0], 0x01, "Primary variant should have type byte 0x01");
320
321 let next_index = IndexId::primary(11);
322 let next_bytes = serialize_index_id(&next_index);
323
324 assert!(next_bytes < bytes10, "index(11) should be < index(10) for proper range boundaries");
325 }
326
327 #[test]
328 fn test_index_entry_key_encoding_with_discriminator() {
329 let shape = ShapeId::table(42);
330 let index = IndexId::primary(7);
331
332 let primitive_bytes = serialize_shape_id(&shape);
333 let index_bytes = serialize_index_id(&index);
334
335 assert_eq!(primitive_bytes.len(), 2, "ShapeId(42) should be 2 bytes");
336 assert_eq!(index_bytes.len(), 2, "IndexId(7) should be 2 bytes");
337
338 assert_eq!(primitive_bytes[0], 0x01, "Table shape should have type byte 0x01");
339 assert_eq!(index_bytes[0], 0x01, "Primary index should have type byte 0x01");
340
341 let total_prefix_size = 1 + 1 + primitive_bytes.len() + index_bytes.len();
342 assert_eq!(total_prefix_size, 6, "Total IndexEntryKey prefix should be 6 bytes");
343 }
344}
345
346#[cfg(test)]
347mod moved_catalog_key_tests {
348 use reifydb_codec::key::{deserializer::KeyDeserializer, serializer::KeySerializer};
349
350 use super::{KeyDeserializerCatalogExt, KeySerializerCatalogExt};
351 use crate::interface::catalog::{
352 id::{IndexId, PrimaryKeyId, TableId},
353 shape::ShapeId,
354 };
355
356 #[test]
357 fn test_index_id() {
358 let mut serializer = KeySerializer::new();
359 serializer.extend_index_id(IndexId::Primary(PrimaryKeyId(123456789)));
360 let result = serializer.finish();
361
362 assert_eq!(result.len(), 5);
364 assert_eq!(result[0], 0x01); let mut serializer2 = KeySerializer::new();
368 serializer2.extend_index_id(IndexId::Primary(PrimaryKeyId(1)));
369 let result2 = serializer2.finish();
370
371 assert!(result2[1..] > result[1..]);
374 }
375
376 #[test]
377 fn test_object_id() {
378 let mut serializer = KeySerializer::new();
379 serializer.extend_shape_id(ShapeId::Table(TableId(987654321)));
380 let result = serializer.finish();
381
382 assert_eq!(result.len(), 6);
384 assert_eq!(result[0], 0x01); let mut serializer2 = KeySerializer::new();
388 serializer2.extend_shape_id(ShapeId::Table(TableId(987654322)));
389 let result2 = serializer2.finish();
390
391 assert!(result2[1..] < result[1..]);
394 }
395
396 #[test]
397 fn test_read_shape_id() {
398 let mut ser = KeySerializer::new();
399 let primitive = ShapeId::table(42);
400 ser.extend_shape_id(primitive);
401 let bytes = ser.finish();
402
403 let mut de = KeyDeserializer::from_bytes(&bytes);
404 assert_eq!(de.read_shape_id().unwrap(), primitive);
405 assert!(de.is_empty());
406 }
407
408 #[test]
409 fn test_read_index_id() {
410 let mut ser = KeySerializer::new();
411 let index = IndexId::primary(999);
412 ser.extend_index_id(index);
413 let bytes = ser.finish();
414
415 let mut de = KeyDeserializer::from_bytes(&bytes);
416 assert_eq!(de.read_index_id().unwrap(), index);
417 assert!(de.is_empty());
418 }
419}