| 1 | #include "duckdb/storage/checkpoint/table_data_writer.hpp" |
| 2 | |
| 3 | #include "duckdb/catalog/catalog_entry/duck_table_entry.hpp" |
| 4 | #include "duckdb/catalog/catalog_entry/table_catalog_entry.hpp" |
| 5 | #include "duckdb/common/vector_operations/vector_operations.hpp" |
| 6 | #include "duckdb/common/serializer/buffered_serializer.hpp" |
| 7 | #include "duckdb/storage/table/column_checkpoint_state.hpp" |
| 8 | #include "duckdb/storage/table/table_statistics.hpp" |
| 9 | |
| 10 | namespace duckdb { |
| 11 | |
| 12 | TableDataWriter::TableDataWriter(TableCatalogEntry &table_p) : table(table_p.Cast<DuckTableEntry>()) { |
| 13 | D_ASSERT(table_p.IsDuckTable()); |
| 14 | } |
| 15 | |
| 16 | TableDataWriter::~TableDataWriter() { |
| 17 | } |
| 18 | |
| 19 | void TableDataWriter::WriteTableData() { |
| 20 | // start scanning the table and append the data to the uncompressed segments |
| 21 | table.GetStorage().Checkpoint(writer&: *this); |
| 22 | } |
| 23 | |
| 24 | CompressionType TableDataWriter::GetColumnCompressionType(idx_t i) { |
| 25 | return table.GetColumn(idx: LogicalIndex(i)).CompressionType(); |
| 26 | } |
| 27 | |
| 28 | void TableDataWriter::AddRowGroup(RowGroupPointer &&row_group_pointer, unique_ptr<RowGroupWriter> &&writer) { |
| 29 | row_group_pointers.push_back(x: std::move(row_group_pointer)); |
| 30 | writer.reset(); |
| 31 | } |
| 32 | |
| 33 | SingleFileTableDataWriter::SingleFileTableDataWriter(SingleFileCheckpointWriter &checkpoint_manager, |
| 34 | TableCatalogEntry &table, MetaBlockWriter &table_data_writer, |
| 35 | MetaBlockWriter &meta_data_writer) |
| 36 | : TableDataWriter(table), checkpoint_manager(checkpoint_manager), table_data_writer(table_data_writer), |
| 37 | meta_data_writer(meta_data_writer) { |
| 38 | } |
| 39 | |
| 40 | unique_ptr<RowGroupWriter> SingleFileTableDataWriter::GetRowGroupWriter(RowGroup &row_group) { |
| 41 | return make_uniq<SingleFileRowGroupWriter>(args&: table, args&: checkpoint_manager.partial_block_manager, args&: table_data_writer); |
| 42 | } |
| 43 | |
| 44 | void SingleFileTableDataWriter::FinalizeTable(TableStatistics &&global_stats, DataTableInfo *info) { |
| 45 | // store the current position in the metadata writer |
| 46 | // this is where the row groups for this table start |
| 47 | auto pointer = table_data_writer.GetBlockPointer(); |
| 48 | |
| 49 | global_stats.Serialize(serializer&: table_data_writer); |
| 50 | |
| 51 | // now start writing the row group pointers to disk |
| 52 | table_data_writer.Write<uint64_t>(element: row_group_pointers.size()); |
| 53 | idx_t total_rows = 0; |
| 54 | for (auto &row_group_pointer : row_group_pointers) { |
| 55 | auto row_group_count = row_group_pointer.row_start + row_group_pointer.tuple_count; |
| 56 | if (row_group_count > total_rows) { |
| 57 | total_rows = row_group_count; |
| 58 | } |
| 59 | RowGroup::Serialize(pointer&: row_group_pointer, serializer&: table_data_writer); |
| 60 | } |
| 61 | |
| 62 | // Pointer to the table itself goes to the metadata stream. |
| 63 | meta_data_writer.Write<block_id_t>(element: pointer.block_id); |
| 64 | meta_data_writer.Write<uint64_t>(element: pointer.offset); |
| 65 | meta_data_writer.Write<idx_t>(element: total_rows); |
| 66 | |
| 67 | // Now we serialize indexes in the table_metadata_writer |
| 68 | vector<BlockPointer> index_pointers = info->indexes.SerializeIndexes(writer&: table_data_writer); |
| 69 | |
| 70 | // Write-off to metadata block ids and offsets of indexes |
| 71 | meta_data_writer.Write<idx_t>(element: index_pointers.size()); |
| 72 | for (auto &block_info : index_pointers) { |
| 73 | meta_data_writer.Write<idx_t>(element: block_info.block_id); |
| 74 | meta_data_writer.Write<idx_t>(element: block_info.offset); |
| 75 | } |
| 76 | } |
| 77 | |
| 78 | } // namespace duckdb |
| 79 | |