duckdb 0.3.2-dev1288.0 → 0.3.2-dev1306.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.
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "duckdb",
3
3
  "main": "./lib/duckdb.js",
4
- "version": "0.3.2-dev1288.0",
4
+ "version": "0.3.2-dev1306.0",
5
5
  "description": "DuckDB node.js API",
6
6
  "gypfile": true,
7
7
  "dependencies": {
package/src/duckdb.cpp CHANGED
@@ -4687,6 +4687,37 @@ data_ptr_t Allocator::ReallocateData(data_ptr_t pointer, idx_t size) {
4687
4687
 
4688
4688
 
4689
4689
 
4690
+
4691
+ //===----------------------------------------------------------------------===//
4692
+ // DuckDB
4693
+ //
4694
+ // duckdb/common/result_arrow_wrapper.hpp
4695
+ //
4696
+ //
4697
+ //===----------------------------------------------------------------------===//
4698
+
4699
+
4700
+
4701
+
4702
+
4703
+
4704
+ namespace duckdb {
4705
+ class ResultArrowArrayStreamWrapper {
4706
+ public:
4707
+ explicit ResultArrowArrayStreamWrapper(unique_ptr<QueryResult> result, idx_t approx_batch_size);
4708
+ ArrowArrayStream stream;
4709
+ unique_ptr<QueryResult> result;
4710
+ std::string last_error;
4711
+ idx_t vectors_per_chunk;
4712
+
4713
+ private:
4714
+ static int MyStreamGetSchema(struct ArrowArrayStream *stream, struct ArrowSchema *out);
4715
+ static int MyStreamGetNext(struct ArrowArrayStream *stream, struct ArrowArray *out);
4716
+ static void MyStreamRelease(struct ArrowArrayStream *stream);
4717
+ static const char *MyStreamGetLastError(struct ArrowArrayStream *stream);
4718
+ };
4719
+ } // namespace duckdb
4720
+
4690
4721
  namespace duckdb {
4691
4722
 
4692
4723
  ArrowSchemaWrapper::~ArrowSchemaWrapper() {
@@ -4737,8 +4768,8 @@ void ArrowArrayStreamWrapper::GetSchema(ArrowSchemaWrapper &schema) {
4737
4768
  // LCOV_EXCL_STOP
4738
4769
  }
4739
4770
 
4740
- unique_ptr<ArrowArrayWrapper> ArrowArrayStreamWrapper::GetNextChunk() {
4741
- auto current_chunk = make_unique<ArrowArrayWrapper>();
4771
+ shared_ptr<ArrowArrayWrapper> ArrowArrayStreamWrapper::GetNextChunk() {
4772
+ auto current_chunk = make_shared<ArrowArrayWrapper>();
4742
4773
  if (arrow_array_stream.get_next(&arrow_array_stream, &current_chunk->arrow_array)) { // LCOV_EXCL_START
4743
4774
  throw InvalidInputException("arrow_scan: get_next failed(): %s", string(GetError()));
4744
4775
  } // LCOV_EXCL_STOP
@@ -30174,7 +30205,29 @@ struct SelCache {
30174
30205
 
30175
30206
 
30176
30207
 
30208
+ //===----------------------------------------------------------------------===//
30209
+ // DuckDB
30210
+ //
30211
+ // duckdb/common/types/arrow_aux_data.hpp
30212
+ //
30213
+ //
30214
+ //===----------------------------------------------------------------------===//
30215
+
30216
+
30217
+
30218
+
30219
+
30220
+
30221
+ namespace duckdb {
30222
+ struct ArrowAuxiliaryData : VectorAuxiliaryData {
30223
+ explicit ArrowAuxiliaryData(shared_ptr<ArrowArrayWrapper> arrow_array_p)
30224
+ : VectorAuxiliaryData(VectorAuxiliaryDataType::ARROW_AUXILIARY), arrow_array(std::move(arrow_array_p)) {
30177
30225
 
30226
+ };
30227
+ ~ArrowAuxiliaryData() override {};
30228
+ shared_ptr<ArrowArrayWrapper> arrow_array;
30229
+ };
30230
+ } // namespace duckdb
30178
30231
 
30179
30232
 
30180
30233
  namespace duckdb {
@@ -30443,6 +30496,7 @@ struct DuckDBArrowArrayHolder {
30443
30496
  vector<DuckDBArrowArrayChildHolder> children = {};
30444
30497
  vector<ArrowArray *> children_ptrs = {};
30445
30498
  array<const void *, 1> buffers = {{nullptr}};
30499
+ vector<shared_ptr<ArrowArrayWrapper>> arrow_original_array;
30446
30500
  };
30447
30501
 
30448
30502
  static void ReleaseDuckDBArrowArray(ArrowArray *array) {
@@ -30869,7 +30923,12 @@ void DataChunk::ToArrowArray(ArrowArray *out_array) {
30869
30923
  InitializeChild(child_holder, size());
30870
30924
  auto &vector = child_holder.vector;
30871
30925
  auto &child = child_holder.array;
30872
-
30926
+ auto vec_buffer = data[col_idx].GetBuffer();
30927
+ if (vec_buffer->GetAuxiliaryData() &&
30928
+ vec_buffer->GetAuxiliaryDataType() == VectorAuxiliaryDataType::ARROW_AUXILIARY) {
30929
+ auto arrow_aux_data = (ArrowAuxiliaryData *)vec_buffer->GetAuxiliaryData();
30930
+ root_holder->arrow_original_array.push_back(arrow_aux_data->arrow_array);
30931
+ }
30873
30932
  //! We could, in theory, output other types of vectors here, currently only FLAT Vectors
30874
30933
  SetArrowChild(child_holder, GetTypes()[col_idx], data[col_idx], size());
30875
30934
  SetChildValidityMask(*vector, child);
@@ -58342,8 +58401,8 @@ bool BufferedCSVReader::ReadBuffer(idx_t &start) {
58342
58401
  while (remaining > buffer_read_size) {
58343
58402
  buffer_read_size *= 2;
58344
58403
  }
58345
- if (remaining + buffer_read_size > MAXIMUM_CSV_LINE_SIZE) {
58346
- throw InvalidInputException("Maximum line size of %llu bytes exceeded!", MAXIMUM_CSV_LINE_SIZE);
58404
+ if (remaining + buffer_read_size > options.maximum_line_size) {
58405
+ throw InvalidInputException("Maximum line size of %llu bytes exceeded!", options.maximum_line_size);
58347
58406
  }
58348
58407
  buffer = unique_ptr<char[]>(new char[buffer_read_size + remaining + 1]);
58349
58408
  buffer_size = remaining + buffer_read_size;
@@ -90093,7 +90152,7 @@ struct ArrowScanState : public FunctionOperatorData {
90093
90152
  explicit ArrowScanState(unique_ptr<ArrowArrayWrapper> current_chunk) : chunk(move(current_chunk)) {
90094
90153
  }
90095
90154
  unique_ptr<ArrowArrayStreamWrapper> stream;
90096
- unique_ptr<ArrowArrayWrapper> chunk;
90155
+ shared_ptr<ArrowArrayWrapper> chunk;
90097
90156
  idx_t chunk_offset = 0;
90098
90157
  vector<column_t> column_ids;
90099
90158
  //! Store child vectors for Arrow Dictionary Vectors (col-idx,vector)
@@ -90172,6 +90231,7 @@ private:
90172
90231
 
90173
90232
 
90174
90233
 
90234
+
90175
90235
  #include <map>
90176
90236
 
90177
90237
  namespace duckdb {
@@ -91146,6 +91206,8 @@ void ArrowTableFunction::ArrowToDuckDB(ArrowScanState &scan_state,
91146
91206
  if (array.length != scan_state.chunk->arrow_array.length) {
91147
91207
  throw InvalidInputException("arrow_scan: array length mismatch");
91148
91208
  }
91209
+ output.data[idx].GetBuffer()->SetAuxiliaryData(make_unique<ArrowAuxiliaryData>(scan_state.chunk),
91210
+ VectorAuxiliaryDataType::ARROW_AUXILIARY);
91149
91211
  if (array.dictionary) {
91150
91212
  ColumnArrowToDuckDBDictionary(output.data[idx], array, scan_state, output.size(), arrow_convert_data,
91151
91213
  col_idx, arrow_convert_idx);
@@ -91497,6 +91559,8 @@ static bool ParseBaseOption(BufferedCSVReaderOptions &options, string &loption,
91497
91559
  options.compression = FileCompressionTypeFromString(ParseString(set));
91498
91560
  } else if (loption == "skip") {
91499
91561
  options.skip_rows = ParseInteger(set);
91562
+ } else if (loption == "max_line_size" || loption == "maximum_line_size") {
91563
+ options.maximum_line_size = ParseInteger(set);
91500
91564
  } else {
91501
91565
  // unrecognized option in base CSV
91502
91566
  return false;
@@ -92801,6 +92865,8 @@ static unique_ptr<FunctionData> ReadCSVBind(ClientContext &context, vector<Value
92801
92865
  result->include_file_name = BooleanValue::Get(kv.second);
92802
92866
  } else if (loption == "skip") {
92803
92867
  options.skip_rows = kv.second.GetValue<int64_t>();
92868
+ } else if (loption == "max_line_size" || loption == "maximum_line_size") {
92869
+ options.maximum_line_size = kv.second.GetValue<int64_t>();
92804
92870
  } else {
92805
92871
  throw InternalException("Unrecognized parameter %s", kv.first);
92806
92872
  }
@@ -92907,6 +92973,8 @@ static void ReadCSVAddNamedParameters(TableFunction &table_function) {
92907
92973
  table_function.named_parameters["compression"] = LogicalType::VARCHAR;
92908
92974
  table_function.named_parameters["filename"] = LogicalType::BOOLEAN;
92909
92975
  table_function.named_parameters["skip"] = LogicalType::BIGINT;
92976
+ table_function.named_parameters["max_line_size"] = LogicalType::VARCHAR;
92977
+ table_function.named_parameters["maximum_line_size"] = LogicalType::VARCHAR;
92910
92978
  }
92911
92979
 
92912
92980
  double CSVReaderProgress(ClientContext &context, const FunctionData *bind_data_p) {
@@ -121200,6 +121268,10 @@ unique_ptr<NodeStatistics> StatisticsPropagator::PropagateStatistics(LogicalCros
121200
121268
 
121201
121269
  namespace duckdb {
121202
121270
 
121271
+ static bool IsCompareDistinct(ExpressionType type) {
121272
+ return type == ExpressionType::COMPARE_DISTINCT_FROM || type == ExpressionType::COMPARE_NOT_DISTINCT_FROM;
121273
+ }
121274
+
121203
121275
  bool StatisticsPropagator::ExpressionIsConstant(Expression &expr, const Value &val) {
121204
121276
  if (expr.GetExpressionClass() != ExpressionClass::BOUND_CONSTANT) {
121205
121277
  return false;
@@ -121227,8 +121299,10 @@ void StatisticsPropagator::SetStatisticsNotNull(ColumnBinding binding) {
121227
121299
 
121228
121300
  void StatisticsPropagator::UpdateFilterStatistics(BaseStatistics &stats, ExpressionType comparison_type,
121229
121301
  const Value &constant) {
121230
- // any comparison filter removes all null values
121231
- stats.validity_stats = make_unique<ValidityStatistics>(false);
121302
+ // regular comparisons removes all null values
121303
+ if (!IsCompareDistinct(comparison_type)) {
121304
+ stats.validity_stats = make_unique<ValidityStatistics>(false);
121305
+ }
121232
121306
  if (!stats.type.IsNumeric()) {
121233
121307
  // don't handle non-numeric columns here (yet)
121234
121308
  return;
@@ -121264,9 +121338,11 @@ void StatisticsPropagator::UpdateFilterStatistics(BaseStatistics &stats, Express
121264
121338
 
121265
121339
  void StatisticsPropagator::UpdateFilterStatistics(BaseStatistics &lstats, BaseStatistics &rstats,
121266
121340
  ExpressionType comparison_type) {
121267
- // any comparison filter removes all null values
121268
- lstats.validity_stats = make_unique<ValidityStatistics>(false);
121269
- rstats.validity_stats = make_unique<ValidityStatistics>(false);
121341
+ // regular comparisons removes all null values
121342
+ if (!IsCompareDistinct(comparison_type)) {
121343
+ lstats.validity_stats = make_unique<ValidityStatistics>(false);
121344
+ rstats.validity_stats = make_unique<ValidityStatistics>(false);
121345
+ }
121270
121346
  D_ASSERT(lstats.type == rstats.type);
121271
121347
  if (!lstats.type.IsNumeric()) {
121272
121348
  // don't handle non-numeric columns here (yet)
@@ -121312,6 +121388,7 @@ void StatisticsPropagator::UpdateFilterStatistics(BaseStatistics &lstats, BaseSt
121312
121388
  }
121313
121389
  break;
121314
121390
  case ExpressionType::COMPARE_EQUAL:
121391
+ case ExpressionType::COMPARE_NOT_DISTINCT_FROM:
121315
121392
  // LEFT = RIGHT
121316
121393
  // only the tightest bounds pass
121317
121394
  // so if we have e.g. left = [-50, 250] and right = [-100, 100]
@@ -121337,10 +121414,11 @@ void StatisticsPropagator::UpdateFilterStatistics(BaseStatistics &lstats, BaseSt
121337
121414
  void StatisticsPropagator::UpdateFilterStatistics(Expression &left, Expression &right, ExpressionType comparison_type) {
121338
121415
  // first check if either side is a bound column ref
121339
121416
  // any column ref involved in a comparison will not be null after the comparison
121340
- if (left.type == ExpressionType::BOUND_COLUMN_REF) {
121417
+ bool compare_distinct = IsCompareDistinct(comparison_type);
121418
+ if (!compare_distinct && left.type == ExpressionType::BOUND_COLUMN_REF) {
121341
121419
  SetStatisticsNotNull(((BoundColumnRefExpression &)left).binding);
121342
121420
  }
121343
- if (right.type == ExpressionType::BOUND_COLUMN_REF) {
121421
+ if (!compare_distinct && right.type == ExpressionType::BOUND_COLUMN_REF) {
121344
121422
  SetStatisticsNotNull(((BoundColumnRefExpression &)right).binding);
121345
121423
  }
121346
121424
  // check if this is a comparison between a constant and a column ref
@@ -153477,8 +153555,9 @@ unique_ptr<LogicalOperator> FlattenDependentJoins::PushDownDependentJoinInternal
153477
153555
  join->children.push_back(move(plan->children[1]));
153478
153556
  return move(join);
153479
153557
  }
153558
+ case LogicalOperatorType::LOGICAL_ANY_JOIN:
153480
153559
  case LogicalOperatorType::LOGICAL_COMPARISON_JOIN: {
153481
- auto &join = (LogicalComparisonJoin &)*plan;
153560
+ auto &join = (LogicalJoin &)*plan;
153482
153561
  D_ASSERT(plan->children.size() == 2);
153483
153562
  // check the correlated expressions in the children of the join
153484
153563
  bool left_has_correlation = has_correlated_expressions.find(plan->children[0].get())->second;
@@ -153503,6 +153582,13 @@ unique_ptr<LogicalOperator> FlattenDependentJoins::PushDownDependentJoinInternal
153503
153582
  plan->children[0] = PushDownDependentJoinInternal(move(plan->children[0]));
153504
153583
  return plan;
153505
153584
  }
153585
+ } else if (join.join_type == JoinType::RIGHT) {
153586
+ // left outer join
153587
+ if (!left_has_correlation) {
153588
+ // only right has correlation: push into right
153589
+ plan->children[1] = PushDownDependentJoinInternal(move(plan->children[1]));
153590
+ return plan;
153591
+ }
153506
153592
  } else if (join.join_type == JoinType::MARK) {
153507
153593
  if (right_has_correlation) {
153508
153594
  throw Exception("MARK join with correlation in RHS not supported");
@@ -153518,27 +153604,42 @@ unique_ptr<LogicalOperator> FlattenDependentJoins::PushDownDependentJoinInternal
153518
153604
  }
153519
153605
  // both sides have correlation
153520
153606
  // push into both sides
153521
- // NOTE: for OUTER JOINS it matters what the BASE BINDING is after the join
153522
- // for the LEFT OUTER JOIN, we want the LEFT side to be the base binding after we push
153523
- // because the RIGHT binding might contain NULL values
153524
153607
  plan->children[0] = PushDownDependentJoinInternal(move(plan->children[0]));
153525
153608
  auto left_binding = this->base_binding;
153526
153609
  plan->children[1] = PushDownDependentJoinInternal(move(plan->children[1]));
153527
153610
  auto right_binding = this->base_binding;
153611
+ // NOTE: for OUTER JOINS it matters what the BASE BINDING is after the join
153612
+ // for the LEFT OUTER JOIN, we want the LEFT side to be the base binding after we push
153613
+ // because the RIGHT binding might contain NULL values
153528
153614
  if (join.join_type == JoinType::LEFT) {
153529
153615
  this->base_binding = left_binding;
153616
+ } else if (join.join_type == JoinType::RIGHT) {
153617
+ this->base_binding = right_binding;
153530
153618
  }
153531
153619
  // add the correlated columns to the join conditions
153532
153620
  for (idx_t i = 0; i < correlated_columns.size(); i++) {
153533
- JoinCondition cond;
153534
-
153535
- cond.left = make_unique<BoundColumnRefExpression>(
153621
+ auto left = make_unique<BoundColumnRefExpression>(
153536
153622
  correlated_columns[i].type, ColumnBinding(left_binding.table_index, left_binding.column_index + i));
153537
- cond.right = make_unique<BoundColumnRefExpression>(
153623
+ auto right = make_unique<BoundColumnRefExpression>(
153538
153624
  correlated_columns[i].type, ColumnBinding(right_binding.table_index, right_binding.column_index + i));
153539
- cond.comparison = ExpressionType::COMPARE_EQUAL;
153540
- cond.null_values_are_equal = true;
153541
- join.conditions.push_back(move(cond));
153625
+
153626
+ if (join.type == LogicalOperatorType::LOGICAL_COMPARISON_JOIN) {
153627
+ JoinCondition cond;
153628
+ cond.left = move(left);
153629
+ cond.right = move(right);
153630
+ cond.comparison = ExpressionType::COMPARE_EQUAL;
153631
+ cond.null_values_are_equal = true;
153632
+
153633
+ auto &comparison_join = (LogicalComparisonJoin &)join;
153634
+ comparison_join.conditions.push_back(move(cond));
153635
+ } else {
153636
+ auto &any_join = (LogicalAnyJoin &)join;
153637
+ auto comparison = make_unique<BoundComparisonExpression>(ExpressionType::COMPARE_NOT_DISTINCT_FROM,
153638
+ move(left), move(right));
153639
+ auto conjunction = make_unique<BoundConjunctionExpression>(ExpressionType::CONJUNCTION_AND,
153640
+ move(comparison), move(any_join.condition));
153641
+ any_join.condition = move(conjunction);
153642
+ }
153542
153643
  }
153543
153644
  // then we replace any correlated expressions with the corresponding entry in the correlated_map
153544
153645
  RewriteCorrelatedExpressions rewriter(right_binding, correlated_map);
@@ -222743,12 +222844,17 @@ static void allocate_new(parser_state *state, size_t n) {
222743
222844
 
222744
222845
  void *palloc(size_t n) {
222745
222846
  // we need to align our pointers for the sanitizer
222746
- auto aligned_n = ((n + 7) / 8) * 8;
222847
+ auto allocate_n = n + sizeof(size_t);
222848
+ auto aligned_n = ((allocate_n + 7) / 8) * 8;
222747
222849
  if (pg_parser_state.malloc_pos + aligned_n > PG_MALLOC_SIZE) {
222748
222850
  allocate_new(&pg_parser_state, aligned_n);
222749
222851
  }
222750
222852
 
222751
- void *ptr = pg_parser_state.malloc_ptrs[pg_parser_state.malloc_ptr_idx - 1] + pg_parser_state.malloc_pos;
222853
+ // store the length of the allocation
222854
+ char *base_ptr = pg_parser_state.malloc_ptrs[pg_parser_state.malloc_ptr_idx - 1] + pg_parser_state.malloc_pos;
222855
+ memcpy(base_ptr, &n, sizeof(size_t));
222856
+ // store the actual pointer
222857
+ char *ptr = (char*) base_ptr + sizeof(size_t);
222752
222858
  memset(ptr, 0, n);
222753
222859
  pg_parser_state.malloc_pos += aligned_n;
222754
222860
  return ptr;
@@ -222861,7 +222967,14 @@ void *palloc0fast(size_t n) { // very fast
222861
222967
  return palloc(n);
222862
222968
  }
222863
222969
  void *repalloc(void *ptr, size_t n) {
222864
- return palloc(n);
222970
+ // get the length of the allocation
222971
+ size_t old_len;
222972
+ char *old_len_ptr = (char *) ptr - sizeof(size_t);
222973
+ memcpy((void *) &old_len, old_len_ptr, sizeof(size_t));
222974
+ // re-allocate and copy the data
222975
+ void *new_buf = palloc(n);
222976
+ memcpy(new_buf, ptr, old_len);
222977
+ return new_buf;
222865
222978
  }
222866
222979
  char *NameListToString(PGList *names) {
222867
222980
  throw std::runtime_error("NameListToString NOT IMPLEMENTED");