1pub mod batch_adapter;
18pub mod compat;
19pub mod dedup;
20pub mod flat_dedup;
21pub mod flat_merge;
22pub mod flat_projection;
23pub mod last_row;
24pub mod projection;
25pub(crate) mod prune;
26pub(crate) mod pruner;
27pub mod range;
28#[cfg(feature = "test")]
29pub mod range_cache;
30#[cfg(not(feature = "test"))]
31pub(crate) mod range_cache;
32pub mod read_columns;
33pub mod scan_region;
34pub mod scan_util;
35pub(crate) mod seq_scan;
36pub(crate) mod series_candidate;
37pub(crate) mod series_reader;
38pub mod series_scan;
39pub mod stream;
40pub(crate) mod unordered_scan;
41
42use std::collections::HashMap;
43use std::sync::Arc;
44use std::time::Duration;
45
46use api::v1::OpType;
47use arrow_schema::SchemaRef;
48use common_time::Timestamp;
49use datafusion_common::arrow::array::UInt8Array;
50use datatypes::arrow;
51use datatypes::arrow::array::{Array, ArrayRef};
52use datatypes::arrow::compute::SortOptions;
53use datatypes::arrow::record_batch::RecordBatch;
54use datatypes::arrow::row::{RowConverter, SortField};
55use datatypes::prelude::{ConcreteDataType, DataType, ScalarVector};
56use datatypes::scalars::ScalarVectorBuilder;
57use datatypes::types::TimestampType;
58use datatypes::value::{Value, ValueRef};
59use datatypes::vectors::{
60 BooleanVector, Helper, TimestampMicrosecondVector, TimestampMillisecondVector,
61 TimestampMillisecondVectorBuilder, TimestampNanosecondVector, TimestampSecondVector,
62 UInt8Vector, UInt8VectorBuilder, UInt32Vector, UInt64Vector, UInt64VectorBuilder, Vector,
63 VectorRef,
64};
65use futures::TryStreamExt;
66use futures::stream::BoxStream;
67use mito_codec::row_converter::{CompositeValues, DensePrimaryKeyCodec, PrimaryKeyCodec};
68use snafu::{OptionExt, ResultExt, ensure};
69use store_api::storage::{ColumnId, SequenceNumber, SequenceRange};
70
71use crate::error::{
72 ComputeArrowSnafu, ComputeVectorSnafu, ConvertVectorSnafu, DecodeSnafu, InvalidBatchSnafu,
73 Result,
74};
75use crate::memtable::BoxedRecordBatchIterator;
76
77pub(crate) fn timestamp_array_to_i64_slice(arr: &ArrayRef) -> &[i64] {
78 use datatypes::arrow::array::{
79 TimestampMicrosecondArray, TimestampMillisecondArray, TimestampNanosecondArray,
80 TimestampSecondArray,
81 };
82 use datatypes::arrow::datatypes::{DataType, TimeUnit};
83
84 match arr.data_type() {
85 DataType::Timestamp(t, _) => match t {
86 TimeUnit::Second => arr
87 .as_any()
88 .downcast_ref::<TimestampSecondArray>()
89 .unwrap()
90 .values(),
91 TimeUnit::Millisecond => arr
92 .as_any()
93 .downcast_ref::<TimestampMillisecondArray>()
94 .unwrap()
95 .values(),
96 TimeUnit::Microsecond => arr
97 .as_any()
98 .downcast_ref::<TimestampMicrosecondArray>()
99 .unwrap()
100 .values(),
101 TimeUnit::Nanosecond => arr
102 .as_any()
103 .downcast_ref::<TimestampNanosecondArray>()
104 .unwrap()
105 .values(),
106 },
107 _ => unreachable!(),
108 }
109}
110
111#[derive(Debug, PartialEq, Clone)]
116pub struct Batch {
117 primary_key: Vec<u8>,
119 pk_values: Option<CompositeValues>,
121 dense_pk_cache: Option<Box<DensePkCache>>,
123 timestamps: VectorRef,
125 sequences: Arc<UInt64Vector>,
129 op_types: Arc<UInt8Vector>,
133 fields: Vec<BatchColumn>,
135 fields_idx: Option<HashMap<ColumnId, usize>>,
137}
138
139#[derive(Debug, PartialEq, Clone)]
141struct DensePkCache {
142 offsets: Vec<usize>,
143 values: Vec<Option<Value>>,
144}
145
146impl Batch {
147 pub fn new(
149 primary_key: Vec<u8>,
150 timestamps: VectorRef,
151 sequences: Arc<UInt64Vector>,
152 op_types: Arc<UInt8Vector>,
153 fields: Vec<BatchColumn>,
154 ) -> Result<Batch> {
155 BatchBuilder::with_required_columns(primary_key, timestamps, sequences, op_types)
156 .with_fields(fields)
157 .build()
158 }
159
160 pub fn with_fields(self, fields: Vec<BatchColumn>) -> Result<Batch> {
162 Batch::new(
163 self.primary_key,
164 self.timestamps,
165 self.sequences,
166 self.op_types,
167 fields,
168 )
169 }
170
171 pub fn primary_key(&self) -> &[u8] {
173 &self.primary_key
174 }
175
176 pub fn pk_values(&self) -> Option<&CompositeValues> {
178 self.pk_values.as_ref()
179 }
180
181 pub fn set_pk_values(&mut self, pk_values: CompositeValues) {
183 self.pk_values = Some(pk_values);
184 self.dense_pk_cache = None;
185 }
186
187 #[cfg(any(test, feature = "test"))]
189 pub fn remove_pk_values(&mut self) {
190 self.pk_values = None;
191 self.dense_pk_cache = None;
192 }
193
194 pub fn fields(&self) -> &[BatchColumn] {
196 &self.fields
197 }
198
199 pub fn timestamps(&self) -> &VectorRef {
201 &self.timestamps
202 }
203
204 pub fn sequences(&self) -> &Arc<UInt64Vector> {
206 &self.sequences
207 }
208
209 pub fn op_types(&self) -> &Arc<UInt8Vector> {
211 &self.op_types
212 }
213
214 pub fn num_rows(&self) -> usize {
216 self.sequences.len()
219 }
220
221 #[allow(dead_code)]
223 pub(crate) fn empty() -> Self {
224 Self {
225 primary_key: vec![],
226 pk_values: None,
227 dense_pk_cache: None,
228 timestamps: Arc::new(TimestampMillisecondVectorBuilder::with_capacity(0).finish()),
229 sequences: Arc::new(UInt64VectorBuilder::with_capacity(0).finish()),
230 op_types: Arc::new(UInt8VectorBuilder::with_capacity(0).finish()),
231 fields: vec![],
232 fields_idx: None,
233 }
234 }
235
236 pub fn is_empty(&self) -> bool {
238 self.num_rows() == 0
239 }
240
241 pub fn first_timestamp(&self) -> Option<Timestamp> {
243 if self.timestamps.is_empty() {
244 return None;
245 }
246
247 Some(self.get_timestamp(0))
248 }
249
250 pub fn last_timestamp(&self) -> Option<Timestamp> {
252 if self.timestamps.is_empty() {
253 return None;
254 }
255
256 Some(self.get_timestamp(self.timestamps.len() - 1))
257 }
258
259 pub fn first_sequence(&self) -> Option<SequenceNumber> {
261 if self.sequences.is_empty() {
262 return None;
263 }
264
265 Some(self.get_sequence(0))
266 }
267
268 pub fn last_sequence(&self) -> Option<SequenceNumber> {
270 if self.sequences.is_empty() {
271 return None;
272 }
273
274 Some(self.get_sequence(self.sequences.len() - 1))
275 }
276
277 pub fn set_primary_key(&mut self, primary_key: Vec<u8>) {
282 self.primary_key = primary_key;
283 self.dense_pk_cache = None;
284 }
285
286 pub fn slice(&self, offset: usize, length: usize) -> Batch {
291 let fields = self
292 .fields
293 .iter()
294 .map(|column| BatchColumn {
295 column_id: column.column_id,
296 data: column.data.slice(offset, length),
297 })
298 .collect();
299 Batch {
301 primary_key: self.primary_key.clone(),
304 pk_values: self.pk_values.clone(),
305 dense_pk_cache: self.dense_pk_cache.clone(),
306 timestamps: self.timestamps.slice(offset, length),
307 sequences: Arc::new(self.sequences.get_slice(offset, length)),
308 op_types: Arc::new(self.op_types.get_slice(offset, length)),
309 fields,
310 fields_idx: self.fields_idx.clone(),
311 }
312 }
313
314 pub fn concat(mut batches: Vec<Batch>) -> Result<Batch> {
318 ensure!(
319 !batches.is_empty(),
320 InvalidBatchSnafu {
321 reason: "empty batches",
322 }
323 );
324 if batches.len() == 1 {
325 return Ok(batches.pop().unwrap());
327 }
328
329 let primary_key = std::mem::take(&mut batches[0].primary_key);
330 let first = &batches[0];
331 ensure!(
333 batches
334 .iter()
335 .skip(1)
336 .all(|b| b.primary_key() == primary_key),
337 InvalidBatchSnafu {
338 reason: "batches have different primary key",
339 }
340 );
341 for b in batches.iter().skip(1) {
342 ensure!(
343 b.fields.len() == first.fields.len(),
344 InvalidBatchSnafu {
345 reason: "batches have different field num",
346 }
347 );
348 for (l, r) in b.fields.iter().zip(&first.fields) {
349 ensure!(
350 l.column_id == r.column_id,
351 InvalidBatchSnafu {
352 reason: "batches have different fields",
353 }
354 );
355 }
356 }
357
358 let mut builder = BatchBuilder::new(primary_key);
360 let array = concat_arrays(batches.iter().map(|b| b.timestamps().to_arrow_array()))?;
362 builder.timestamps_array(array)?;
363 let array = concat_arrays(batches.iter().map(|b| b.sequences().to_arrow_array()))?;
364 builder.sequences_array(array)?;
365 let array = concat_arrays(batches.iter().map(|b| b.op_types().to_arrow_array()))?;
366 builder.op_types_array(array)?;
367 for (i, batch_column) in first.fields.iter().enumerate() {
368 let array = concat_arrays(batches.iter().map(|b| b.fields()[i].data.to_arrow_array()))?;
369 builder.push_field_array(batch_column.column_id, array)?;
370 }
371
372 builder.build()
373 }
374
375 pub fn filter_deleted(&mut self) -> Result<()> {
377 let array = self.op_types.as_arrow();
379 let rhs = UInt8Array::new_scalar(OpType::Delete as u8);
381 let predicate =
382 arrow::compute::kernels::cmp::neq(array, &rhs).context(ComputeArrowSnafu)?;
383 self.filter(&BooleanVector::from(predicate))
384 }
385
386 pub fn filter(&mut self, predicate: &BooleanVector) -> Result<()> {
389 self.timestamps = self
390 .timestamps
391 .filter(predicate)
392 .context(ComputeVectorSnafu)?;
393 self.sequences = Arc::new(
394 UInt64Vector::try_from_arrow_array(
395 arrow::compute::filter(self.sequences.as_arrow(), predicate.as_boolean_array())
396 .context(ComputeArrowSnafu)?,
397 )
398 .unwrap(),
399 );
400 self.op_types = Arc::new(
401 UInt8Vector::try_from_arrow_array(
402 arrow::compute::filter(self.op_types.as_arrow(), predicate.as_boolean_array())
403 .context(ComputeArrowSnafu)?,
404 )
405 .unwrap(),
406 );
407 for batch_column in &mut self.fields {
408 batch_column.data = batch_column
409 .data
410 .filter(predicate)
411 .context(ComputeVectorSnafu)?;
412 }
413
414 Ok(())
415 }
416
417 pub fn filter_by_sequence(&mut self, sequence: Option<SequenceRange>) -> Result<()> {
419 let seq_range = match sequence {
420 None => return Ok(()),
421 Some(seq_range) => {
422 let (Some(first), Some(last)) = (self.first_sequence(), self.last_sequence())
423 else {
424 return Ok(());
425 };
426 let is_subset = match seq_range {
427 SequenceRange::Gt { min } => min < first,
428 SequenceRange::LtEq { max } => max >= last,
429 SequenceRange::GtLtEq { min, max } => min < first && max >= last,
430 };
431 if is_subset {
432 return Ok(());
433 }
434 seq_range
435 }
436 };
437
438 let seqs = self.sequences.as_arrow();
439 let predicate = seq_range.filter(seqs).context(ComputeArrowSnafu)?;
440
441 let predicate = BooleanVector::from(predicate);
442 self.filter(&predicate)?;
443
444 Ok(())
445 }
446
447 pub fn sort(&mut self, dedup: bool) -> Result<()> {
454 let converter = RowConverter::new(vec![
457 SortField::new(self.timestamps.data_type().as_arrow_type()),
458 SortField::new_with_options(
459 self.sequences.data_type().as_arrow_type(),
460 SortOptions {
461 descending: true,
462 ..Default::default()
463 },
464 ),
465 ])
466 .context(ComputeArrowSnafu)?;
467 let columns = [
469 self.timestamps.to_arrow_array(),
470 self.sequences.to_arrow_array(),
471 ];
472 let rows = converter.convert_columns(&columns).unwrap();
473 let mut to_sort: Vec<_> = rows.iter().enumerate().collect();
474
475 let was_sorted = to_sort.is_sorted_by_key(|x| x.1);
476 if !was_sorted {
477 to_sort.sort_unstable_by_key(|x| x.1);
478 }
479
480 let num_rows = to_sort.len();
481 if dedup {
482 to_sort.dedup_by(|left, right| {
484 debug_assert_eq!(18, left.1.as_ref().len());
485 debug_assert_eq!(18, right.1.as_ref().len());
486 let (left_key, right_key) = (left.1.as_ref(), right.1.as_ref());
487 left_key[..TIMESTAMP_KEY_LEN] == right_key[..TIMESTAMP_KEY_LEN]
489 });
490 }
491 let no_dedup = to_sort.len() == num_rows;
492
493 if was_sorted && no_dedup {
494 return Ok(());
495 }
496 let indices = UInt32Vector::from_iter_values(to_sort.iter().map(|v| v.0 as u32));
497 self.take_in_place(&indices)
498 }
499
500 pub(crate) fn merge_last_non_null(&mut self) -> Result<()> {
508 let num_rows = self.num_rows();
509 if num_rows < 2 {
510 return Ok(());
511 }
512
513 let Some(timestamps) = self.timestamps_native() else {
514 return Ok(());
515 };
516
517 let mut has_dup = false;
519 let mut group_count = 1;
520 for i in 1..num_rows {
521 has_dup |= timestamps[i] == timestamps[i - 1];
522 group_count += (timestamps[i] != timestamps[i - 1]) as usize;
523 }
524 if !has_dup {
525 return Ok(());
526 }
527
528 let num_fields = self.fields.len();
529 let op_types = self.op_types.as_arrow().values();
530
531 let mut base_indices: Vec<u32> = Vec::with_capacity(group_count);
532 let mut field_indices: Vec<Vec<u32>> = (0..num_fields)
533 .map(|_| Vec::with_capacity(group_count))
534 .collect();
535
536 let mut start = 0;
537 while start < num_rows {
538 let ts = timestamps[start];
539 let mut end = start + 1;
540 while end < num_rows && timestamps[end] == ts {
541 end += 1;
542 }
543
544 let group_pos = base_indices.len();
545 base_indices.push(start as u32);
546
547 if num_fields > 0 {
548 for idx in &mut field_indices {
550 idx.push(start as u32);
551 }
552
553 let base_deleted = op_types[start] == OpType::Delete as u8;
554 if !base_deleted {
555 let mut missing_fields = Vec::new();
558 for (field_idx, col) in self.fields.iter().enumerate() {
559 if col.data.is_null(start) {
560 missing_fields.push(field_idx);
561 }
562 }
563
564 if !missing_fields.is_empty() {
565 for row_idx in (start + 1)..end {
566 if op_types[row_idx] == OpType::Delete as u8 {
567 break;
568 }
569
570 missing_fields.retain(|&field_idx| {
571 if self.fields[field_idx].data.is_null(row_idx) {
572 true
573 } else {
574 field_indices[field_idx][group_pos] = row_idx as u32;
575 false
576 }
577 });
578
579 if missing_fields.is_empty() {
580 break;
581 }
582 }
583 }
584 }
585 }
586
587 start = end;
588 }
589
590 let base_indices = UInt32Vector::from_vec(base_indices);
591 self.timestamps = self
592 .timestamps
593 .take(&base_indices)
594 .context(ComputeVectorSnafu)?;
595 let array = arrow::compute::take(self.sequences.as_arrow(), base_indices.as_arrow(), None)
596 .context(ComputeArrowSnafu)?;
597 self.sequences = Arc::new(UInt64Vector::try_from_arrow_array(array).unwrap());
599 let array = arrow::compute::take(self.op_types.as_arrow(), base_indices.as_arrow(), None)
600 .context(ComputeArrowSnafu)?;
601 self.op_types = Arc::new(UInt8Vector::try_from_arrow_array(array).unwrap());
603
604 for (field_idx, batch_column) in self.fields.iter_mut().enumerate() {
605 let idx = UInt32Vector::from_vec(std::mem::take(&mut field_indices[field_idx]));
606 batch_column.data = batch_column.data.take(&idx).context(ComputeVectorSnafu)?;
607 }
608
609 Ok(())
610 }
611
612 pub fn memory_size(&self) -> usize {
614 let mut size = std::mem::size_of::<Self>();
615 size += self.primary_key.len();
616 size += self.timestamps.memory_size();
617 size += self.sequences.memory_size();
618 size += self.op_types.memory_size();
619 for batch_column in &self.fields {
620 size += batch_column.data.memory_size();
621 }
622 size
623 }
624
625 pub(crate) fn timestamps_native(&self) -> Option<&[i64]> {
627 if self.timestamps.is_empty() {
628 return None;
629 }
630
631 let values = match self.timestamps.data_type() {
632 ConcreteDataType::Timestamp(TimestampType::Second(_)) => self
633 .timestamps
634 .as_any()
635 .downcast_ref::<TimestampSecondVector>()
636 .unwrap()
637 .as_arrow()
638 .values(),
639 ConcreteDataType::Timestamp(TimestampType::Millisecond(_)) => self
640 .timestamps
641 .as_any()
642 .downcast_ref::<TimestampMillisecondVector>()
643 .unwrap()
644 .as_arrow()
645 .values(),
646 ConcreteDataType::Timestamp(TimestampType::Microsecond(_)) => self
647 .timestamps
648 .as_any()
649 .downcast_ref::<TimestampMicrosecondVector>()
650 .unwrap()
651 .as_arrow()
652 .values(),
653 ConcreteDataType::Timestamp(TimestampType::Nanosecond(_)) => self
654 .timestamps
655 .as_any()
656 .downcast_ref::<TimestampNanosecondVector>()
657 .unwrap()
658 .as_arrow()
659 .values(),
660 other => panic!("timestamps in a Batch has other type {:?}", other),
661 };
662
663 Some(values)
664 }
665
666 fn take_in_place(&mut self, indices: &UInt32Vector) -> Result<()> {
668 self.timestamps = self.timestamps.take(indices).context(ComputeVectorSnafu)?;
669 let array = arrow::compute::take(self.sequences.as_arrow(), indices.as_arrow(), None)
670 .context(ComputeArrowSnafu)?;
671 self.sequences = Arc::new(UInt64Vector::try_from_arrow_array(array).unwrap());
673 let array = arrow::compute::take(self.op_types.as_arrow(), indices.as_arrow(), None)
674 .context(ComputeArrowSnafu)?;
675 self.op_types = Arc::new(UInt8Vector::try_from_arrow_array(array).unwrap());
676 for batch_column in &mut self.fields {
677 batch_column.data = batch_column
678 .data
679 .take(indices)
680 .context(ComputeVectorSnafu)?;
681 }
682
683 Ok(())
684 }
685
686 fn get_timestamp(&self, index: usize) -> Timestamp {
691 match self.timestamps.get_ref(index) {
692 ValueRef::Timestamp(timestamp) => timestamp,
693
694 value => panic!("{:?} is not a timestamp", value),
696 }
697 }
698
699 pub(crate) fn get_sequence(&self, index: usize) -> SequenceNumber {
704 self.sequences.get_data(index).unwrap()
706 }
707
708 pub(crate) fn ensure_dense_pk_decoded(&mut self, codec: &DensePrimaryKeyCodec) -> Result<()> {
711 if self.pk_values.is_none() {
712 let mut values = Vec::with_capacity(codec.num_fields());
715 for value in codec.decode_dense_iter(&self.primary_key) {
716 values.push(value.context(DecodeSnafu)?);
717 }
718 self.set_pk_values(CompositeValues::Dense(values));
719 }
720 Ok(())
721 }
722
723 pub fn pk_col_value(
729 &mut self,
730 codec: &dyn PrimaryKeyCodec,
731 col_idx_in_pk: usize,
732 column_id: ColumnId,
733 ) -> Result<Option<&Value>> {
734 if self.pk_values.is_none() {
735 if let Some(codec) = codec.as_dense() {
736 if col_idx_in_pk >= codec.num_fields() {
737 return Ok(None);
738 }
739 let cache = self.dense_pk_cache.get_or_insert_with(|| {
740 Box::new(DensePkCache {
741 offsets: Vec::new(),
742 values: vec![None; codec.num_fields()],
743 })
744 });
745 if cache.values[col_idx_in_pk].is_none() {
746 let value = codec
747 .decode_value_at(&self.primary_key, col_idx_in_pk, &mut cache.offsets)
748 .context(DecodeSnafu)?;
749 cache.values[col_idx_in_pk] = Some(value);
750 }
751 return Ok(cache.values[col_idx_in_pk].as_ref());
752 }
753 self.pk_values = Some(codec.decode(&self.primary_key).context(DecodeSnafu)?);
754 }
755
756 let pk_values = self.pk_values.as_ref().unwrap();
757 Ok(match pk_values {
758 CompositeValues::Dense(values) => values.get(col_idx_in_pk).map(|(_, v)| v),
759 CompositeValues::Sparse(values) => values.get(&column_id),
760 })
761 }
762
763 pub fn field_col_value(&mut self, column_id: ColumnId) -> Option<&BatchColumn> {
767 if self.fields_idx.is_none() {
768 self.fields_idx = Some(
769 self.fields
770 .iter()
771 .enumerate()
772 .map(|(i, c)| (c.column_id, i))
773 .collect(),
774 );
775 }
776
777 self.fields_idx
778 .as_ref()
779 .unwrap()
780 .get(&column_id)
781 .map(|&idx| &self.fields[idx])
782 }
783}
784
785const TIMESTAMP_KEY_LEN: usize = 9;
787
788fn concat_arrays(iter: impl Iterator<Item = ArrayRef>) -> Result<ArrayRef> {
790 let arrays: Vec<_> = iter.collect();
791 let dyn_arrays: Vec<_> = arrays.iter().map(|array| array.as_ref()).collect();
792 arrow::compute::concat(&dyn_arrays).context(ComputeArrowSnafu)
793}
794
795#[derive(Debug, PartialEq, Eq, Clone)]
797pub struct BatchColumn {
798 pub column_id: ColumnId,
800 pub data: VectorRef,
802}
803
804pub struct BatchBuilder {
806 primary_key: Vec<u8>,
807 timestamps: Option<VectorRef>,
808 sequences: Option<Arc<UInt64Vector>>,
809 op_types: Option<Arc<UInt8Vector>>,
810 fields: Vec<BatchColumn>,
811}
812
813impl BatchBuilder {
814 pub fn new(primary_key: Vec<u8>) -> BatchBuilder {
816 BatchBuilder {
817 primary_key,
818 timestamps: None,
819 sequences: None,
820 op_types: None,
821 fields: Vec::new(),
822 }
823 }
824
825 pub fn with_required_columns(
827 primary_key: Vec<u8>,
828 timestamps: VectorRef,
829 sequences: Arc<UInt64Vector>,
830 op_types: Arc<UInt8Vector>,
831 ) -> BatchBuilder {
832 BatchBuilder {
833 primary_key,
834 timestamps: Some(timestamps),
835 sequences: Some(sequences),
836 op_types: Some(op_types),
837 fields: Vec::new(),
838 }
839 }
840
841 pub fn with_fields(mut self, fields: Vec<BatchColumn>) -> Self {
843 self.fields = fields;
844 self
845 }
846
847 pub fn push_field(&mut self, column: BatchColumn) -> &mut Self {
849 self.fields.push(column);
850 self
851 }
852
853 pub fn push_field_array(&mut self, column_id: ColumnId, array: ArrayRef) -> Result<&mut Self> {
855 let vector = Helper::try_into_vector(array).context(ConvertVectorSnafu)?;
856 self.fields.push(BatchColumn {
857 column_id,
858 data: vector,
859 });
860
861 Ok(self)
862 }
863
864 pub fn timestamps_array(&mut self, array: ArrayRef) -> Result<&mut Self> {
866 let vector = Helper::try_into_vector(array).context(ConvertVectorSnafu)?;
867 ensure!(
868 vector.data_type().is_timestamp(),
869 InvalidBatchSnafu {
870 reason: format!("{:?} is not a timestamp type", vector.data_type()),
871 }
872 );
873
874 self.timestamps = Some(vector);
875 Ok(self)
876 }
877
878 pub fn sequences_array(&mut self, array: ArrayRef) -> Result<&mut Self> {
880 ensure!(
881 *array.data_type() == arrow::datatypes::DataType::UInt64,
882 InvalidBatchSnafu {
883 reason: "sequence array is not UInt64 type",
884 }
885 );
886 let vector = Arc::new(UInt64Vector::try_from_arrow_array(array).unwrap());
888 self.sequences = Some(vector);
889
890 Ok(self)
891 }
892
893 pub fn op_types_array(&mut self, array: ArrayRef) -> Result<&mut Self> {
895 ensure!(
896 *array.data_type() == arrow::datatypes::DataType::UInt8,
897 InvalidBatchSnafu {
898 reason: "sequence array is not UInt8 type",
899 }
900 );
901 let vector = Arc::new(UInt8Vector::try_from_arrow_array(array).unwrap());
903 self.op_types = Some(vector);
904
905 Ok(self)
906 }
907
908 pub fn build(self) -> Result<Batch> {
910 let timestamps = self.timestamps.context(InvalidBatchSnafu {
911 reason: "missing timestamps",
912 })?;
913 let sequences = self.sequences.context(InvalidBatchSnafu {
914 reason: "missing sequences",
915 })?;
916 let op_types = self.op_types.context(InvalidBatchSnafu {
917 reason: "missing op_types",
918 })?;
919 assert_eq!(0, timestamps.null_count());
922 assert_eq!(0, sequences.null_count());
923 assert_eq!(0, op_types.null_count());
924
925 let ts_len = timestamps.len();
926 ensure!(
927 sequences.len() == ts_len,
928 InvalidBatchSnafu {
929 reason: format!(
930 "sequence have different len {} != {}",
931 sequences.len(),
932 ts_len
933 ),
934 }
935 );
936 ensure!(
937 op_types.len() == ts_len,
938 InvalidBatchSnafu {
939 reason: format!(
940 "op type have different len {} != {}",
941 op_types.len(),
942 ts_len
943 ),
944 }
945 );
946 for column in &self.fields {
947 ensure!(
948 column.data.len() == ts_len,
949 InvalidBatchSnafu {
950 reason: format!(
951 "column {} has different len {} != {}",
952 column.column_id,
953 column.data.len(),
954 ts_len
955 ),
956 }
957 );
958 }
959
960 Ok(Batch {
961 primary_key: self.primary_key,
962 pk_values: None,
963 dense_pk_cache: None,
964 timestamps,
965 sequences,
966 op_types,
967 fields: self.fields,
968 fields_idx: None,
969 })
970 }
971}
972
973impl From<Batch> for BatchBuilder {
974 fn from(batch: Batch) -> Self {
975 Self {
976 primary_key: batch.primary_key,
977 timestamps: Some(batch.timestamps),
978 sequences: Some(batch.sequences),
979 op_types: Some(batch.op_types),
980 fields: batch.fields,
981 }
982 }
983}
984
985pub struct FlatSource {
987 schema: SchemaRef,
988 inner: FlatSourceInner,
989}
990
991impl FlatSource {
992 pub fn new_iter(schema: SchemaRef, iter: BoxedRecordBatchIterator) -> Self {
994 Self {
995 schema,
996 inner: FlatSourceInner::Iter(iter),
997 }
998 }
999
1000 pub fn new_stream(schema: SchemaRef, stream: BoxedRecordBatchStream) -> Self {
1002 Self {
1003 schema,
1004 inner: FlatSourceInner::Stream(stream),
1005 }
1006 }
1007
1008 pub(crate) fn schema(&self) -> &SchemaRef {
1009 &self.schema
1010 }
1011
1012 pub async fn next_batch(&mut self) -> Result<Option<RecordBatch>> {
1013 self.inner.next_batch().await
1014 }
1015
1016 pub(crate) fn into_stream(self) -> BoxedRecordBatchStream {
1018 match self.inner {
1019 FlatSourceInner::Iter(iter) => Box::pin(futures::stream::iter(iter)),
1020 FlatSourceInner::Stream(stream) => stream,
1021 }
1022 }
1023
1024 #[cfg(test)]
1025 pub(crate) fn take_iter(self) -> BoxedRecordBatchIterator {
1026 match self.inner {
1027 FlatSourceInner::Iter(iter) => iter,
1028 FlatSourceInner::Stream(_) => unreachable!(),
1029 }
1030 }
1031}
1032
1033enum FlatSourceInner {
1034 Iter(BoxedRecordBatchIterator),
1036 Stream(BoxedRecordBatchStream),
1038}
1039
1040impl FlatSourceInner {
1041 pub async fn next_batch(&mut self) -> Result<Option<RecordBatch>> {
1043 match self {
1044 Self::Iter(iter) => iter.next().transpose(),
1045 Self::Stream(stream) => stream.try_next().await,
1046 }
1047 }
1048}
1049
1050pub type BoxedRecordBatchStream = BoxStream<'static, Result<RecordBatch>>;
1052
1053#[derive(Debug, Default)]
1055pub(crate) struct ScannerMetrics {
1056 scan_cost: Duration,
1058 yield_cost: Duration,
1060 num_batches: usize,
1062 num_rows: usize,
1064}
1065
1066#[cfg(test)]
1067mod tests {
1068 use datatypes::arrow::array::{TimestampMillisecondArray, UInt8Array, UInt64Array};
1069 use mito_codec::row_converter::{self, build_primary_key_codec_with_fields};
1070 use store_api::codec::PrimaryKeyEncoding;
1071 use store_api::storage::consts::ReservedColumnId;
1072
1073 use super::*;
1074 use crate::error::Error;
1075 use crate::test_util::new_batch_builder;
1076
1077 #[test]
1078 fn dense_pk_columns_are_lazy_and_reset_with_the_key() {
1079 use mito_codec::row_converter::{DensePrimaryKeyCodec, PrimaryKeyCodecExt, SortField};
1080
1081 let codec = DensePrimaryKeyCodec::with_fields(vec![
1082 (7, SortField::new(ConcreteDataType::string_datatype())),
1083 (3, SortField::new(ConcreteDataType::int64_datatype())),
1084 (9, SortField::new(ConcreteDataType::string_datatype())),
1085 ]);
1086 let values = [
1087 Value::from("䏿–‡\0abcdefgh"),
1088 Value::Int64(-42),
1089 Value::Null,
1090 ];
1091 let key = codec
1092 .encode(values.iter().map(Value::as_value_ref))
1093 .unwrap();
1094 let mut batch = new_batch_without_fields(&[1, 2], &[1, 1], &[OpType::Put, OpType::Put]);
1095 batch.set_primary_key(key);
1096 for pos in [2, 0, 1, 2] {
1097 assert_eq!(
1098 batch.pk_col_value(&codec, pos, [7, 3, 9][pos]).unwrap(),
1099 Some(&values[pos])
1100 );
1101 }
1102 assert!(batch.pk_col_value(&codec, 3, 99).unwrap().is_none());
1103 let mut sliced = batch.slice(1, 1);
1104 assert_eq!(sliced.pk_col_value(&codec, 0, 7).unwrap(), Some(&values[0]));
1105
1106 batch.set_primary_key(vec![0, 1]);
1108 assert_eq!(
1109 batch.pk_col_value(&codec, 0, 7).unwrap(),
1110 Some(&Value::Null)
1111 );
1112 assert!(batch.pk_col_value(&codec, 1, 3).is_err());
1113 batch.set_primary_key(
1114 codec
1115 .encode(
1116 [
1117 ValueRef::String(""),
1118 ValueRef::Int64(8),
1119 ValueRef::String("new"),
1120 ]
1121 .into_iter(),
1122 )
1123 .unwrap(),
1124 );
1125 assert_eq!(
1126 batch.pk_col_value(&codec, 2, 9).unwrap(),
1127 Some(&Value::from("new"))
1128 );
1129 assert_eq!(
1130 batch.pk_col_value(&codec, 0, 7).unwrap(),
1131 Some(&Value::from(""))
1132 );
1133
1134 batch.set_pk_values(CompositeValues::Dense(vec![(7, Value::from("default"))]));
1136 batch.ensure_dense_pk_decoded(&codec).unwrap();
1137 assert_eq!(
1138 batch.pk_col_value(&codec, 0, 7).unwrap(),
1139 Some(&Value::from("default"))
1140 );
1141 assert!(batch.pk_col_value(&codec, 1, 3).unwrap().is_none());
1142 batch.remove_pk_values();
1143 batch.ensure_dense_pk_decoded(&codec).unwrap();
1144 assert_eq!(
1145 batch.pk_col_value(&codec, 1, 3).unwrap(),
1146 Some(&Value::Int64(8))
1147 );
1148 }
1149
1150 fn new_batch(
1151 timestamps: &[i64],
1152 sequences: &[u64],
1153 op_types: &[OpType],
1154 field: &[u64],
1155 ) -> Batch {
1156 new_batch_builder(b"test", timestamps, sequences, op_types, 1, field)
1157 .build()
1158 .unwrap()
1159 }
1160
1161 fn new_batch_with_u64_fields(
1162 timestamps: &[i64],
1163 sequences: &[u64],
1164 op_types: &[OpType],
1165 fields: &[(ColumnId, &[Option<u64>])],
1166 ) -> Batch {
1167 assert_eq!(timestamps.len(), sequences.len());
1168 assert_eq!(timestamps.len(), op_types.len());
1169 for (_, values) in fields {
1170 assert_eq!(timestamps.len(), values.len());
1171 }
1172
1173 let mut builder = BatchBuilder::new(b"test".to_vec());
1174 builder
1175 .timestamps_array(Arc::new(TimestampMillisecondArray::from_iter_values(
1176 timestamps.iter().copied(),
1177 )))
1178 .unwrap()
1179 .sequences_array(Arc::new(UInt64Array::from_iter_values(
1180 sequences.iter().copied(),
1181 )))
1182 .unwrap()
1183 .op_types_array(Arc::new(UInt8Array::from_iter_values(
1184 op_types.iter().map(|v| *v as u8),
1185 )))
1186 .unwrap();
1187
1188 for (col_id, values) in fields {
1189 builder
1190 .push_field_array(*col_id, Arc::new(UInt64Array::from(values.to_vec())))
1191 .unwrap();
1192 }
1193
1194 builder.build().unwrap()
1195 }
1196
1197 fn new_batch_without_fields(
1198 timestamps: &[i64],
1199 sequences: &[u64],
1200 op_types: &[OpType],
1201 ) -> Batch {
1202 assert_eq!(timestamps.len(), sequences.len());
1203 assert_eq!(timestamps.len(), op_types.len());
1204
1205 let mut builder = BatchBuilder::new(b"test".to_vec());
1206 builder
1207 .timestamps_array(Arc::new(TimestampMillisecondArray::from_iter_values(
1208 timestamps.iter().copied(),
1209 )))
1210 .unwrap()
1211 .sequences_array(Arc::new(UInt64Array::from_iter_values(
1212 sequences.iter().copied(),
1213 )))
1214 .unwrap()
1215 .op_types_array(Arc::new(UInt8Array::from_iter_values(
1216 op_types.iter().map(|v| *v as u8),
1217 )))
1218 .unwrap();
1219
1220 builder.build().unwrap()
1221 }
1222
1223 #[test]
1224 fn test_empty_batch() {
1225 let batch = Batch::empty();
1226 assert!(batch.is_empty());
1227 assert_eq!(None, batch.first_timestamp());
1228 assert_eq!(None, batch.last_timestamp());
1229 assert_eq!(None, batch.first_sequence());
1230 assert_eq!(None, batch.last_sequence());
1231 assert!(batch.timestamps_native().is_none());
1232 }
1233
1234 #[test]
1235 fn test_first_last_one() {
1236 let batch = new_batch(&[1], &[2], &[OpType::Put], &[4]);
1237 assert_eq!(
1238 Timestamp::new_millisecond(1),
1239 batch.first_timestamp().unwrap()
1240 );
1241 assert_eq!(
1242 Timestamp::new_millisecond(1),
1243 batch.last_timestamp().unwrap()
1244 );
1245 assert_eq!(2, batch.first_sequence().unwrap());
1246 assert_eq!(2, batch.last_sequence().unwrap());
1247 }
1248
1249 #[test]
1250 fn test_first_last_multiple() {
1251 let batch = new_batch(
1252 &[1, 2, 3],
1253 &[11, 12, 13],
1254 &[OpType::Put, OpType::Put, OpType::Put],
1255 &[21, 22, 23],
1256 );
1257 assert_eq!(
1258 Timestamp::new_millisecond(1),
1259 batch.first_timestamp().unwrap()
1260 );
1261 assert_eq!(
1262 Timestamp::new_millisecond(3),
1263 batch.last_timestamp().unwrap()
1264 );
1265 assert_eq!(11, batch.first_sequence().unwrap());
1266 assert_eq!(13, batch.last_sequence().unwrap());
1267 }
1268
1269 #[test]
1270 fn test_slice() {
1271 let batch = new_batch(
1272 &[1, 2, 3, 4],
1273 &[11, 12, 13, 14],
1274 &[OpType::Put, OpType::Delete, OpType::Put, OpType::Put],
1275 &[21, 22, 23, 24],
1276 );
1277 let batch = batch.slice(1, 2);
1278 let expect = new_batch(
1279 &[2, 3],
1280 &[12, 13],
1281 &[OpType::Delete, OpType::Put],
1282 &[22, 23],
1283 );
1284 assert_eq!(expect, batch);
1285 }
1286
1287 #[test]
1288 fn test_timestamps_native() {
1289 let batch = new_batch(
1290 &[1, 2, 3, 4],
1291 &[11, 12, 13, 14],
1292 &[OpType::Put, OpType::Delete, OpType::Put, OpType::Put],
1293 &[21, 22, 23, 24],
1294 );
1295 assert_eq!(&[1, 2, 3, 4], batch.timestamps_native().unwrap());
1296 }
1297
1298 #[test]
1299 fn test_concat_empty() {
1300 let err = Batch::concat(vec![]).unwrap_err();
1301 assert!(
1302 matches!(err, Error::InvalidBatch { .. }),
1303 "unexpected err: {err}"
1304 );
1305 }
1306
1307 #[test]
1308 fn test_concat_one() {
1309 let batch = new_batch(&[], &[], &[], &[]);
1310 let actual = Batch::concat(vec![batch.clone()]).unwrap();
1311 assert_eq!(batch, actual);
1312
1313 let batch = new_batch(&[1, 2], &[11, 12], &[OpType::Put, OpType::Put], &[21, 22]);
1314 let actual = Batch::concat(vec![batch.clone()]).unwrap();
1315 assert_eq!(batch, actual);
1316 }
1317
1318 #[test]
1319 fn test_concat_multiple() {
1320 let batches = vec![
1321 new_batch(&[1, 2], &[11, 12], &[OpType::Put, OpType::Put], &[21, 22]),
1322 new_batch(
1323 &[3, 4, 5],
1324 &[13, 14, 15],
1325 &[OpType::Put, OpType::Delete, OpType::Put],
1326 &[23, 24, 25],
1327 ),
1328 new_batch(&[], &[], &[], &[]),
1329 new_batch(&[6], &[16], &[OpType::Put], &[26]),
1330 ];
1331 let batch = Batch::concat(batches).unwrap();
1332 let expect = new_batch(
1333 &[1, 2, 3, 4, 5, 6],
1334 &[11, 12, 13, 14, 15, 16],
1335 &[
1336 OpType::Put,
1337 OpType::Put,
1338 OpType::Put,
1339 OpType::Delete,
1340 OpType::Put,
1341 OpType::Put,
1342 ],
1343 &[21, 22, 23, 24, 25, 26],
1344 );
1345 assert_eq!(expect, batch);
1346 }
1347
1348 #[test]
1349 fn test_concat_different() {
1350 let batch1 = new_batch(&[1], &[1], &[OpType::Put], &[1]);
1351 let mut batch2 = new_batch(&[2], &[2], &[OpType::Put], &[2]);
1352 batch2.primary_key = b"hello".to_vec();
1353 let err = Batch::concat(vec![batch1, batch2]).unwrap_err();
1354 assert!(
1355 matches!(err, Error::InvalidBatch { .. }),
1356 "unexpected err: {err}"
1357 );
1358 }
1359
1360 #[test]
1361 fn test_concat_different_fields() {
1362 let batch1 = new_batch(&[1], &[1], &[OpType::Put], &[1]);
1363 let fields = vec![
1364 batch1.fields()[0].clone(),
1365 BatchColumn {
1366 column_id: 2,
1367 data: Arc::new(UInt64Vector::from_slice([2])),
1368 },
1369 ];
1370 let batch2 = batch1.clone().with_fields(fields).unwrap();
1372 let err = Batch::concat(vec![batch1.clone(), batch2]).unwrap_err();
1373 assert!(
1374 matches!(err, Error::InvalidBatch { .. }),
1375 "unexpected err: {err}"
1376 );
1377
1378 let fields = vec![BatchColumn {
1380 column_id: 2,
1381 data: Arc::new(UInt64Vector::from_slice([2])),
1382 }];
1383 let batch2 = batch1.clone().with_fields(fields).unwrap();
1384 let err = Batch::concat(vec![batch1, batch2]).unwrap_err();
1385 assert!(
1386 matches!(err, Error::InvalidBatch { .. }),
1387 "unexpected err: {err}"
1388 );
1389 }
1390
1391 #[test]
1392 fn test_filter_deleted_empty() {
1393 let mut batch = new_batch(&[], &[], &[], &[]);
1394 batch.filter_deleted().unwrap();
1395 assert!(batch.is_empty());
1396 }
1397
1398 #[test]
1399 fn test_filter_deleted() {
1400 let mut batch = new_batch(
1401 &[1, 2, 3, 4],
1402 &[11, 12, 13, 14],
1403 &[OpType::Delete, OpType::Put, OpType::Delete, OpType::Put],
1404 &[21, 22, 23, 24],
1405 );
1406 batch.filter_deleted().unwrap();
1407 let expect = new_batch(&[2, 4], &[12, 14], &[OpType::Put, OpType::Put], &[22, 24]);
1408 assert_eq!(expect, batch);
1409
1410 let mut batch = new_batch(
1411 &[1, 2, 3, 4],
1412 &[11, 12, 13, 14],
1413 &[OpType::Put, OpType::Put, OpType::Put, OpType::Put],
1414 &[21, 22, 23, 24],
1415 );
1416 let expect = batch.clone();
1417 batch.filter_deleted().unwrap();
1418 assert_eq!(expect, batch);
1419 }
1420
1421 #[test]
1422 fn test_filter_by_sequence() {
1423 let mut batch = new_batch(
1425 &[1, 2, 3, 4],
1426 &[11, 12, 13, 14],
1427 &[OpType::Put, OpType::Put, OpType::Put, OpType::Put],
1428 &[21, 22, 23, 24],
1429 );
1430 batch
1431 .filter_by_sequence(Some(SequenceRange::LtEq { max: 13 }))
1432 .unwrap();
1433 let expect = new_batch(
1434 &[1, 2, 3],
1435 &[11, 12, 13],
1436 &[OpType::Put, OpType::Put, OpType::Put],
1437 &[21, 22, 23],
1438 );
1439 assert_eq!(expect, batch);
1440
1441 let mut batch = new_batch(
1443 &[1, 2, 3, 4],
1444 &[11, 12, 13, 14],
1445 &[OpType::Put, OpType::Delete, OpType::Put, OpType::Put],
1446 &[21, 22, 23, 24],
1447 );
1448
1449 batch
1450 .filter_by_sequence(Some(SequenceRange::LtEq { max: 10 }))
1451 .unwrap();
1452 assert!(batch.is_empty());
1453
1454 let mut batch = new_batch(
1456 &[1, 2, 3, 4],
1457 &[11, 12, 13, 14],
1458 &[OpType::Put, OpType::Delete, OpType::Put, OpType::Put],
1459 &[21, 22, 23, 24],
1460 );
1461 let expect = batch.clone();
1462 batch.filter_by_sequence(None).unwrap();
1463 assert_eq!(expect, batch);
1464
1465 let mut batch = new_batch(&[], &[], &[], &[]);
1467 batch
1468 .filter_by_sequence(Some(SequenceRange::LtEq { max: 10 }))
1469 .unwrap();
1470 assert!(batch.is_empty());
1471
1472 let mut batch = new_batch(&[], &[], &[], &[]);
1474 batch.filter_by_sequence(None).unwrap();
1475 assert!(batch.is_empty());
1476
1477 let mut batch = new_batch(
1479 &[1, 2, 3, 4],
1480 &[11, 12, 13, 14],
1481 &[OpType::Put, OpType::Put, OpType::Put, OpType::Put],
1482 &[21, 22, 23, 24],
1483 );
1484 batch
1485 .filter_by_sequence(Some(SequenceRange::Gt { min: 12 }))
1486 .unwrap();
1487 let expect = new_batch(&[3, 4], &[13, 14], &[OpType::Put, OpType::Put], &[23, 24]);
1488 assert_eq!(expect, batch);
1489
1490 let mut batch = new_batch(
1492 &[1, 2, 3, 4],
1493 &[11, 12, 13, 14],
1494 &[OpType::Put, OpType::Delete, OpType::Put, OpType::Put],
1495 &[21, 22, 23, 24],
1496 );
1497 batch
1498 .filter_by_sequence(Some(SequenceRange::Gt { min: 20 }))
1499 .unwrap();
1500 assert!(batch.is_empty());
1501
1502 let mut batch = new_batch(
1504 &[1, 2, 3, 4, 5],
1505 &[11, 12, 13, 14, 15],
1506 &[
1507 OpType::Put,
1508 OpType::Put,
1509 OpType::Put,
1510 OpType::Put,
1511 OpType::Put,
1512 ],
1513 &[21, 22, 23, 24, 25],
1514 );
1515 batch
1516 .filter_by_sequence(Some(SequenceRange::GtLtEq { min: 12, max: 14 }))
1517 .unwrap();
1518 let expect = new_batch(&[3, 4], &[13, 14], &[OpType::Put, OpType::Put], &[23, 24]);
1519 assert_eq!(expect, batch);
1520
1521 let mut batch = new_batch(
1523 &[1, 2, 3, 4, 5],
1524 &[11, 12, 13, 14, 15],
1525 &[
1526 OpType::Put,
1527 OpType::Delete,
1528 OpType::Put,
1529 OpType::Delete,
1530 OpType::Put,
1531 ],
1532 &[21, 22, 23, 24, 25],
1533 );
1534 batch
1535 .filter_by_sequence(Some(SequenceRange::GtLtEq { min: 11, max: 13 }))
1536 .unwrap();
1537 let expect = new_batch(
1538 &[2, 3],
1539 &[12, 13],
1540 &[OpType::Delete, OpType::Put],
1541 &[22, 23],
1542 );
1543 assert_eq!(expect, batch);
1544
1545 let mut batch = new_batch(
1547 &[1, 2, 3, 4],
1548 &[11, 12, 13, 14],
1549 &[OpType::Put, OpType::Put, OpType::Put, OpType::Put],
1550 &[21, 22, 23, 24],
1551 );
1552 batch
1553 .filter_by_sequence(Some(SequenceRange::GtLtEq { min: 20, max: 25 }))
1554 .unwrap();
1555 assert!(batch.is_empty());
1556 }
1557
1558 #[test]
1559 fn test_merge_last_non_null_no_dup() {
1560 let mut batch = new_batch_with_u64_fields(
1561 &[1, 2],
1562 &[2, 1],
1563 &[OpType::Put, OpType::Put],
1564 &[(1, &[Some(10), None]), (2, &[Some(100), Some(200)])],
1565 );
1566 let expect = batch.clone();
1567 batch.merge_last_non_null().unwrap();
1568 assert_eq!(expect, batch);
1569 }
1570
1571 #[test]
1572 fn test_merge_last_non_null_fill_null_fields() {
1573 let mut batch = new_batch_with_u64_fields(
1575 &[1, 1, 1],
1576 &[3, 2, 1],
1577 &[OpType::Put, OpType::Put, OpType::Put],
1578 &[
1579 (1, &[None, Some(10), Some(11)]),
1580 (2, &[Some(100), Some(200), Some(300)]),
1581 ],
1582 );
1583 batch.merge_last_non_null().unwrap();
1584
1585 let expect = new_batch_with_u64_fields(
1588 &[1],
1589 &[3],
1590 &[OpType::Put],
1591 &[(1, &[Some(10)]), (2, &[Some(100)])],
1592 );
1593 assert_eq!(expect, batch);
1594 }
1595
1596 #[test]
1597 fn test_merge_last_non_null_stop_at_delete_row() {
1598 let mut batch = new_batch_with_u64_fields(
1601 &[1, 1, 1],
1602 &[3, 2, 1],
1603 &[OpType::Put, OpType::Delete, OpType::Put],
1604 &[
1605 (1, &[None, Some(10), Some(11)]),
1606 (2, &[Some(100), Some(200), Some(300)]),
1607 ],
1608 );
1609 batch.merge_last_non_null().unwrap();
1610
1611 let expect = new_batch_with_u64_fields(
1612 &[1],
1613 &[3],
1614 &[OpType::Put],
1615 &[(1, &[None]), (2, &[Some(100)])],
1616 );
1617 assert_eq!(expect, batch);
1618 }
1619
1620 #[test]
1621 fn test_merge_last_non_null_base_delete_no_merge() {
1622 let mut batch = new_batch_with_u64_fields(
1623 &[1, 1],
1624 &[3, 2],
1625 &[OpType::Delete, OpType::Put],
1626 &[(1, &[None, Some(10)]), (2, &[None, Some(200)])],
1627 );
1628 batch.merge_last_non_null().unwrap();
1629
1630 let expect =
1632 new_batch_with_u64_fields(&[1], &[3], &[OpType::Delete], &[(1, &[None]), (2, &[None])]);
1633 assert_eq!(expect, batch);
1634 }
1635
1636 #[test]
1637 fn test_merge_last_non_null_multiple_timestamp_groups() {
1638 let mut batch = new_batch_with_u64_fields(
1639 &[1, 1, 2, 3, 3],
1640 &[5, 4, 3, 2, 1],
1641 &[
1642 OpType::Put,
1643 OpType::Put,
1644 OpType::Put,
1645 OpType::Put,
1646 OpType::Put,
1647 ],
1648 &[
1649 (1, &[None, Some(10), Some(20), None, Some(30)]),
1650 (2, &[Some(100), Some(110), Some(120), None, Some(130)]),
1651 ],
1652 );
1653 batch.merge_last_non_null().unwrap();
1654
1655 let expect = new_batch_with_u64_fields(
1656 &[1, 2, 3],
1657 &[5, 3, 2],
1658 &[OpType::Put, OpType::Put, OpType::Put],
1659 &[
1660 (1, &[Some(10), Some(20), Some(30)]),
1661 (2, &[Some(100), Some(120), Some(130)]),
1662 ],
1663 );
1664 assert_eq!(expect, batch);
1665 }
1666
1667 #[test]
1668 fn test_merge_last_non_null_no_fields() {
1669 let mut batch = new_batch_without_fields(
1670 &[1, 1, 2],
1671 &[3, 2, 1],
1672 &[OpType::Put, OpType::Put, OpType::Put],
1673 );
1674 batch.merge_last_non_null().unwrap();
1675
1676 let expect = new_batch_without_fields(&[1, 2], &[3, 1], &[OpType::Put, OpType::Put]);
1677 assert_eq!(expect, batch);
1678 }
1679
1680 #[test]
1681 fn test_filter() {
1682 let mut batch = new_batch(
1684 &[1, 2, 3, 4],
1685 &[11, 12, 13, 14],
1686 &[OpType::Put, OpType::Put, OpType::Put, OpType::Put],
1687 &[21, 22, 23, 24],
1688 );
1689 let predicate = BooleanVector::from_vec(vec![false, false, true, true]);
1690 batch.filter(&predicate).unwrap();
1691 let expect = new_batch(&[3, 4], &[13, 14], &[OpType::Put, OpType::Put], &[23, 24]);
1692 assert_eq!(expect, batch);
1693
1694 let mut batch = new_batch(
1696 &[1, 2, 3, 4],
1697 &[11, 12, 13, 14],
1698 &[OpType::Put, OpType::Delete, OpType::Put, OpType::Put],
1699 &[21, 22, 23, 24],
1700 );
1701 let predicate = BooleanVector::from_vec(vec![false, false, true, true]);
1702 batch.filter(&predicate).unwrap();
1703 let expect = new_batch(&[3, 4], &[13, 14], &[OpType::Put, OpType::Put], &[23, 24]);
1704 assert_eq!(expect, batch);
1705
1706 let predicate = BooleanVector::from_vec(vec![false, false]);
1708 batch.filter(&predicate).unwrap();
1709 assert!(batch.is_empty());
1710 }
1711
1712 #[test]
1713 fn test_sort_and_dedup() {
1714 let original = new_batch(
1715 &[2, 3, 1, 4, 5, 2],
1716 &[1, 2, 3, 4, 5, 6],
1717 &[
1718 OpType::Put,
1719 OpType::Put,
1720 OpType::Put,
1721 OpType::Put,
1722 OpType::Put,
1723 OpType::Put,
1724 ],
1725 &[21, 22, 23, 24, 25, 26],
1726 );
1727
1728 let mut batch = original.clone();
1729 batch.sort(true).unwrap();
1730 assert_eq!(
1732 new_batch(
1733 &[1, 2, 3, 4, 5],
1734 &[3, 6, 2, 4, 5],
1735 &[
1736 OpType::Put,
1737 OpType::Put,
1738 OpType::Put,
1739 OpType::Put,
1740 OpType::Put,
1741 ],
1742 &[23, 26, 22, 24, 25],
1743 ),
1744 batch
1745 );
1746
1747 let mut batch = original.clone();
1748 batch.sort(false).unwrap();
1749
1750 assert_eq!(
1752 new_batch(
1753 &[1, 2, 2, 3, 4, 5],
1754 &[3, 6, 1, 2, 4, 5],
1755 &[
1756 OpType::Put,
1757 OpType::Put,
1758 OpType::Put,
1759 OpType::Put,
1760 OpType::Put,
1761 OpType::Put,
1762 ],
1763 &[23, 26, 21, 22, 24, 25],
1764 ),
1765 batch
1766 );
1767
1768 let original = new_batch(
1769 &[2, 2, 1],
1770 &[1, 6, 1],
1771 &[OpType::Delete, OpType::Put, OpType::Put],
1772 &[21, 22, 23],
1773 );
1774
1775 let mut batch = original.clone();
1776 batch.sort(true).unwrap();
1777 let expect = new_batch(&[1, 2], &[1, 6], &[OpType::Put, OpType::Put], &[23, 22]);
1778 assert_eq!(expect, batch);
1779
1780 let mut batch = original.clone();
1781 batch.sort(false).unwrap();
1782 let expect = new_batch(
1783 &[1, 2, 2],
1784 &[1, 6, 1],
1785 &[OpType::Put, OpType::Put, OpType::Delete],
1786 &[23, 22, 21],
1787 );
1788 assert_eq!(expect, batch);
1789 }
1790
1791 #[test]
1792 fn test_get_value() {
1793 let encodings = [PrimaryKeyEncoding::Dense, PrimaryKeyEncoding::Sparse];
1794
1795 for encoding in encodings {
1796 let codec = build_primary_key_codec_with_fields(
1797 encoding,
1798 [
1799 (
1800 ReservedColumnId::table_id(),
1801 row_converter::SortField::new(ConcreteDataType::uint32_datatype()),
1802 ),
1803 (
1804 ReservedColumnId::tsid(),
1805 row_converter::SortField::new(ConcreteDataType::uint64_datatype()),
1806 ),
1807 (
1808 100,
1809 row_converter::SortField::new(ConcreteDataType::string_datatype()),
1810 ),
1811 (
1812 200,
1813 row_converter::SortField::new(ConcreteDataType::string_datatype()),
1814 ),
1815 ]
1816 .into_iter(),
1817 );
1818
1819 let values = [
1820 Value::UInt32(1000),
1821 Value::UInt64(2000),
1822 Value::String("abcdefgh".into()),
1823 Value::String("zyxwvu".into()),
1824 ];
1825 let mut buf = vec![];
1826 codec
1827 .encode_values(
1828 &[
1829 (ReservedColumnId::table_id(), values[0].clone()),
1830 (ReservedColumnId::tsid(), values[1].clone()),
1831 (100, values[2].clone()),
1832 (200, values[3].clone()),
1833 ],
1834 &mut buf,
1835 )
1836 .unwrap();
1837
1838 let field_col_id = 2;
1839 let mut batch = new_batch_builder(
1840 &buf,
1841 &[1, 2, 3],
1842 &[1, 1, 1],
1843 &[OpType::Put, OpType::Put, OpType::Put],
1844 field_col_id,
1845 &[42, 43, 44],
1846 )
1847 .build()
1848 .unwrap();
1849
1850 let v = batch
1851 .pk_col_value(&*codec, 0, ReservedColumnId::table_id())
1852 .unwrap()
1853 .unwrap();
1854 assert_eq!(values[0], *v);
1855
1856 let v = batch
1857 .pk_col_value(&*codec, 1, ReservedColumnId::tsid())
1858 .unwrap()
1859 .unwrap();
1860 assert_eq!(values[1], *v);
1861
1862 let v = batch.pk_col_value(&*codec, 2, 100).unwrap().unwrap();
1863 assert_eq!(values[2], *v);
1864
1865 let v = batch.pk_col_value(&*codec, 3, 200).unwrap().unwrap();
1866 assert_eq!(values[3], *v);
1867
1868 let v = batch.field_col_value(field_col_id).unwrap();
1869 assert_eq!(v.data.get(0), Value::UInt64(42));
1870 assert_eq!(v.data.get(1), Value::UInt64(43));
1871 assert_eq!(v.data.get(2), Value::UInt64(44));
1872 }
1873 }
1874}