@malloydata/render 0.0.123-dev240209030627 → 0.0.123-dev240209210150

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.
@@ -56036,10 +56036,10 @@ QUERY: ${(0, util_1.inspect)(opDesc, { breakLength: 72, depth: Infinity })}`);
56036
56036
  const e12 = partitionField.getField(fs);
56037
56037
  if (e12.found === void 0) {
56038
56038
  partitionField.log(`${partitionField.refString} is not defined`);
56039
- } else if ((0, malloy_types_1.expressionIsScalar)(e12.found.typeDesc().expressionType)) {
56040
- partitionByFields.push(partitionField.nameString);
56039
+ } else if ((0, malloy_types_1.expressionIsAnalytic)(e12.found.typeDesc().expressionType) || (0, malloy_types_1.expressionIsUngroupedAggregate)(e12.found.typeDesc().expressionType)) {
56040
+ partitionField.log("Partition expression must be scalar or aggregate");
56041
56041
  } else {
56042
- partitionField.log("Partition expression must be scalar");
56042
+ partitionByFields.push(partitionField.nameString);
56043
56043
  }
56044
56044
  }
56045
56045
  }
@@ -71618,6 +71618,7 @@ ${errText}`, errors);
71618
71618
  this.rowSeparator = "\n";
71619
71619
  this.quoteCharacter = '"';
71620
71620
  this.includeHeader = true;
71621
+ this.emptyCell = "";
71621
71622
  }
71622
71623
  escape(value3) {
71623
71624
  const hasInnerQuote = value3.includes(this.quoteCharacter);
@@ -71632,43 +71633,136 @@ ${errText}`, errors);
71632
71633
  }
71633
71634
  return value3;
71634
71635
  }
71635
- stringify(cell2) {
71636
- if (cell2.isNull()) {
71637
- return "";
71638
- } else if (cell2.isArray() || cell2.isRecord() || cell2.isBoolean() || cell2.isNumber()) {
71639
- return JSON.stringify(cell2.value);
71640
- } else if (cell2.isDate() || cell2.isTimestamp()) {
71641
- return cell2.value.toISOString();
71642
- } else if (cell2.isString()) {
71643
- return cell2.value;
71644
- } else {
71645
- return `${cell2.value}`;
71636
+ // Re-using the old stringify method for sanity.
71637
+ stringify(value3) {
71638
+ if (value3 === null) {
71639
+ return this.emptyCell;
71640
+ } else if (value3 instanceof Date) {
71641
+ return value3.toISOString();
71642
+ } else if (typeof value3 === "boolean" || typeof value3 === "number") {
71643
+ return JSON.stringify(value3);
71644
+ } else {
71645
+ return `${value3}`;
71646
+ }
71647
+ }
71648
+ // Extra weight to be added becase of nested tables inside the cells.
71649
+ getColWeight(jsonVal) {
71650
+ let firstVal = jsonVal;
71651
+ if (Array.isArray(jsonVal)) {
71652
+ firstVal = jsonVal[0];
71653
+ }
71654
+ let numKeys = 0;
71655
+ for (const key2 in firstVal) {
71656
+ numKeys = numKeys + 1;
71657
+ const val = firstVal[key2];
71658
+ if (Array.isArray(val)) {
71659
+ const weight = this.getColWeight(val) - 1;
71660
+ numKeys = numKeys + weight;
71661
+ }
71662
+ }
71663
+ return numKeys;
71664
+ }
71665
+ // Get header row along with extra empty spaces for nested children.
71666
+ getHeaderRow(row) {
71667
+ const csv = [];
71668
+ let width2 = 0;
71669
+ for (const key2 in row) {
71670
+ csv.push(this.escape(key2));
71671
+ const val = row[key2];
71672
+ width2++;
71673
+ if (Array.isArray(val)) {
71674
+ const numKeys = this.getColWeight(val) - 1;
71675
+ width2 = width2 + numKeys;
71676
+ for (let i6 = 0; i6 < numKeys; i6++) {
71677
+ csv.push(this.emptyCell);
71678
+ }
71679
+ }
71680
+ }
71681
+ return { rows: [csv.join(this.columnSeparator)], length: 1, width: width2 };
71682
+ }
71683
+ // Merge the child matrices i.e. merge the columns into one bigger matrix i.e. CSV.
71684
+ mergeMatrices(matrices) {
71685
+ const maxLength = Math.max(...matrices.map((matrix) => matrix.length));
71686
+ const matrixWidth = matrices.reduce((sum3, matrix) => sum3 + matrix.width, 0);
71687
+ const csvMatrix = [];
71688
+ for (let i6 = 0; i6 < maxLength; i6++) {
71689
+ const csvRow = [];
71690
+ for (const matrix of matrices) {
71691
+ if (i6 < matrix.length) {
71692
+ csvRow.push(matrix.rows[i6]);
71693
+ } else {
71694
+ const emptyCells = Array(matrix.width).fill(this.emptyCell);
71695
+ csvRow.push(...emptyCells);
71696
+ }
71697
+ }
71698
+ csvMatrix.push(csvRow.join(this.columnSeparator));
71646
71699
  }
71700
+ return {
71701
+ rows: csvMatrix,
71702
+ length: maxLength,
71703
+ width: matrixWidth
71704
+ };
71705
+ }
71706
+ // Gets CSV for a data cell that has nested data.
71707
+ getChildMatrix(jsonVal) {
71708
+ if (!Array.isArray(jsonVal)) {
71709
+ return {
71710
+ rows: ["Invalid data found, value is not an array"],
71711
+ length: 1,
71712
+ width: 1
71713
+ };
71714
+ } else if (jsonVal.length === 0) {
71715
+ return {
71716
+ rows: [""],
71717
+ length: 1,
71718
+ width: 1
71719
+ };
71720
+ }
71721
+ const csvMatrix = [];
71722
+ const header = this.getHeaderRow(jsonVal[0]);
71723
+ csvMatrix.push(...header.rows);
71724
+ const width2 = header.width;
71725
+ let rowCount = 1;
71726
+ for (const row of jsonVal) {
71727
+ const rowMatrix = this.getRowMatrix(row);
71728
+ rowCount = rowCount + rowMatrix.length;
71729
+ csvMatrix.push(...rowMatrix.rows);
71730
+ }
71731
+ return { rows: csvMatrix, length: rowCount, width: width2 };
71732
+ }
71733
+ // Creates CSV content for one row of data.
71734
+ getRowMatrix(row) {
71735
+ const matrices = [];
71736
+ for (const key2 in row) {
71737
+ const val = row[key2];
71738
+ if (!Array.isArray(val)) {
71739
+ const cell2 = {
71740
+ rows: [this.stringify(val)],
71741
+ length: 1,
71742
+ width: 1
71743
+ };
71744
+ matrices.push(cell2);
71745
+ } else {
71746
+ const cell2 = this.getChildMatrix(val);
71747
+ matrices.push(cell2);
71748
+ }
71749
+ }
71750
+ return this.mergeMatrices(matrices);
71647
71751
  }
71648
71752
  async process(data3) {
71649
- let fields;
71753
+ let headerDefined = false;
71650
71754
  for await (const row of data3) {
71651
- if (fields === void 0) {
71652
- fields = row.field.allFields;
71653
- if (this.includeHeader) {
71654
- for (let fieldIndex = 0; fieldIndex < fields.length; fieldIndex++) {
71655
- const field3 = fields[fieldIndex];
71656
- this.stream.write(this.escape(field3.name));
71657
- if (fieldIndex !== fields.length - 1) {
71658
- this.stream.write(this.columnSeparator);
71659
- }
71660
- }
71661
- this.stream.write(this.rowSeparator);
71662
- }
71755
+ if (!headerDefined && this.includeHeader) {
71756
+ const header = this.getHeaderRow(row.toObject());
71757
+ this.stream.write(header.rows[0]);
71758
+ this.stream.write(this.rowSeparator);
71759
+ headerDefined = true;
71663
71760
  }
71664
- for (let fieldIndex = 0; fieldIndex < fields.length; fieldIndex++) {
71665
- const field3 = fields[fieldIndex];
71666
- this.stream.write(this.escape(this.stringify(row.cell(field3))));
71667
- if (fieldIndex !== fields.length - 1) {
71668
- this.stream.write(this.columnSeparator);
71669
- }
71761
+ const rowCsv = this.getRowMatrix(row.toObject());
71762
+ for (const line4 of rowCsv.rows) {
71763
+ this.stream.write(line4);
71764
+ this.stream.write(this.rowSeparator);
71670
71765
  }
71671
- this.stream.write(this.rowSeparator);
71672
71766
  }
71673
71767
  this.stream.close();
71674
71768
  }