duckdb 1.1.4-dev13.0 → 1.1.4-dev14.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (219) hide show
  1. package/binding.gyp +1 -0
  2. package/package.json +1 -1
  3. package/src/duckdb/extension/core_functions/function_list.cpp +1 -0
  4. package/src/duckdb/extension/core_functions/include/core_functions/scalar/map_functions.hpp +9 -0
  5. package/src/duckdb/extension/core_functions/scalar/date/current.cpp +1 -0
  6. package/src/duckdb/extension/core_functions/scalar/generic/can_implicitly_cast.cpp +2 -2
  7. package/src/duckdb/extension/core_functions/scalar/generic/typeof.cpp +1 -1
  8. package/src/duckdb/extension/core_functions/scalar/list/flatten.cpp +91 -61
  9. package/src/duckdb/extension/core_functions/scalar/map/map_extract.cpp +89 -8
  10. package/src/duckdb/extension/icu/icu-current.cpp +63 -0
  11. package/src/duckdb/extension/icu/icu-makedate.cpp +43 -39
  12. package/src/duckdb/extension/icu/icu-timezone.cpp +63 -63
  13. package/src/duckdb/extension/icu/icu_extension.cpp +2 -0
  14. package/src/duckdb/extension/icu/include/icu-casts.hpp +39 -0
  15. package/src/duckdb/extension/icu/include/icu-current.hpp +17 -0
  16. package/src/duckdb/extension/icu/third_party/icu/stubdata/stubdata.cpp +1 -1
  17. package/src/duckdb/extension/json/json_functions/json_structure.cpp +3 -1
  18. package/src/duckdb/extension/parquet/column_writer.cpp +26 -18
  19. package/src/duckdb/extension/parquet/include/parquet_reader.hpp +0 -6
  20. package/src/duckdb/extension/parquet/include/parquet_writer.hpp +15 -1
  21. package/src/duckdb/extension/parquet/include/resizable_buffer.hpp +1 -0
  22. package/src/duckdb/extension/parquet/parquet_extension.cpp +67 -15
  23. package/src/duckdb/extension/parquet/parquet_reader.cpp +5 -3
  24. package/src/duckdb/extension/parquet/parquet_writer.cpp +5 -6
  25. package/src/duckdb/src/catalog/catalog.cpp +21 -8
  26. package/src/duckdb/src/catalog/catalog_search_path.cpp +17 -1
  27. package/src/duckdb/src/catalog/catalog_set.cpp +1 -1
  28. package/src/duckdb/src/catalog/default/default_functions.cpp +0 -3
  29. package/src/duckdb/src/catalog/dependency_list.cpp +7 -0
  30. package/src/duckdb/src/common/adbc/adbc.cpp +1 -56
  31. package/src/duckdb/src/common/arrow/arrow_converter.cpp +3 -2
  32. package/src/duckdb/src/common/arrow/arrow_type_extension.cpp +58 -28
  33. package/src/duckdb/src/common/arrow/schema_metadata.cpp +1 -1
  34. package/src/duckdb/src/common/compressed_file_system.cpp +6 -2
  35. package/src/duckdb/src/common/enum_util.cpp +26 -22
  36. package/src/duckdb/src/common/error_data.cpp +3 -2
  37. package/src/duckdb/src/common/gzip_file_system.cpp +8 -8
  38. package/src/duckdb/src/common/local_file_system.cpp +2 -2
  39. package/src/duckdb/src/common/multi_file_reader.cpp +1 -1
  40. package/src/duckdb/src/common/random_engine.cpp +4 -1
  41. package/src/duckdb/src/common/serializer/memory_stream.cpp +23 -19
  42. package/src/duckdb/src/common/serializer/serializer.cpp +1 -1
  43. package/src/duckdb/src/common/types/bit.cpp +1 -1
  44. package/src/duckdb/src/common/types/column/column_data_allocator.cpp +0 -5
  45. package/src/duckdb/src/common/types/column/column_data_collection.cpp +4 -1
  46. package/src/duckdb/src/common/types/data_chunk.cpp +2 -1
  47. package/src/duckdb/src/common/types/row/tuple_data_segment.cpp +0 -4
  48. package/src/duckdb/src/common/types.cpp +1 -1
  49. package/src/duckdb/src/execution/index/art/art.cpp +52 -42
  50. package/src/duckdb/src/execution/index/art/leaf.cpp +4 -9
  51. package/src/duckdb/src/execution/index/art/node.cpp +13 -13
  52. package/src/duckdb/src/execution/index/art/prefix.cpp +21 -16
  53. package/src/duckdb/src/execution/index/bound_index.cpp +6 -8
  54. package/src/duckdb/src/execution/index/fixed_size_allocator.cpp +39 -34
  55. package/src/duckdb/src/execution/index/fixed_size_buffer.cpp +2 -1
  56. package/src/duckdb/src/execution/index/unbound_index.cpp +10 -0
  57. package/src/duckdb/src/execution/operator/aggregate/physical_streaming_window.cpp +62 -44
  58. package/src/duckdb/src/execution/operator/csv_scanner/scanner/column_count_scanner.cpp +26 -0
  59. package/src/duckdb/src/execution/operator/csv_scanner/scanner/string_value_scanner.cpp +69 -40
  60. package/src/duckdb/src/execution/operator/csv_scanner/sniffer/dialect_detection.cpp +3 -7
  61. package/src/duckdb/src/execution/operator/csv_scanner/sniffer/header_detection.cpp +11 -5
  62. package/src/duckdb/src/execution/operator/csv_scanner/sniffer/type_detection.cpp +4 -0
  63. package/src/duckdb/src/execution/operator/csv_scanner/state_machine/csv_state_machine_cache.cpp +8 -8
  64. package/src/duckdb/src/execution/operator/csv_scanner/util/csv_error.cpp +36 -12
  65. package/src/duckdb/src/execution/operator/csv_scanner/util/csv_reader_options.cpp +12 -9
  66. package/src/duckdb/src/execution/operator/join/physical_hash_join.cpp +0 -1
  67. package/src/duckdb/src/execution/operator/persistent/physical_copy_database.cpp +29 -1
  68. package/src/duckdb/src/execution/operator/persistent/physical_delete.cpp +58 -10
  69. package/src/duckdb/src/execution/operator/persistent/physical_insert.cpp +58 -35
  70. package/src/duckdb/src/execution/operator/schema/physical_create_art_index.cpp +2 -1
  71. package/src/duckdb/src/execution/radix_partitioned_hashtable.cpp +9 -4
  72. package/src/duckdb/src/execution/sample/reservoir_sample.cpp +7 -6
  73. package/src/duckdb/src/function/compression_config.cpp +4 -0
  74. package/src/duckdb/src/function/function_binder.cpp +1 -1
  75. package/src/duckdb/src/function/scalar/system/write_log.cpp +2 -2
  76. package/src/duckdb/src/function/table/arrow/arrow_duck_schema.cpp +15 -2
  77. package/src/duckdb/src/function/table/arrow_conversion.cpp +10 -10
  78. package/src/duckdb/src/function/table/copy_csv.cpp +8 -5
  79. package/src/duckdb/src/function/table/read_csv.cpp +21 -4
  80. package/src/duckdb/src/function/table/sniff_csv.cpp +7 -0
  81. package/src/duckdb/src/function/table/system/duckdb_extensions.cpp +4 -0
  82. package/src/duckdb/src/function/table/system/duckdb_secret_types.cpp +71 -0
  83. package/src/duckdb/src/function/table/system_functions.cpp +1 -0
  84. package/src/duckdb/src/function/table/table_scan.cpp +120 -36
  85. package/src/duckdb/src/function/table/version/pragma_version.cpp +4 -4
  86. package/src/duckdb/src/function/window/window_aggregate_function.cpp +6 -1
  87. package/src/duckdb/src/function/window/window_boundaries_state.cpp +135 -11
  88. package/src/duckdb/src/function/window/window_segment_tree.cpp +50 -22
  89. package/src/duckdb/src/function/window/window_token_tree.cpp +4 -3
  90. package/src/duckdb/src/include/duckdb/catalog/catalog.hpp +4 -0
  91. package/src/duckdb/src/include/duckdb/catalog/catalog_search_path.hpp +2 -0
  92. package/src/duckdb/src/include/duckdb/catalog/dependency_list.hpp +1 -0
  93. package/src/duckdb/src/include/duckdb/common/arrow/arrow_type_extension.hpp +4 -2
  94. package/src/duckdb/src/include/duckdb/common/enum_util.hpp +8 -8
  95. package/src/duckdb/src/include/duckdb/common/multi_file_reader.hpp +0 -2
  96. package/src/duckdb/src/include/duckdb/common/serializer/deserializer.hpp +8 -3
  97. package/src/duckdb/src/include/duckdb/common/serializer/memory_stream.hpp +6 -1
  98. package/src/duckdb/src/include/duckdb/common/serializer/serialization_data.hpp +25 -0
  99. package/src/duckdb/src/include/duckdb/common/serializer/serializer.hpp +9 -3
  100. package/src/duckdb/src/include/duckdb/common/types/selection_vector.hpp +1 -1
  101. package/src/duckdb/src/include/duckdb/execution/index/art/art.hpp +11 -14
  102. package/src/duckdb/src/include/duckdb/execution/index/art/prefix.hpp +5 -4
  103. package/src/duckdb/src/include/duckdb/execution/index/bound_index.hpp +21 -10
  104. package/src/duckdb/src/include/duckdb/execution/index/fixed_size_allocator.hpp +6 -5
  105. package/src/duckdb/src/include/duckdb/execution/index/fixed_size_buffer.hpp +37 -32
  106. package/src/duckdb/src/include/duckdb/execution/operator/csv_scanner/base_scanner.hpp +36 -1
  107. package/src/duckdb/src/include/duckdb/execution/operator/csv_scanner/column_count_scanner.hpp +3 -0
  108. package/src/duckdb/src/include/duckdb/execution/operator/csv_scanner/sniffer/csv_sniffer.hpp +2 -0
  109. package/src/duckdb/src/include/duckdb/execution/operator/csv_scanner/state_machine_options.hpp +5 -5
  110. package/src/duckdb/src/include/duckdb/execution/operator/csv_scanner/string_value_scanner.hpp +5 -30
  111. package/src/duckdb/src/include/duckdb/execution/reservoir_sample.hpp +7 -1
  112. package/src/duckdb/src/include/duckdb/function/scalar_function.hpp +3 -3
  113. package/src/duckdb/src/include/duckdb/function/table/arrow/arrow_duck_schema.hpp +1 -0
  114. package/src/duckdb/src/include/duckdb/function/table/system_functions.hpp +4 -0
  115. package/src/duckdb/src/include/duckdb/function/window/window_boundaries_state.hpp +2 -2
  116. package/src/duckdb/src/include/duckdb/logging/logger.hpp +40 -119
  117. package/src/duckdb/src/include/duckdb/logging/logging.hpp +0 -2
  118. package/src/duckdb/src/include/duckdb/main/config.hpp +5 -0
  119. package/src/duckdb/src/include/duckdb/main/connection.hpp +0 -8
  120. package/src/duckdb/src/include/duckdb/main/connection_manager.hpp +2 -1
  121. package/src/duckdb/src/include/duckdb/main/extension.hpp +1 -0
  122. package/src/duckdb/src/include/duckdb/main/extension_entries.hpp +11 -7
  123. package/src/duckdb/src/include/duckdb/main/extension_helper.hpp +1 -0
  124. package/src/duckdb/src/include/duckdb/main/secret/secret.hpp +2 -0
  125. package/src/duckdb/src/include/duckdb/main/secret/secret_manager.hpp +3 -0
  126. package/src/duckdb/src/include/duckdb/main/settings.hpp +10 -0
  127. package/src/duckdb/src/include/duckdb/parser/constraint.hpp +9 -0
  128. package/src/duckdb/src/include/duckdb/parser/expression/window_expression.hpp +36 -9
  129. package/src/duckdb/src/include/duckdb/parser/parsed_data/create_view_info.hpp +2 -1
  130. package/src/duckdb/src/include/duckdb/parser/query_node/set_operation_node.hpp +8 -2
  131. package/src/duckdb/src/include/duckdb/planner/binder.hpp +4 -0
  132. package/src/duckdb/src/include/duckdb/planner/expression/bound_parameter_data.hpp +9 -1
  133. package/src/duckdb/src/include/duckdb/planner/filter/constant_filter.hpp +1 -0
  134. package/src/duckdb/src/include/duckdb/planner/filter/in_filter.hpp +0 -2
  135. package/src/duckdb/src/include/duckdb/planner/filter/optional_filter.hpp +4 -4
  136. package/src/duckdb/src/include/duckdb/planner/table_filter.hpp +1 -1
  137. package/src/duckdb/src/include/duckdb/storage/data_table.hpp +14 -10
  138. package/src/duckdb/src/include/duckdb/storage/index_storage_info.hpp +4 -0
  139. package/src/duckdb/src/include/duckdb/storage/single_file_block_manager.hpp +6 -1
  140. package/src/duckdb/src/include/duckdb/storage/storage_info.hpp +7 -2
  141. package/src/duckdb/src/include/duckdb/storage/storage_manager.hpp +9 -0
  142. package/src/duckdb/src/include/duckdb/storage/storage_options.hpp +2 -0
  143. package/src/duckdb/src/include/duckdb/storage/string_uncompressed.hpp +4 -3
  144. package/src/duckdb/src/include/duckdb/storage/table/column_data.hpp +2 -0
  145. package/src/duckdb/src/include/duckdb/storage/table/table_index_list.hpp +6 -4
  146. package/src/duckdb/src/include/duckdb/storage/table/table_statistics.hpp +1 -1
  147. package/src/duckdb/src/include/duckdb/storage/write_ahead_log.hpp +2 -0
  148. package/src/duckdb/src/include/duckdb/transaction/local_storage.hpp +2 -0
  149. package/src/duckdb/src/include/duckdb/transaction/meta_transaction.hpp +1 -1
  150. package/src/duckdb/src/logging/logger.cpp +8 -66
  151. package/src/duckdb/src/main/attached_database.cpp +3 -1
  152. package/src/duckdb/src/main/client_context.cpp +4 -2
  153. package/src/duckdb/src/main/config.cpp +20 -2
  154. package/src/duckdb/src/main/connection.cpp +2 -29
  155. package/src/duckdb/src/main/connection_manager.cpp +5 -3
  156. package/src/duckdb/src/main/database.cpp +2 -2
  157. package/src/duckdb/src/main/extension/extension_helper.cpp +4 -5
  158. package/src/duckdb/src/main/extension/extension_install.cpp +23 -10
  159. package/src/duckdb/src/main/extension/extension_load.cpp +6 -7
  160. package/src/duckdb/src/main/extension.cpp +27 -9
  161. package/src/duckdb/src/main/secret/secret_manager.cpp +11 -0
  162. package/src/duckdb/src/main/settings/custom_settings.cpp +44 -0
  163. package/src/duckdb/src/optimizer/column_lifetime_analyzer.cpp +6 -0
  164. package/src/duckdb/src/optimizer/filter_combiner.cpp +13 -3
  165. package/src/duckdb/src/optimizer/filter_pushdown.cpp +33 -6
  166. package/src/duckdb/src/optimizer/late_materialization.cpp +14 -3
  167. package/src/duckdb/src/optimizer/remove_unused_columns.cpp +0 -3
  168. package/src/duckdb/src/parser/parsed_data/attach_info.cpp +5 -1
  169. package/src/duckdb/src/parser/parsed_data/create_view_info.cpp +6 -3
  170. package/src/duckdb/src/parser/query_node/set_operation_node.cpp +49 -0
  171. package/src/duckdb/src/parser/transform/expression/transform_columnref.cpp +1 -0
  172. package/src/duckdb/src/parser/transform/expression/transform_function.cpp +50 -12
  173. package/src/duckdb/src/planner/binder/expression/bind_columnref_expression.cpp +7 -5
  174. package/src/duckdb/src/planner/binder/expression/bind_comparison_expression.cpp +1 -0
  175. package/src/duckdb/src/planner/binder/expression/bind_operator_expression.cpp +2 -2
  176. package/src/duckdb/src/planner/binder/expression/bind_star_expression.cpp +12 -2
  177. package/src/duckdb/src/planner/binder/statement/bind_copy_database.cpp +0 -1
  178. package/src/duckdb/src/planner/binder/statement/bind_create.cpp +55 -39
  179. package/src/duckdb/src/planner/binder/statement/bind_execute.cpp +2 -1
  180. package/src/duckdb/src/planner/binder/tableref/bind_basetableref.cpp +15 -7
  181. package/src/duckdb/src/planner/binder/tableref/bind_showref.cpp +13 -8
  182. package/src/duckdb/src/planner/binder/tableref/bind_table_function.cpp +8 -3
  183. package/src/duckdb/src/planner/expression/bound_function_expression.cpp +17 -1
  184. package/src/duckdb/src/planner/expression_binder/index_binder.cpp +1 -0
  185. package/src/duckdb/src/planner/filter/conjunction_filter.cpp +1 -0
  186. package/src/duckdb/src/planner/filter/constant_filter.cpp +21 -0
  187. package/src/duckdb/src/planner/filter/in_filter.cpp +4 -7
  188. package/src/duckdb/src/planner/logical_operator.cpp +5 -3
  189. package/src/duckdb/src/planner/planner.cpp +1 -1
  190. package/src/duckdb/src/planner/subquery/flatten_dependent_join.cpp +2 -0
  191. package/src/duckdb/src/storage/checkpoint/table_data_writer.cpp +3 -4
  192. package/src/duckdb/src/storage/checkpoint_manager.cpp +3 -5
  193. package/src/duckdb/src/storage/compression/dictionary/decompression.cpp +4 -4
  194. package/src/duckdb/src/storage/compression/fsst.cpp +2 -2
  195. package/src/duckdb/src/storage/compression/roaring/common.cpp +10 -1
  196. package/src/duckdb/src/storage/compression/string_uncompressed.cpp +11 -6
  197. package/src/duckdb/src/storage/compression/validity_uncompressed.cpp +4 -0
  198. package/src/duckdb/src/storage/compression/zstd.cpp +6 -0
  199. package/src/duckdb/src/storage/data_table.cpp +104 -109
  200. package/src/duckdb/src/storage/local_storage.cpp +8 -6
  201. package/src/duckdb/src/storage/magic_bytes.cpp +1 -1
  202. package/src/duckdb/src/storage/serialization/serialize_dependency.cpp +3 -3
  203. package/src/duckdb/src/storage/serialization/serialize_nodes.cpp +3 -3
  204. package/src/duckdb/src/storage/serialization/serialize_query_node.cpp +7 -5
  205. package/src/duckdb/src/storage/single_file_block_manager.cpp +95 -28
  206. package/src/duckdb/src/storage/storage_info.cpp +38 -0
  207. package/src/duckdb/src/storage/storage_manager.cpp +11 -0
  208. package/src/duckdb/src/storage/table/column_data.cpp +4 -0
  209. package/src/duckdb/src/storage/table/column_data_checkpointer.cpp +3 -3
  210. package/src/duckdb/src/storage/table/row_group_collection.cpp +67 -68
  211. package/src/duckdb/src/storage/table/table_statistics.cpp +4 -4
  212. package/src/duckdb/src/storage/table_index_list.cpp +41 -15
  213. package/src/duckdb/src/storage/wal_replay.cpp +3 -1
  214. package/src/duckdb/src/storage/write_ahead_log.cpp +11 -4
  215. package/src/duckdb/src/transaction/meta_transaction.cpp +1 -1
  216. package/src/duckdb/src/verification/deserialized_statement_verifier.cpp +2 -1
  217. package/src/duckdb/third_party/httplib/httplib.hpp +0 -1
  218. package/src/duckdb/third_party/re2/util/logging.h +10 -10
  219. package/src/duckdb/ub_src_function_table_system.cpp +2 -0
@@ -339,7 +339,8 @@ void DataTable::AddIndex(unique_ptr<Index> index) {
339
339
  }
340
340
 
341
341
  bool DataTable::HasForeignKeyIndex(const vector<PhysicalIndex> &keys, ForeignKeyType type) {
342
- return info->indexes.FindForeignKeyIndex(keys, type) != nullptr;
342
+ auto index = info->indexes.FindForeignKeyIndex(keys, type);
343
+ return index != nullptr;
343
344
  }
344
345
 
345
346
  void DataTable::SetIndexStorageInfo(vector<IndexStorageInfo> index_storage_info) {
@@ -466,28 +467,6 @@ static void VerifyCheckConstraint(ClientContext &context, TableCatalogEntry &tab
466
467
  }
467
468
  }
468
469
 
469
- bool DataTable::IsForeignKeyIndex(const vector<PhysicalIndex> &fk_keys, Index &index, ForeignKeyType fk_type) {
470
- if (fk_type == ForeignKeyType::FK_TYPE_PRIMARY_KEY_TABLE ? !index.IsUnique() : !index.IsForeign()) {
471
- return false;
472
- }
473
- if (fk_keys.size() != index.GetColumnIds().size()) {
474
- return false;
475
- }
476
- for (auto &fk_key : fk_keys) {
477
- bool is_found = false;
478
- for (auto &index_key : index.GetColumnIds()) {
479
- if (fk_key.index == index_key) {
480
- is_found = true;
481
- break;
482
- }
483
- }
484
- if (!is_found) {
485
- return false;
486
- }
487
- }
488
- return true;
489
- }
490
-
491
470
  // Find the first index that is not null, and did not find a match
492
471
  static idx_t FirstMissingMatch(const ManagedSelection &matches) {
493
472
  idx_t match_idx = 0;
@@ -537,65 +516,71 @@ static bool IsAppend(VerifyExistenceType verify_type) {
537
516
  return verify_type == VerifyExistenceType::APPEND_FK;
538
517
  }
539
518
 
540
- void DataTable::VerifyForeignKeyConstraint(const BoundForeignKeyConstraint &bfk, ClientContext &context,
519
+ void DataTable::VerifyForeignKeyConstraint(optional_ptr<LocalTableStorage> storage,
520
+ const BoundForeignKeyConstraint &bound_foreign_key, ClientContext &context,
541
521
  DataChunk &chunk, VerifyExistenceType verify_type) {
542
- const vector<PhysicalIndex> *src_keys_ptr = &bfk.info.fk_keys;
543
- const vector<PhysicalIndex> *dst_keys_ptr = &bfk.info.pk_keys;
522
+ reference<const vector<PhysicalIndex>> src_keys_ptr = bound_foreign_key.info.fk_keys;
523
+ reference<const vector<PhysicalIndex>> dst_keys_ptr = bound_foreign_key.info.pk_keys;
544
524
 
545
525
  bool is_append = IsAppend(verify_type);
546
526
  if (!is_append) {
547
- src_keys_ptr = &bfk.info.pk_keys;
548
- dst_keys_ptr = &bfk.info.fk_keys;
527
+ src_keys_ptr = bound_foreign_key.info.pk_keys;
528
+ dst_keys_ptr = bound_foreign_key.info.fk_keys;
549
529
  }
550
530
 
551
- auto &table_entry_ptr =
552
- Catalog::GetEntry<TableCatalogEntry>(context, db.GetName(), bfk.info.schema, bfk.info.table);
553
- // make the data chunk to check
531
+ // Get the column types in their physical order.
532
+ auto &table_entry = Catalog::GetEntry<TableCatalogEntry>(context, db.GetName(), bound_foreign_key.info.schema,
533
+ bound_foreign_key.info.table);
554
534
  vector<LogicalType> types;
555
- for (auto &col : table_entry_ptr.GetColumns().Physical()) {
535
+ for (auto &col : table_entry.GetColumns().Physical()) {
556
536
  types.emplace_back(col.Type());
557
537
  }
538
+
539
+ // Create the data chunk that has to be verified.
558
540
  DataChunk dst_chunk;
559
541
  dst_chunk.InitializeEmpty(types);
560
- for (idx_t i = 0; i < src_keys_ptr->size(); i++) {
561
- dst_chunk.data[(*dst_keys_ptr)[i].index].Reference(chunk.data[(*src_keys_ptr)[i].index]);
542
+ for (idx_t i = 0; i < src_keys_ptr.get().size(); i++) {
543
+ auto &src_chunk = chunk.data[src_keys_ptr.get()[i].index];
544
+ dst_chunk.data[dst_keys_ptr.get()[i].index].Reference(src_chunk);
562
545
  }
563
- dst_chunk.SetCardinality(chunk.size());
564
- auto &data_table = table_entry_ptr.GetStorage();
565
546
 
566
- idx_t count = dst_chunk.size();
547
+ auto count = chunk.size();
548
+ dst_chunk.SetCardinality(count);
567
549
  if (count <= 0) {
568
550
  return;
569
551
  }
570
552
 
571
- // Set up a way to record conflicts, rather than directly throw on them
553
+ // Record conflicts instead of throwing immediately.
572
554
  unordered_set<column_t> empty_column_list;
573
555
  ConflictInfo empty_conflict_info(empty_column_list, false);
574
- ConflictManager regular_conflicts(verify_type, count, &empty_conflict_info);
575
- ConflictManager transaction_conflicts(verify_type, count, &empty_conflict_info);
576
- regular_conflicts.SetMode(ConflictManagerMode::SCAN);
577
- transaction_conflicts.SetMode(ConflictManagerMode::SCAN);
578
-
579
- data_table.info->indexes.VerifyForeignKey(*dst_keys_ptr, dst_chunk, regular_conflicts);
580
- regular_conflicts.Finalize();
581
- auto &regular_matches = regular_conflicts.Conflicts();
582
-
583
- // check if we can insert the chunk into the reference table's local storage
556
+ ConflictManager global_conflicts(verify_type, count, &empty_conflict_info);
557
+ ConflictManager local_conflicts(verify_type, count, &empty_conflict_info);
558
+ global_conflicts.SetMode(ConflictManagerMode::SCAN);
559
+ local_conflicts.SetMode(ConflictManagerMode::SCAN);
560
+
561
+ // Global constraint verification.
562
+ auto &data_table = table_entry.GetStorage();
563
+ data_table.info->indexes.VerifyForeignKey(storage, dst_keys_ptr, dst_chunk, global_conflicts);
564
+ global_conflicts.Finalize();
565
+ auto &global_matches = global_conflicts.Conflicts();
566
+
567
+ // Check if we can insert the chunk into the local storage.
584
568
  auto &local_storage = LocalStorage::Get(context, db);
585
- bool error = IsForeignKeyConstraintError(is_append, count, regular_matches);
586
- bool transaction_error = false;
587
- bool transaction_check = local_storage.Find(data_table);
569
+ bool local_error = false;
570
+ auto local_verification = local_storage.Find(data_table);
588
571
 
589
- if (transaction_check) {
590
- auto &transact_index = local_storage.GetIndexes(data_table);
591
- transact_index.VerifyForeignKey(*dst_keys_ptr, dst_chunk, transaction_conflicts);
592
- transaction_conflicts.Finalize();
593
- auto &transaction_matches = transaction_conflicts.Conflicts();
594
- transaction_error = IsForeignKeyConstraintError(is_append, count, transaction_matches);
572
+ // Local constraint verification.
573
+ if (local_verification) {
574
+ auto &local_indexes = local_storage.GetIndexes(data_table);
575
+ local_indexes.VerifyForeignKey(storage, dst_keys_ptr, dst_chunk, local_conflicts);
576
+ local_conflicts.Finalize();
577
+ auto &local_matches = local_conflicts.Conflicts();
578
+ local_error = IsForeignKeyConstraintError(is_append, count, local_matches);
595
579
  }
596
580
 
597
- if (!transaction_error && !error) {
598
- // No error occurred;
581
+ // No constraint violation.
582
+ auto global_error = IsForeignKeyConstraintError(is_append, count, global_matches);
583
+ if (!global_error && !local_error) {
599
584
  return;
600
585
  }
601
586
 
@@ -605,29 +590,29 @@ void DataTable::VerifyForeignKeyConstraint(const BoundForeignKeyConstraint &bfk,
605
590
 
606
591
  auto fk_type = is_append ? ForeignKeyType::FK_TYPE_PRIMARY_KEY_TABLE : ForeignKeyType::FK_TYPE_FOREIGN_KEY_TABLE;
607
592
  // check whether or not the chunk can be inserted or deleted into the referenced table' storage
608
- index = data_table.info->indexes.FindForeignKeyIndex(*dst_keys_ptr, fk_type);
609
- if (transaction_check) {
593
+ index = data_table.info->indexes.FindForeignKeyIndex(dst_keys_ptr, fk_type);
594
+ if (local_verification) {
610
595
  auto &transact_index = local_storage.GetIndexes(data_table);
611
596
  // check whether or not the chunk can be inserted or deleted into the referenced table' storage
612
- transaction_index = transact_index.FindForeignKeyIndex(*dst_keys_ptr, fk_type);
597
+ transaction_index = transact_index.FindForeignKeyIndex(dst_keys_ptr, fk_type);
613
598
  }
614
599
 
615
- if (!transaction_check) {
600
+ if (!local_verification) {
616
601
  // Only local state is checked, throw the error
617
- D_ASSERT(error);
618
- auto failed_index = LocateErrorIndex(is_append, regular_matches);
602
+ D_ASSERT(global_error);
603
+ auto failed_index = LocateErrorIndex(is_append, global_matches);
619
604
  D_ASSERT(failed_index != DConstants::INVALID_INDEX);
620
605
  ThrowForeignKeyConstraintError(failed_index, is_append, *index, dst_chunk);
621
606
  }
622
- if (transaction_error && error && is_append) {
607
+ if (local_error && global_error && is_append) {
623
608
  // When we want to do an append, we only throw if the foreign key does not exist in both transaction and local
624
609
  // storage
625
- auto &transaction_matches = transaction_conflicts.Conflicts();
610
+ auto &transaction_matches = local_conflicts.Conflicts();
626
611
  idx_t failed_index = DConstants::INVALID_INDEX;
627
612
  idx_t regular_idx = 0;
628
613
  idx_t transaction_idx = 0;
629
614
  for (idx_t i = 0; i < count; i++) {
630
- bool in_regular = regular_matches.IndexMapsToLocation(regular_idx, i);
615
+ bool in_regular = global_matches.IndexMapsToLocation(regular_idx, i);
631
616
  regular_idx += in_regular;
632
617
  bool in_transaction = transaction_matches.IndexMapsToLocation(transaction_idx, i);
633
618
  transaction_idx += in_transaction;
@@ -646,14 +631,14 @@ void DataTable::VerifyForeignKeyConstraint(const BoundForeignKeyConstraint &bfk,
646
631
  ThrowForeignKeyConstraintError(failed_index, true, *index, dst_chunk);
647
632
  }
648
633
  if (!is_append) {
649
- D_ASSERT(transaction_check);
650
- auto &transaction_matches = transaction_conflicts.Conflicts();
651
- if (error) {
652
- auto failed_index = LocateErrorIndex(false, regular_matches);
634
+ D_ASSERT(local_verification);
635
+ auto &transaction_matches = local_conflicts.Conflicts();
636
+ if (global_error) {
637
+ auto failed_index = LocateErrorIndex(false, global_matches);
653
638
  D_ASSERT(failed_index != DConstants::INVALID_INDEX);
654
639
  ThrowForeignKeyConstraintError(failed_index, false, *index, dst_chunk);
655
640
  } else {
656
- D_ASSERT(transaction_error);
641
+ D_ASSERT(local_error);
657
642
  D_ASSERT(transaction_matches.Count() != DConstants::INVALID_INDEX);
658
643
  auto failed_index = LocateErrorIndex(false, transaction_matches);
659
644
  D_ASSERT(failed_index != DConstants::INVALID_INDEX);
@@ -662,14 +647,16 @@ void DataTable::VerifyForeignKeyConstraint(const BoundForeignKeyConstraint &bfk,
662
647
  }
663
648
  }
664
649
 
665
- void DataTable::VerifyAppendForeignKeyConstraint(const BoundForeignKeyConstraint &bfk, ClientContext &context,
666
- DataChunk &chunk) {
667
- VerifyForeignKeyConstraint(bfk, context, chunk, VerifyExistenceType::APPEND_FK);
650
+ void DataTable::VerifyAppendForeignKeyConstraint(optional_ptr<LocalTableStorage> storage,
651
+ const BoundForeignKeyConstraint &bound_foreign_key,
652
+ ClientContext &context, DataChunk &chunk) {
653
+ VerifyForeignKeyConstraint(storage, bound_foreign_key, context, chunk, VerifyExistenceType::APPEND_FK);
668
654
  }
669
655
 
670
- void DataTable::VerifyDeleteForeignKeyConstraint(const BoundForeignKeyConstraint &bfk, ClientContext &context,
671
- DataChunk &chunk) {
672
- VerifyForeignKeyConstraint(bfk, context, chunk, VerifyExistenceType::DELETE_FK);
656
+ void DataTable::VerifyDeleteForeignKeyConstraint(optional_ptr<LocalTableStorage> storage,
657
+ const BoundForeignKeyConstraint &bound_foreign_key,
658
+ ClientContext &context, DataChunk &chunk) {
659
+ VerifyForeignKeyConstraint(storage, bound_foreign_key, context, chunk, VerifyExistenceType::DELETE_FK);
673
660
  }
674
661
 
675
662
  void DataTable::VerifyNewConstraint(LocalStorage &local_storage, DataTable &parent, const BoundConstraint &constraint) {
@@ -692,9 +679,11 @@ void DataTable::VerifyUniqueIndexes(TableIndexList &indexes, optional_ptr<LocalT
692
679
 
693
680
  if (storage) {
694
681
  auto delete_index = storage->delete_indexes.Find(art.GetIndexName());
695
- art.VerifyAppend(chunk, delete_index, nullptr);
682
+ IndexAppendInfo index_append_info(IndexAppendMode::DEFAULT, delete_index);
683
+ art.VerifyAppend(chunk, index_append_info, nullptr);
696
684
  } else {
697
- art.VerifyAppend(chunk, nullptr, nullptr);
685
+ IndexAppendInfo index_append_info;
686
+ art.VerifyAppend(chunk, index_append_info, nullptr);
698
687
  }
699
688
  return false;
700
689
  });
@@ -725,8 +714,10 @@ void DataTable::VerifyUniqueIndexes(TableIndexList &indexes, optional_ptr<LocalT
725
714
  manager->SetMode(ConflictManagerMode::SCAN);
726
715
  auto &matched_indexes = manager->MatchedIndexes();
727
716
  auto &matched_delete_indexes = manager->MatchedDeleteIndexes();
717
+ IndexAppendInfo index_append_info(IndexAppendMode::DEFAULT, nullptr);
728
718
  for (idx_t i = 0; i < matched_indexes.size(); i++) {
729
- matched_indexes[i].get().VerifyAppend(chunk, matched_delete_indexes[i], *manager);
719
+ index_append_info.delete_index = matched_delete_indexes[i];
720
+ matched_indexes[i].get().VerifyAppend(chunk, index_append_info, *manager);
730
721
  }
731
722
 
732
723
  // Scan the other indexes and throw, if there are any conflicts.
@@ -741,9 +732,11 @@ void DataTable::VerifyUniqueIndexes(TableIndexList &indexes, optional_ptr<LocalT
741
732
 
742
733
  if (storage) {
743
734
  auto delete_index = storage->delete_indexes.Find(art.GetIndexName());
744
- art.VerifyAppend(chunk, delete_index, *manager);
735
+ IndexAppendInfo index_append_info(IndexAppendMode::DEFAULT, delete_index);
736
+ art.VerifyAppend(chunk, index_append_info, *manager);
745
737
  } else {
746
- art.VerifyAppend(chunk, nullptr, *manager);
738
+ IndexAppendInfo index_append_info;
739
+ art.VerifyAppend(chunk, index_append_info, *manager);
747
740
  }
748
741
  return false;
749
742
  });
@@ -754,7 +747,6 @@ void DataTable::VerifyAppendConstraints(ConstraintState &constraint_state, Clien
754
747
  optional_ptr<ConflictManager> manager) {
755
748
 
756
749
  auto &table = constraint_state.table;
757
-
758
750
  if (table.HasGeneratedColumns()) {
759
751
  // Verify the generated columns against the inserted values.
760
752
  auto binder = Binder::CreateBinder(context);
@@ -799,10 +791,9 @@ void DataTable::VerifyAppendConstraints(ConstraintState &constraint_state, Clien
799
791
  break;
800
792
  }
801
793
  case ConstraintType::FOREIGN_KEY: {
802
- auto &bfk = constraint->Cast<BoundForeignKeyConstraint>();
803
- if (bfk.info.type == ForeignKeyType::FK_TYPE_FOREIGN_KEY_TABLE ||
804
- bfk.info.type == ForeignKeyType::FK_TYPE_SELF_REFERENCE_TABLE) {
805
- VerifyAppendForeignKeyConstraint(bfk, context, chunk);
794
+ auto &bound_foreign_key = constraint->Cast<BoundForeignKeyConstraint>();
795
+ if (bound_foreign_key.info.IsAppendConstraint()) {
796
+ VerifyAppendForeignKeyConstraint(storage, bound_foreign_key, context, chunk);
806
797
  }
807
798
  break;
808
799
  }
@@ -878,13 +869,14 @@ void DataTable::LocalMerge(ClientContext &context, RowGroupCollection &collectio
878
869
  local_storage.LocalMerge(*this, collection);
879
870
  }
880
871
 
881
- void DataTable::LocalAppend(TableCatalogEntry &table, ClientContext &context, DataChunk &chunk,
882
- const vector<unique_ptr<BoundConstraint>> &bound_constraints) {
872
+ void DataTable::LocalWALAppend(TableCatalogEntry &table, ClientContext &context, DataChunk &chunk,
873
+ const vector<unique_ptr<BoundConstraint>> &bound_constraints) {
883
874
  LocalAppendState append_state;
884
875
  auto &storage = table.GetStorage();
885
876
  storage.InitializeLocalAppend(append_state, table, context, bound_constraints);
886
877
 
887
- storage.LocalAppend(append_state, context, chunk, false);
878
+ storage.LocalAppend(append_state, context, chunk, true);
879
+ append_state.storage->index_append_mode = IndexAppendMode::INSERT_DUPLICATES;
888
880
  storage.FinalizeLocalAppend(append_state);
889
881
  }
890
882
 
@@ -1124,7 +1116,7 @@ void DataTable::RevertAppend(DuckTransaction &transaction, idx_t start_row, idx_
1124
1116
  // Indexes
1125
1117
  //===--------------------------------------------------------------------===//
1126
1118
  ErrorData DataTable::AppendToIndexes(TableIndexList &indexes, optional_ptr<TableIndexList> delete_indexes,
1127
- DataChunk &chunk, row_t row_start) {
1119
+ DataChunk &chunk, row_t row_start, const IndexAppendMode index_append_mode) {
1128
1120
  ErrorData error;
1129
1121
  if (indexes.Empty()) {
1130
1122
  return error;
@@ -1152,7 +1144,8 @@ ErrorData DataTable::AppendToIndexes(TableIndexList &indexes, optional_ptr<Table
1152
1144
  }
1153
1145
 
1154
1146
  try {
1155
- error = index.AppendWithDeleteIndex(chunk, row_ids, delete_index);
1147
+ IndexAppendInfo index_append_info(index_append_mode, delete_index);
1148
+ error = index.Append(chunk, row_ids, index_append_info);
1156
1149
  } catch (std::exception &ex) {
1157
1150
  error = ErrorData(ex);
1158
1151
  }
@@ -1175,9 +1168,10 @@ ErrorData DataTable::AppendToIndexes(TableIndexList &indexes, optional_ptr<Table
1175
1168
  return error;
1176
1169
  }
1177
1170
 
1178
- ErrorData DataTable::AppendToIndexes(optional_ptr<TableIndexList> delete_indexes, DataChunk &chunk, row_t row_start) {
1171
+ ErrorData DataTable::AppendToIndexes(optional_ptr<TableIndexList> delete_indexes, DataChunk &chunk, row_t row_start,
1172
+ const IndexAppendMode index_append_mode) {
1179
1173
  D_ASSERT(is_root);
1180
- return AppendToIndexes(info->indexes, delete_indexes, chunk, row_start);
1174
+ return AppendToIndexes(info->indexes, delete_indexes, chunk, row_start, index_append_mode);
1181
1175
  }
1182
1176
 
1183
1177
  void DataTable::RemoveFromIndexes(TableAppendState &state, DataChunk &chunk, row_t row_start) {
@@ -1199,7 +1193,8 @@ void DataTable::RemoveFromIndexes(TableAppendState &state, DataChunk &chunk, Vec
1199
1193
  if (!index.IsBound()) {
1200
1194
  throw InternalException("Unbound index found in DataTable::RemoveFromIndexes");
1201
1195
  }
1202
- index.Cast<BoundIndex>().Delete(chunk, row_identifiers);
1196
+ auto &bound_index = index.Cast<BoundIndex>();
1197
+ bound_index.Delete(chunk, row_identifiers);
1203
1198
  return false;
1204
1199
  });
1205
1200
  }
@@ -1220,9 +1215,8 @@ static bool TableHasDeleteConstraints(TableCatalogEntry &table) {
1220
1215
  case ConstraintType::UNIQUE:
1221
1216
  break;
1222
1217
  case ConstraintType::FOREIGN_KEY: {
1223
- auto &bfk = constraint->Cast<ForeignKeyConstraint>();
1224
- if (bfk.info.type == ForeignKeyType::FK_TYPE_PRIMARY_KEY_TABLE ||
1225
- bfk.info.type == ForeignKeyType::FK_TYPE_SELF_REFERENCE_TABLE) {
1218
+ auto &foreign_key = constraint->Cast<ForeignKeyConstraint>();
1219
+ if (foreign_key.info.IsDeleteConstraint()) {
1226
1220
  return true;
1227
1221
  }
1228
1222
  break;
@@ -1234,7 +1228,8 @@ static bool TableHasDeleteConstraints(TableCatalogEntry &table) {
1234
1228
  return false;
1235
1229
  }
1236
1230
 
1237
- void DataTable::VerifyDeleteConstraints(TableDeleteState &state, ClientContext &context, DataChunk &chunk) {
1231
+ void DataTable::VerifyDeleteConstraints(optional_ptr<LocalTableStorage> storage, TableDeleteState &state,
1232
+ ClientContext &context, DataChunk &chunk) {
1238
1233
  for (auto &constraint : state.constraint_state->bound_constraints) {
1239
1234
  switch (constraint->type) {
1240
1235
  case ConstraintType::NOT_NULL:
@@ -1242,10 +1237,9 @@ void DataTable::VerifyDeleteConstraints(TableDeleteState &state, ClientContext &
1242
1237
  case ConstraintType::UNIQUE:
1243
1238
  break;
1244
1239
  case ConstraintType::FOREIGN_KEY: {
1245
- auto &bfk = constraint->Cast<BoundForeignKeyConstraint>();
1246
- if (bfk.info.type == ForeignKeyType::FK_TYPE_PRIMARY_KEY_TABLE ||
1247
- bfk.info.type == ForeignKeyType::FK_TYPE_SELF_REFERENCE_TABLE) {
1248
- VerifyDeleteForeignKeyConstraint(bfk, context, chunk);
1240
+ auto &bound_foreign_key = constraint->Cast<BoundForeignKeyConstraint>();
1241
+ if (bound_foreign_key.info.IsDeleteConstraint()) {
1242
+ VerifyDeleteForeignKeyConstraint(storage, bound_foreign_key, context, chunk);
1249
1243
  }
1250
1244
  break;
1251
1245
  }
@@ -1284,6 +1278,7 @@ idx_t DataTable::Delete(TableDeleteState &state, ClientContext &context, Vector
1284
1278
 
1285
1279
  auto &transaction = DuckTransaction::Get(context, db);
1286
1280
  auto &local_storage = LocalStorage::Get(transaction);
1281
+ auto storage = local_storage.GetStorage(*this);
1287
1282
 
1288
1283
  row_identifiers.Flatten(count);
1289
1284
  auto ids = FlatVector::GetData<row_t>(row_identifiers);
@@ -1308,11 +1303,11 @@ idx_t DataTable::Delete(TableDeleteState &state, ClientContext &context, Vector
1308
1303
  // This is a transaction-local DELETE.
1309
1304
  if (is_transaction_delete) {
1310
1305
  if (state.has_delete_constraints) {
1311
- // perform the constraint verification
1306
+ // Verify any delete constraints.
1312
1307
  ColumnFetchState fetch_state;
1313
1308
  local_storage.FetchChunk(*this, offset_ids, current_count, state.col_ids, state.verify_chunk,
1314
1309
  fetch_state);
1315
- VerifyDeleteConstraints(state, context, state.verify_chunk);
1310
+ VerifyDeleteConstraints(storage, state, context, state.verify_chunk);
1316
1311
  }
1317
1312
  delete_count += local_storage.Delete(*this, offset_ids, current_count);
1318
1313
  continue;
@@ -1320,10 +1315,10 @@ idx_t DataTable::Delete(TableDeleteState &state, ClientContext &context, Vector
1320
1315
 
1321
1316
  // This is a regular DELETE.
1322
1317
  if (state.has_delete_constraints) {
1323
- // perform the constraint verification
1318
+ // Verify any delete constraints.
1324
1319
  ColumnFetchState fetch_state;
1325
1320
  Fetch(transaction, state.verify_chunk, state.col_ids, offset_ids, current_count, fetch_state);
1326
- VerifyDeleteConstraints(state, context, state.verify_chunk);
1321
+ VerifyDeleteConstraints(storage, state, context, state.verify_chunk);
1327
1322
  }
1328
1323
  delete_count += row_groups->Delete(transaction, *this, ids + current_offset, current_count);
1329
1324
  }
@@ -41,7 +41,6 @@ LocalTableStorage::LocalTableStorage(ClientContext &context, DataTable &table)
41
41
  // Create a delete index and a local index.
42
42
  auto delete_index = make_uniq<ART>(art.GetIndexName(), constraint_type, art.GetColumnIds(),
43
43
  art.table_io_manager, std::move(delete_expressions), art.db);
44
- delete_index->append_mode = ARTAppendMode::IGNORE_DUPLICATES;
45
44
  delete_indexes.AddIndex(std::move(delete_index));
46
45
 
47
46
  auto index = make_uniq<ART>(art.GetIndexName(), constraint_type, art.GetColumnIds(), art.table_io_manager,
@@ -152,7 +151,7 @@ ErrorData LocalTableStorage::AppendToIndexes(DuckTransaction &transaction, RowGr
152
151
  }
153
152
  mock_chunk.SetCardinality(chunk);
154
153
  // append this chunk to the indexes of the table
155
- error = DataTable::AppendToIndexes(index_list, nullptr, mock_chunk, start_row);
154
+ error = DataTable::AppendToIndexes(index_list, nullptr, mock_chunk, start_row, index_append_mode);
156
155
  if (error.HasError()) {
157
156
  return false;
158
157
  }
@@ -173,7 +172,7 @@ void LocalTableStorage::AppendToIndexes(DuckTransaction &transaction, TableAppen
173
172
  // appending: need to scan entire
174
173
  row_groups->Scan(transaction, [&](DataChunk &chunk) -> bool {
175
174
  // append this chunk to the indexes of the table
176
- error = table.AppendToIndexes(delete_indexes, chunk, append_state.current_row);
175
+ error = table.AppendToIndexes(delete_indexes, chunk, append_state.current_row, index_append_mode);
177
176
  if (error.HasError()) {
178
177
  return false;
179
178
  }
@@ -186,12 +185,13 @@ void LocalTableStorage::AppendToIndexes(DuckTransaction &transaction, TableAppen
186
185
  auto &index_list = data_table_info->GetIndexes();
187
186
  error = AppendToIndexes(transaction, *row_groups, index_list, table.GetTypes(), append_state.current_row);
188
187
  }
188
+
189
189
  if (error.HasError()) {
190
190
  // need to revert all appended row ids
191
191
  row_t current_row = append_state.row_start;
192
192
  // remove the data from the indexes, if there are any indexes
193
193
  row_groups->Scan(transaction, [&](DataChunk &chunk) -> bool {
194
- // append this chunk to the indexes of the table
194
+ // Remove this chunk from the indexes.
195
195
  try {
196
196
  table.RemoveFromIndexes(append_state, chunk, current_row);
197
197
  } catch (std::exception &ex) { // LCOV_EXCL_START
@@ -386,7 +386,8 @@ void LocalTableStorage::AppendToDeleteIndexes(Vector &row_ids, DataChunk &delete
386
386
  if (!art.IsUnique()) {
387
387
  return false;
388
388
  }
389
- auto result = art.Cast<BoundIndex>().Append(delete_chunk, row_ids);
389
+ IndexAppendInfo index_append_info(IndexAppendMode::IGNORE_DUPLICATES, nullptr);
390
+ auto result = art.Cast<BoundIndex>().Append(delete_chunk, row_ids, index_append_info);
390
391
  if (result.HasError()) {
391
392
  throw InternalException("unexpected constraint violation on delete ART: ", result.Message());
392
393
  }
@@ -401,7 +402,7 @@ void LocalStorage::Append(LocalAppendState &state, DataChunk &chunk) {
401
402
  idx_t base_id = offset + state.append_state.total_append_count;
402
403
 
403
404
  auto error = DataTable::AppendToIndexes(storage->append_indexes, storage->delete_indexes, chunk,
404
- NumericCast<row_t>(base_id));
405
+ NumericCast<row_t>(base_id), storage->index_append_mode);
405
406
  if (error.HasError()) {
406
407
  error.Throw();
407
408
  }
@@ -473,6 +474,7 @@ idx_t LocalStorage::Delete(DataTable &table, Vector &row_ids, idx_t count) {
473
474
 
474
475
  void LocalStorage::Update(DataTable &table, Vector &row_ids, const vector<PhysicalIndex> &column_ids,
475
476
  DataChunk &updates) {
477
+ D_ASSERT(updates.size() >= 1);
476
478
  auto storage = table_manager.GetStorage(table);
477
479
  D_ASSERT(storage);
478
480
 
@@ -14,7 +14,7 @@ DataFileType MagicBytes::CheckMagicBytes(FileSystem &fs, const string &path) {
14
14
  }
15
15
 
16
16
  constexpr const idx_t MAGIC_BYTES_READ_SIZE = 16;
17
- char buffer[MAGIC_BYTES_READ_SIZE];
17
+ char buffer[MAGIC_BYTES_READ_SIZE] = {};
18
18
 
19
19
  handle->Read(buffer, MAGIC_BYTES_READ_SIZE);
20
20
  if (memcmp(buffer, "SQLite format 3\0", 16) == 0) {
@@ -30,9 +30,9 @@ void LogicalDependency::Serialize(Serializer &serializer) const {
30
30
  }
31
31
 
32
32
  LogicalDependency LogicalDependency::Deserialize(Deserializer &deserializer) {
33
- LogicalDependency result;
34
- deserializer.ReadProperty<CatalogEntryInfo>(100, "entry", result.entry);
35
- deserializer.ReadPropertyWithDefault<string>(101, "catalog", result.catalog);
33
+ auto entry = deserializer.ReadProperty<CatalogEntryInfo>(100, "entry");
34
+ auto catalog = deserializer.ReadPropertyWithDefault<string>(101, "catalog");
35
+ LogicalDependency result(deserializer.TryGet<Catalog>(), entry, std::move(catalog));
36
36
  return result;
37
37
  }
38
38
 
@@ -209,7 +209,7 @@ void CSVReaderOptions::Serialize(Serializer &serializer) const {
209
209
  serializer.WritePropertyWithDefault<CSVOption<char>>(137, "comment", dialect_options.state_machine_options.comment, CSVOption<char>('\0'));
210
210
  serializer.WritePropertyWithDefault<idx_t>(138, "rows_until_header", dialect_options.rows_until_header);
211
211
  serializer.WritePropertyWithDefault<string>(139, "encoding", encoding);
212
- serializer.WriteProperty<CSVOption<bool>>(140, "rfc_4180", dialect_options.state_machine_options.rfc_4180);
212
+ serializer.WriteProperty<CSVOption<bool>>(140, "strict_mode", dialect_options.state_machine_options.strict_mode);
213
213
  serializer.WriteProperty<CSVOption<string>>(141, "multi_byte_delimiter", GetMultiByteDelimiter());
214
214
  serializer.WritePropertyWithDefault<bool>(142, "multi_file_reader", multi_file_reader);
215
215
  serializer.WriteProperty<CSVOption<idx_t>>(143, "buffer_size_option", buffer_size_option);
@@ -256,7 +256,7 @@ CSVReaderOptions CSVReaderOptions::Deserialize(Deserializer &deserializer) {
256
256
  auto dialect_options_state_machine_options_comment = deserializer.ReadPropertyWithExplicitDefault<CSVOption<char>>(137, "comment", CSVOption<char>('\0'));
257
257
  auto dialect_options_rows_until_header = deserializer.ReadPropertyWithDefault<idx_t>(138, "rows_until_header");
258
258
  auto encoding = deserializer.ReadPropertyWithDefault<string>(139, "encoding");
259
- auto dialect_options_state_machine_options_rfc_4180 = deserializer.ReadProperty<CSVOption<bool>>(140, "rfc_4180");
259
+ auto dialect_options_state_machine_options_strict_mode = deserializer.ReadProperty<CSVOption<bool>>(140, "strict_mode");
260
260
  auto multi_byte_delimiter = deserializer.ReadProperty<CSVOption<string>>(141, "multi_byte_delimiter");
261
261
  CSVReaderOptions result(dialect_options_state_machine_options_delimiter, multi_byte_delimiter);
262
262
  result.ignore_errors = ignore_errors;
@@ -295,7 +295,7 @@ CSVReaderOptions CSVReaderOptions::Deserialize(Deserializer &deserializer) {
295
295
  result.dialect_options.state_machine_options.comment = dialect_options_state_machine_options_comment;
296
296
  result.dialect_options.rows_until_header = dialect_options_rows_until_header;
297
297
  result.encoding = std::move(encoding);
298
- result.dialect_options.state_machine_options.rfc_4180 = dialect_options_state_machine_options_rfc_4180;
298
+ result.dialect_options.state_machine_options.strict_mode = dialect_options_state_machine_options_strict_mode;
299
299
  deserializer.ReadPropertyWithDefault<bool>(142, "multi_file_reader", result.multi_file_reader);
300
300
  deserializer.ReadProperty<CSVOption<idx_t>>(143, "buffer_size_option", result.buffer_size_option);
301
301
  return result;
@@ -110,14 +110,16 @@ void SetOperationNode::Serialize(Serializer &serializer) const {
110
110
  serializer.WritePropertyWithDefault<unique_ptr<QueryNode>>(201, "left", left);
111
111
  serializer.WritePropertyWithDefault<unique_ptr<QueryNode>>(202, "right", right);
112
112
  serializer.WritePropertyWithDefault<bool>(203, "setop_all", setop_all, true);
113
+ serializer.WritePropertyWithDefault<vector<unique_ptr<QueryNode>>>(204, "children", SerializeChildNodes());
113
114
  }
114
115
 
115
116
  unique_ptr<QueryNode> SetOperationNode::Deserialize(Deserializer &deserializer) {
116
- auto result = duckdb::unique_ptr<SetOperationNode>(new SetOperationNode());
117
- deserializer.ReadProperty<SetOperationType>(200, "setop_type", result->setop_type);
118
- deserializer.ReadPropertyWithDefault<unique_ptr<QueryNode>>(201, "left", result->left);
119
- deserializer.ReadPropertyWithDefault<unique_ptr<QueryNode>>(202, "right", result->right);
120
- deserializer.ReadPropertyWithExplicitDefault<bool>(203, "setop_all", result->setop_all, true);
117
+ auto setop_type = deserializer.ReadProperty<SetOperationType>(200, "setop_type");
118
+ auto left = deserializer.ReadPropertyWithDefault<unique_ptr<QueryNode>>(201, "left");
119
+ auto right = deserializer.ReadPropertyWithDefault<unique_ptr<QueryNode>>(202, "right");
120
+ auto setop_all = deserializer.ReadPropertyWithExplicitDefault<bool>(203, "setop_all", true);
121
+ auto children = deserializer.ReadPropertyWithDefault<vector<unique_ptr<QueryNode>>>(204, "children");
122
+ auto result = duckdb::unique_ptr<SetOperationNode>(new SetOperationNode(setop_type, std::move(left), std::move(right), std::move(children), setop_all));
121
123
  return std::move(result);
122
124
  }
123
125