@malloydata/malloy-query-builder 0.0.266 → 0.0.267-dev250421220633

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.
@@ -2621,4 +2621,308 @@ describe('query builder', () => {
2621
2621
  expect(query.isRunnable()).toBe(true);
2622
2622
  });
2623
2623
  });
2624
+ describe('insertion order', () => {
2625
+ const model: Malloy.ModelInfo = {
2626
+ entries: [
2627
+ {
2628
+ kind: 'source',
2629
+ name: 's',
2630
+ schema: {
2631
+ fields: [
2632
+ {kind: 'dimension', name: 'd1', type: {kind: 'number_type'}},
2633
+ {kind: 'dimension', name: 'd2', type: {kind: 'number_type'}},
2634
+ {kind: 'dimension', name: 'd3', type: {kind: 'number_type'}},
2635
+ {kind: 'measure', name: 'm1', type: {kind: 'number_type'}},
2636
+ {kind: 'measure', name: 'm2', type: {kind: 'number_type'}},
2637
+ {kind: 'measure', name: 'm3', type: {kind: 'number_type'}},
2638
+ {kind: 'view', name: 'v1', schema: {fields: []}},
2639
+ {kind: 'view', name: 'v2', schema: {fields: []}},
2640
+ {kind: 'view', name: 'v3', schema: {fields: []}},
2641
+ ],
2642
+ },
2643
+ },
2644
+ ],
2645
+ anonymous_queries: [],
2646
+ };
2647
+ function group_by(name: string): Malloy.ViewOperationWithGroupBy {
2648
+ return {
2649
+ kind: 'group_by',
2650
+ field: {
2651
+ expression: {
2652
+ kind: 'field_reference',
2653
+ name,
2654
+ },
2655
+ },
2656
+ };
2657
+ }
2658
+ function aggregate(name: string): Malloy.ViewOperationWithAggregate {
2659
+ return {
2660
+ kind: 'aggregate',
2661
+ field: {
2662
+ expression: {
2663
+ kind: 'field_reference',
2664
+ name,
2665
+ },
2666
+ },
2667
+ };
2668
+ }
2669
+ function nest(name: string): Malloy.ViewOperationWithNest {
2670
+ return {
2671
+ kind: 'nest',
2672
+ view: {
2673
+ definition: {
2674
+ kind: 'view_reference',
2675
+ name,
2676
+ },
2677
+ },
2678
+ };
2679
+ }
2680
+ test('add an aggregate after adding some group bys', () => {
2681
+ const from: Malloy.Query = {
2682
+ definition: {
2683
+ kind: 'arrow',
2684
+ source: {
2685
+ kind: 'source_reference',
2686
+ name: 's',
2687
+ },
2688
+ view: {
2689
+ kind: 'segment',
2690
+ operations: [],
2691
+ },
2692
+ },
2693
+ };
2694
+ expect((q: ASTQuery) => {
2695
+ const segment = q.getOrAddDefaultSegment();
2696
+ segment.addGroupBy('d1');
2697
+ segment.addGroupBy('d2');
2698
+ segment.addAggregate('m1');
2699
+ }).toModifyQuery({
2700
+ model,
2701
+ from,
2702
+ to: {
2703
+ definition: {
2704
+ kind: 'arrow',
2705
+ source: {
2706
+ kind: 'source_reference',
2707
+ name: 's',
2708
+ },
2709
+ view: {
2710
+ kind: 'segment',
2711
+ operations: [group_by('d1'), group_by('d2'), aggregate('m1')],
2712
+ },
2713
+ },
2714
+ },
2715
+ malloy: dedent`
2716
+ run: s -> {
2717
+ group_by:
2718
+ d1
2719
+ d2
2720
+ aggregate: m1
2721
+ }
2722
+ `,
2723
+ });
2724
+ });
2725
+ test('add GB, AGG, GB', () => {
2726
+ const from: Malloy.Query = {
2727
+ definition: {
2728
+ kind: 'arrow',
2729
+ source: {
2730
+ kind: 'source_reference',
2731
+ name: 's',
2732
+ },
2733
+ view: {
2734
+ kind: 'segment',
2735
+ operations: [],
2736
+ },
2737
+ },
2738
+ };
2739
+ expect((q: ASTQuery) => {
2740
+ const segment = q.getOrAddDefaultSegment();
2741
+ segment.addGroupBy('d1');
2742
+ segment.addAggregate('m1');
2743
+ segment.addGroupBy('d2');
2744
+ }).toModifyQuery({
2745
+ model,
2746
+ from,
2747
+ to: {
2748
+ definition: {
2749
+ kind: 'arrow',
2750
+ source: {
2751
+ kind: 'source_reference',
2752
+ name: 's',
2753
+ },
2754
+ view: {
2755
+ kind: 'segment',
2756
+ operations: [group_by('d1'), group_by('d2'), aggregate('m1')],
2757
+ },
2758
+ },
2759
+ },
2760
+ malloy: dedent`
2761
+ run: s -> {
2762
+ group_by:
2763
+ d1
2764
+ d2
2765
+ aggregate: m1
2766
+ }
2767
+ `,
2768
+ });
2769
+ });
2770
+ test('add GB, NEST, AGG', () => {
2771
+ const from: Malloy.Query = {
2772
+ definition: {
2773
+ kind: 'arrow',
2774
+ source: {
2775
+ kind: 'source_reference',
2776
+ name: 's',
2777
+ },
2778
+ view: {
2779
+ kind: 'segment',
2780
+ operations: [],
2781
+ },
2782
+ },
2783
+ };
2784
+ expect((q: ASTQuery) => {
2785
+ const segment = q.getOrAddDefaultSegment();
2786
+ segment.addGroupBy('d1');
2787
+ segment.addNest('v1');
2788
+ segment.addAggregate('m1');
2789
+ }).toModifyQuery({
2790
+ model,
2791
+ from,
2792
+ to: {
2793
+ definition: {
2794
+ kind: 'arrow',
2795
+ source: {
2796
+ kind: 'source_reference',
2797
+ name: 's',
2798
+ },
2799
+ view: {
2800
+ kind: 'segment',
2801
+ operations: [group_by('d1'), aggregate('m1'), nest('v1')],
2802
+ },
2803
+ },
2804
+ },
2805
+ malloy: dedent`
2806
+ run: s -> {
2807
+ group_by: d1
2808
+ aggregate: m1
2809
+ nest: v1
2810
+ }
2811
+ `,
2812
+ });
2813
+ });
2814
+ test('add GB, LIMIT, AGG', () => {
2815
+ const from: Malloy.Query = {
2816
+ definition: {
2817
+ kind: 'arrow',
2818
+ source: {
2819
+ kind: 'source_reference',
2820
+ name: 's',
2821
+ },
2822
+ view: {
2823
+ kind: 'segment',
2824
+ operations: [],
2825
+ },
2826
+ },
2827
+ };
2828
+ expect((q: ASTQuery) => {
2829
+ const segment = q.getOrAddDefaultSegment();
2830
+ segment.addGroupBy('d1');
2831
+ segment.setLimit(10);
2832
+ segment.addAggregate('m1');
2833
+ }).toModifyQuery({
2834
+ model,
2835
+ from,
2836
+ to: {
2837
+ definition: {
2838
+ kind: 'arrow',
2839
+ source: {
2840
+ kind: 'source_reference',
2841
+ name: 's',
2842
+ },
2843
+ view: {
2844
+ kind: 'segment',
2845
+ operations: [
2846
+ group_by('d1'),
2847
+ aggregate('m1'),
2848
+ {kind: 'limit', limit: 10},
2849
+ ],
2850
+ },
2851
+ },
2852
+ },
2853
+ malloy: dedent`
2854
+ run: s -> {
2855
+ group_by: d1
2856
+ aggregate: m1
2857
+ limit: 10
2858
+ }
2859
+ `,
2860
+ });
2861
+ });
2862
+ test('add HAVING, WHERE, GROUP BY, LIMIT', () => {
2863
+ const from: Malloy.Query = {
2864
+ definition: {
2865
+ kind: 'arrow',
2866
+ source: {
2867
+ kind: 'source_reference',
2868
+ name: 's',
2869
+ },
2870
+ view: {
2871
+ kind: 'segment',
2872
+ operations: [],
2873
+ },
2874
+ },
2875
+ };
2876
+ expect((q: ASTQuery) => {
2877
+ const segment = q.getOrAddDefaultSegment();
2878
+ segment.addHaving('m1', '> 10');
2879
+ segment.addWhere('d1', '> 10');
2880
+ segment.addGroupBy('d2');
2881
+ segment.setLimit(10);
2882
+ }).toModifyQuery({
2883
+ model,
2884
+ from,
2885
+ to: {
2886
+ definition: {
2887
+ kind: 'arrow',
2888
+ source: {
2889
+ kind: 'source_reference',
2890
+ name: 's',
2891
+ },
2892
+ view: {
2893
+ kind: 'segment',
2894
+ operations: [
2895
+ group_by('d2'),
2896
+ {
2897
+ kind: 'where',
2898
+ filter: {
2899
+ kind: 'filter_string',
2900
+ filter: '> 10',
2901
+ field_reference: {name: 'd1'},
2902
+ },
2903
+ },
2904
+ {
2905
+ kind: 'having',
2906
+ filter: {
2907
+ kind: 'filter_string',
2908
+ filter: '> 10',
2909
+ field_reference: {name: 'm1'},
2910
+ },
2911
+ },
2912
+ {kind: 'limit', limit: 10},
2913
+ ],
2914
+ },
2915
+ },
2916
+ },
2917
+ malloy: dedent`
2918
+ run: s -> {
2919
+ group_by: d2
2920
+ where: d1 ~ f\`> 10\`
2921
+ having: m1 ~ f\`> 10\`
2922
+ limit: 10
2923
+ }
2924
+ `,
2925
+ });
2926
+ });
2927
+ });
2624
2928
  });
package/src/query-ast.ts CHANGED
@@ -2574,11 +2574,13 @@ export class ASTSegmentViewDefinition
2574
2574
  }
2575
2575
 
2576
2576
  private DEFAULT_INSERTION_ORDER: Malloy.ViewOperationType[] = [
2577
- 'where',
2578
2577
  'group_by',
2579
2578
  'aggregate',
2579
+ 'where',
2580
+ 'having',
2580
2581
  'nest',
2581
2582
  'order_by',
2583
+ 'limit',
2582
2584
  ];
2583
2585
 
2584
2586
  private findInsertionPoint(kind: Malloy.ViewOperationType): number {
@@ -2600,7 +2602,7 @@ export class ASTSegmentViewDefinition
2600
2602
  );
2601
2603
  for (const laterType of laterOperations) {
2602
2604
  const firstOfType = this.firstIndexOfOperationType(laterType);
2603
- return firstOfType;
2605
+ if (firstOfType > -1) return firstOfType;
2604
2606
  }
2605
2607
  return this.operations.length;
2606
2608
  }
@@ -4191,7 +4193,7 @@ export class ASTWhereViewOperation extends ASTObjectNode<
4191
4193
  filter: ASTFilter;
4192
4194
  }
4193
4195
  > {
4194
- readonly kind: Malloy.ViewOperationType = 'nest';
4196
+ readonly kind: Malloy.ViewOperationType = 'where';
4195
4197
  constructor(public node: Malloy.ViewOperationWithWhere) {
4196
4198
  super(node, {
4197
4199
  kind: 'where',
@@ -4222,7 +4224,7 @@ export class ASTHavingViewOperation extends ASTObjectNode<
4222
4224
  filter: ASTFilter;
4223
4225
  }
4224
4226
  > {
4225
- readonly kind: Malloy.ViewOperationType = 'nest';
4227
+ readonly kind: Malloy.ViewOperationType = 'having';
4226
4228
  constructor(public node: Malloy.ViewOperationWithHaving) {
4227
4229
  super(node, {
4228
4230
  kind: 'having',
@@ -4580,8 +4582,6 @@ export class ASTAnnotation extends ASTObjectNode<
4580
4582
  value: string;
4581
4583
  }
4582
4584
  > {
4583
- readonly kind: Malloy.ViewOperationType = 'limit';
4584
-
4585
4585
  get value() {
4586
4586
  return this.children.value;
4587
4587
  }