@malloydata/malloy-tests 0.0.243-dev250313213354 → 0.0.243-dev250314032737

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
@@ -21,14 +21,14 @@
21
21
  },
22
22
  "dependencies": {
23
23
  "@jest/globals": "^29.4.3",
24
- "@malloydata/db-bigquery": "^0.0.243-dev250313213354",
25
- "@malloydata/db-duckdb": "^0.0.243-dev250313213354",
26
- "@malloydata/db-postgres": "^0.0.243-dev250313213354",
27
- "@malloydata/db-snowflake": "^0.0.243-dev250313213354",
28
- "@malloydata/db-trino": "^0.0.243-dev250313213354",
29
- "@malloydata/malloy": "^0.0.243-dev250313213354",
30
- "@malloydata/malloy-tag": "^0.0.243-dev250313213354",
31
- "@malloydata/render": "^0.0.243-dev250313213354",
24
+ "@malloydata/db-bigquery": "^0.0.243-dev250314032737",
25
+ "@malloydata/db-duckdb": "^0.0.243-dev250314032737",
26
+ "@malloydata/db-postgres": "^0.0.243-dev250314032737",
27
+ "@malloydata/db-snowflake": "^0.0.243-dev250314032737",
28
+ "@malloydata/db-trino": "^0.0.243-dev250314032737",
29
+ "@malloydata/malloy": "^0.0.243-dev250314032737",
30
+ "@malloydata/malloy-tag": "^0.0.243-dev250314032737",
31
+ "@malloydata/render": "^0.0.243-dev250314032737",
32
32
  "events": "^3.3.0",
33
33
  "jsdom": "^22.1.0",
34
34
  "luxon": "^2.4.0",
@@ -38,5 +38,5 @@
38
38
  "@types/jsdom": "^21.1.1",
39
39
  "@types/luxon": "^2.4.0"
40
40
  },
41
- "version": "0.0.243-dev250313213354"
41
+ "version": "0.0.243-dev250314032737"
42
42
  }
@@ -0,0 +1,352 @@
1
+ /*
2
+ * Copyright (c) Meta Platforms, Inc. and affiliates.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+
8
+ import {RuntimeList, allDatabases} from '../../runtimes';
9
+ import '../../util/db-jest-matchers';
10
+ import {databasesFromEnvironmentOr} from '../../util';
11
+
12
+ const runtimes = new RuntimeList(databasesFromEnvironmentOr(allDatabases));
13
+
14
+ afterAll(async () => {
15
+ await runtimes.closeAll();
16
+ });
17
+
18
+ // mtoy todo sit down with each parser and compiler and make sure there is a test for every case
19
+
20
+ describe.each(runtimes.runtimeList)('filter expressions %s', (dbName, db) => {
21
+ const q = db.getQuoter();
22
+ describe('string filter expressions', () => {
23
+ const bq = db.dialect.sqlLiteralString('x\\');
24
+ const abc = db.loadModel(`
25
+ source: abc is ${dbName}.sql("""
26
+ SELECT 'abc' as ${q`s`}, '0 - abc' as ${q`nm`}
27
+ UNION ALL SELECT 'def', '1 - def'
28
+ UNION ALL SELECT null, '2 - null'
29
+ UNION ALL SELECT '', '3 - empty'
30
+ UNION ALL SELECT ${bq}, '4 - xback'
31
+ """)
32
+ `);
33
+
34
+ test('abc', async () => {
35
+ await expect(`
36
+ run: abc -> {
37
+ where: s ~ f'abc';
38
+ select: s
39
+ }`).malloyResultMatches(abc, [{s: 'abc'}]);
40
+ });
41
+ test('abc,def', async () => {
42
+ await expect(`
43
+ run: abc -> {
44
+ where: s ~ f'abc,def';
45
+ select: nm; order_by: nm
46
+ }`).malloyResultMatches(abc, [{nm: '0 - abc'}, {nm: '1 - def'}]);
47
+ });
48
+ test('-abc', async () => {
49
+ await expect(`
50
+ run: abc -> {
51
+ where: s ~ f'-abc',
52
+ select: nm; order_by: nm asc
53
+ }`).malloyResultMatches(abc, [
54
+ {nm: '1 - def'},
55
+ {nm: '2 - null'},
56
+ {nm: '3 - empty'},
57
+ {nm: '4 - xback'},
58
+ ]);
59
+ });
60
+ test('-starts', async () => {
61
+ await expect(`
62
+ run: abc -> {
63
+ where: s ~ f'-a%',
64
+ select: nm; order_by: nm asc
65
+ }`).malloyResultMatches(abc, [
66
+ {nm: '1 - def'},
67
+ {nm: '2 - null'},
68
+ {nm: '3 - empty'},
69
+ {nm: '4 - xback'},
70
+ ]);
71
+ });
72
+ test('-contains', async () => {
73
+ await expect(`
74
+ run: abc -> {
75
+ where: s ~ f'-%b%',
76
+ select: nm; order_by: nm asc
77
+ }`).malloyResultMatches(abc, [
78
+ {nm: '1 - def'},
79
+ {nm: '2 - null'},
80
+ {nm: '3 - empty'},
81
+ {nm: '4 - xback'},
82
+ ]);
83
+ });
84
+ test('-end', async () => {
85
+ await expect(`
86
+ run: abc -> {
87
+ where: s ~ f'-%c',
88
+ select: nm; order_by: nm asc
89
+ }`).malloyResultMatches(abc, [
90
+ {nm: '1 - def'},
91
+ {nm: '2 - null'},
92
+ {nm: '3 - empty'},
93
+ {nm: '4 - xback'},
94
+ ]);
95
+ });
96
+ test('unlike', async () => {
97
+ await expect(`
98
+ run: abc -> {
99
+ where: s ~ f'-a%c',
100
+ select: nm; order_by: nm asc
101
+ }`).malloyResultMatches(abc, [
102
+ {nm: '1 - def'},
103
+ {nm: '2 - null'},
104
+ {nm: '3 - empty'},
105
+ {nm: '4 - xback'},
106
+ ]);
107
+ });
108
+ test('simple but not ___,-abc', async () => {
109
+ await expect(`
110
+ run: abc -> {
111
+ where: s ~ f'___,-abc';
112
+ select: s
113
+ }`).malloyResultMatches(abc, [{s: 'def'}]);
114
+ });
115
+ test('empty', async () => {
116
+ await expect(`
117
+ run: abc -> {
118
+ where: s ~ f'empty'
119
+ select: nm; order_by: nm asc
120
+ }`).malloyResultMatches(abc, [{nm: '2 - null'}, {nm: '3 - empty'}]);
121
+ });
122
+ test('-empty', async () => {
123
+ await expect(`
124
+ run: abc -> {
125
+ where: s ~ f'-empty'
126
+ select: nm; order_by: nm asc
127
+ }`).malloyResultMatches(abc, [
128
+ {nm: '0 - abc'},
129
+ {nm: '1 - def'},
130
+ {nm: '4 - xback'},
131
+ ]);
132
+ });
133
+ test('null', async () => {
134
+ await expect(`
135
+ run: abc -> {
136
+ where: s ~ f'null'
137
+ select: nm
138
+ }`).malloyResultMatches(abc, [{nm: '2 - null'}]);
139
+ });
140
+ test('-null', async () => {
141
+ await expect(`
142
+ run: abc -> {
143
+ where: s ~ f'-null'
144
+ select: nm; order_by: nm asc
145
+ }`).malloyResultMatches(abc, [
146
+ {nm: '0 - abc'},
147
+ {nm: '1 - def'},
148
+ {nm: '3 - empty'},
149
+ {nm: '4 - xback'},
150
+ ]);
151
+ });
152
+ test('starts', async () => {
153
+ await expect(`
154
+ run: abc -> {
155
+ where: s ~ f'a%';
156
+ select: s
157
+ }`).malloyResultMatches(abc, [{s: 'abc'}]);
158
+ });
159
+ test('contains', async () => {
160
+ await expect(`
161
+ run: abc -> {
162
+ where: s ~ f'%b%,%e%';
163
+ select: s; order_by: s asc
164
+ }`).malloyResultMatches(abc, [{s: 'abc'}, {s: 'def'}]);
165
+ });
166
+ test('simple ends', async () => {
167
+ await expect(`
168
+ run: abc -> {
169
+ where: s ~ f'%c';
170
+ select: s
171
+ }`).malloyResultMatches(abc, [{s: 'abc'}]);
172
+ });
173
+ test('ends in backslash', async () => {
174
+ await expect(`
175
+ run: abc -> {
176
+ where: s ~ f'%\\\\'
177
+ select: nm
178
+ }`).malloyResultMatches(abc, [{nm: '4 - xback'}]);
179
+ });
180
+ test('= x backslash', async () => {
181
+ await expect(`
182
+ run: abc -> {
183
+ where: s ~ f'x\\\\'
184
+ select: nm
185
+ }`).malloyResultMatches(abc, [{nm: '4 - xback'}]);
186
+ });
187
+ });
188
+
189
+ describe('numeric filter expressions', () => {
190
+ const nums = db.loadModel(`
191
+ source: nums is ${dbName}.sql("""
192
+ SELECT 0 as ${q`n`}, '0' as ${q`t`}
193
+ UNION ALL SELECT 1, '1'
194
+ UNION ALL SELECT 2, '2'
195
+ UNION ALL SELECT 3, '3'
196
+ UNION ALL SELECT 4, '4'
197
+ UNION ALL SELECT NULL, 'null'
198
+ """)
199
+ `);
200
+ test('2', async () => {
201
+ await expect(`
202
+ run: nums -> {
203
+ where: n ~ f'2'
204
+ select: n
205
+ }`).malloyResultMatches(nums, [{n: 2}]);
206
+ });
207
+ test('!= 2', async () => {
208
+ await expect(`
209
+ run: nums -> {
210
+ where: n ~ f'!= 2'
211
+ select: t; order_by: t asc
212
+ }`).malloyResultMatches(nums, [
213
+ {t: '0'},
214
+ {t: '1'},
215
+ {t: '3'},
216
+ {t: '4'},
217
+ {t: 'null'},
218
+ ]);
219
+ });
220
+ test('[1 to 3]', async () => {
221
+ await expect(`
222
+ run: nums -> {
223
+ where: n ~ f'[1 to 3]'
224
+ select: t; order_by: t asc
225
+ }`).malloyResultMatches(nums, [{t: '1'}, {t: '2'}, {t: '3'}]);
226
+ });
227
+ test('not [1 to 3]', async () => {
228
+ await expect(`
229
+ # test.verbose
230
+ run: nums -> {
231
+ where: n ~ f'not [1 to 3]'
232
+ select: t; order_by: t asc
233
+ }`).malloyResultMatches(nums, [{t: '0'}, {t: '4'}]);
234
+ });
235
+ test('123', async () => {
236
+ await expect(`
237
+ run: nums -> {
238
+ where: n ~ f'1,2,3'
239
+ select: t; order_by: t asc
240
+ }`).malloyResultMatches(nums, [{t: '1'}, {t: '2'}, {t: '3'}]);
241
+ });
242
+ test('not 123', async () => {
243
+ await expect(`
244
+ run: nums -> {
245
+ where: n ~ f'not 1,2,3'
246
+ select: t; order_by: t asc
247
+ }`).malloyResultMatches(nums, [{t: '0'}, {t: '4'}, {t: 'null'}]);
248
+ });
249
+ test('(1 to 3]', async () => {
250
+ await expect(`
251
+ run: nums -> {
252
+ where: n ~ f'(1 to 3]'
253
+ select: t; order_by: t asc
254
+ }`).malloyResultMatches(nums, [{t: '2'}, {t: '3'}]);
255
+ });
256
+ test('[1 to 3)', async () => {
257
+ await expect(`
258
+ run: nums -> {
259
+ where: n ~ f'[1 to 3)'
260
+ select: t; order_by: t asc
261
+ }`).malloyResultMatches(nums, [{t: '1'}, {t: '2'}]);
262
+ });
263
+ test('(1 to 3)', async () => {
264
+ await expect(`
265
+ run: nums -> {
266
+ where: n ~ f'(1 to 3)'
267
+ select: t; order_by: t asc
268
+ }`).malloyResultMatches(nums, [{t: '2'}]);
269
+ });
270
+ test('>3', async () => {
271
+ await expect(`
272
+ run: nums -> {
273
+ where: n ~ f'>3'
274
+ select: n
275
+ }`).malloyResultMatches(nums, [{n: 4}]);
276
+ });
277
+ test('>=3', async () => {
278
+ await expect(`
279
+ run: nums -> {
280
+ where: n ~ f'>=3'
281
+ select: n; order_by:n asc
282
+ }`).malloyResultMatches(nums, [{n: 3}, {n: 4}]);
283
+ });
284
+ test('<1', async () => {
285
+ await expect(`
286
+ run: nums -> {
287
+ where: n ~ f'<1'
288
+ select: n
289
+ }`).malloyResultMatches(nums, [{n: 0}]);
290
+ });
291
+ test('<=1', async () => {
292
+ await expect(`
293
+ run: nums -> {
294
+ where: n ~ f'<=1'
295
+ select: n; order_by: n asc
296
+ }`).malloyResultMatches(nums, [{n: 0}, {n: 1}]);
297
+ });
298
+ });
299
+
300
+ // mysql doesn't have true booleans ...
301
+ describe('boolean filter expressions', () => {
302
+ const facts = db.loadModel(`
303
+ source: facts is ${dbName}.sql("""
304
+ SELECT true as ${q`b`}, 'true' as ${q`t`}
305
+ UNION ALL SELECT false, 'false'
306
+ UNION ALL SELECT NULL, 'null'
307
+ """)
308
+ `);
309
+ test.when(dbName !== 'mysql')('true', async () => {
310
+ await expect(`
311
+ run: facts -> {
312
+ where: b ~ f'true'
313
+ select: t; order_by: t asc
314
+ }`).malloyResultMatches(facts, [{t: 'true'}]);
315
+ });
316
+ test.when(dbName !== 'mysql')('true', async () => {
317
+ await expect(`
318
+ run: facts -> {
319
+ where: b ~ f'true'
320
+ select: t; order_by: t asc
321
+ }`).malloyResultMatches(facts, [{t: 'true'}]);
322
+ });
323
+ test.when(dbName !== 'mysql')('false', async () => {
324
+ await expect(`
325
+ run: facts -> {
326
+ where: b ~ f'false'
327
+ select: t; order_by: t asc
328
+ }`).malloyResultMatches(facts, [{t: 'false'}, {t: 'null'}]);
329
+ });
330
+ test.when(dbName !== 'mysql')('=false', async () => {
331
+ await expect(`
332
+ run: facts -> {
333
+ where: b ~ f'=false'
334
+ select: t; order_by: t asc
335
+ }`).malloyResultMatches(facts, [{t: 'false'}]);
336
+ });
337
+ test.when(dbName !== 'mysql')('null', async () => {
338
+ await expect(`
339
+ run: facts -> {
340
+ where: b ~ f'null'
341
+ select: t; order_by: t asc
342
+ }`).malloyResultMatches(facts, [{t: 'null'}]);
343
+ });
344
+ test.when(dbName !== 'mysql')('not null', async () => {
345
+ await expect(`
346
+ run: facts -> {
347
+ where: b ~ f'not null'
348
+ select: t; order_by: t asc
349
+ }`).malloyResultMatches(facts, [{t: 'false'}, {t: 'true'}]);
350
+ });
351
+ });
352
+ });
@@ -1,158 +0,0 @@
1
- /*
2
- * Copyright (c) Meta Platforms, Inc. and affiliates.
3
- *
4
- * This source code is licensed under the MIT license found in the
5
- * LICENSE file in the root directory of this source tree.
6
- */
7
-
8
- import {RuntimeList, allDatabases} from '../../runtimes';
9
- import '../../util/db-jest-matchers';
10
- import {databasesFromEnvironmentOr} from '../../util';
11
-
12
- const runtimes = new RuntimeList(databasesFromEnvironmentOr(allDatabases));
13
-
14
- afterAll(async () => {
15
- await runtimes.closeAll();
16
- });
17
-
18
- describe.each(runtimes.runtimeList)('filter expressions %s', (dbName, db) => {
19
- const q = db.getQuoter();
20
- const abc = db.loadModel(`
21
- source: abc is ${dbName}.sql("""
22
- SELECT 'abc' as ${q`s`}, '0 - abc' as ${q`nm`}
23
- UNION ALL SELECT 'def', '1 - def'
24
- UNION ALL SELECT null, '2 - null'
25
- UNION ALL SELECT '', '3 - empty'
26
- """)
27
- `);
28
-
29
- test('abc', async () => {
30
- await expect(`
31
- run: abc -> {
32
- where: s ~ f'abc';
33
- select: s
34
- }`).malloyResultMatches(abc, [{s: 'abc'}]);
35
- });
36
- test('abc,def', async () => {
37
- await expect(`
38
- run: abc -> {
39
- where: s ~ f'abc,def';
40
- select: nm; order_by: nm
41
- }`).malloyResultMatches(abc, [{nm: '0 - abc'}, {nm: '1 - def'}]);
42
- });
43
- test('-abc', async () => {
44
- await expect(`
45
- run: abc -> {
46
- where: s ~ f'-abc',
47
- select: nm; order_by: nm asc
48
- }`).malloyResultMatches(abc, [
49
- {nm: '1 - def'},
50
- {nm: '2 - null'},
51
- {nm: '3 - empty'},
52
- ]);
53
- });
54
- test('-starts', async () => {
55
- await expect(`
56
- run: abc -> {
57
- where: s ~ f'-a%',
58
- select: nm; order_by: nm asc
59
- }`).malloyResultMatches(abc, [
60
- {nm: '1 - def'},
61
- {nm: '2 - null'},
62
- {nm: '3 - empty'},
63
- ]);
64
- });
65
- test('-contains', async () => {
66
- await expect(`
67
- run: abc -> {
68
- where: s ~ f'-%b%',
69
- select: nm; order_by: nm asc
70
- }`).malloyResultMatches(abc, [
71
- {nm: '1 - def'},
72
- {nm: '2 - null'},
73
- {nm: '3 - empty'},
74
- ]);
75
- });
76
- test('-end', async () => {
77
- await expect(`
78
- run: abc -> {
79
- where: s ~ f'-%c',
80
- select: nm; order_by: nm asc
81
- }`).malloyResultMatches(abc, [
82
- {nm: '1 - def'},
83
- {nm: '2 - null'},
84
- {nm: '3 - empty'},
85
- ]);
86
- });
87
- test('unlike', async () => {
88
- await expect(`
89
- run: abc -> {
90
- where: s ~ f'-a%c',
91
- select: nm; order_by: nm asc
92
- }`).malloyResultMatches(abc, [
93
- {nm: '1 - def'},
94
- {nm: '2 - null'},
95
- {nm: '3 - empty'},
96
- ]);
97
- });
98
- test('simple but not _%,-abc', async () => {
99
- await expect(`
100
- run: abc -> {
101
- where: s ~ f'_%,-abc';
102
- select: s
103
- }`).malloyResultMatches(abc, [{s: 'def'}]);
104
- });
105
- test('empty', async () => {
106
- await expect(`
107
- run: abc -> {
108
- where: s ~ f'empty'
109
- select: nm; order_by: nm asc
110
- }`).malloyResultMatches(abc, [{nm: '2 - null'}, {nm: '3 - empty'}]);
111
- });
112
- test('-empty', async () => {
113
- await expect(`
114
- run: abc -> {
115
- where: s ~ f'-empty'
116
- select: nm; order_by: nm asc
117
- }`).malloyResultMatches(abc, [{nm: '0 - abc'}, {nm: '1 - def'}]);
118
- });
119
- test('null', async () => {
120
- await expect(`
121
- run: abc -> {
122
- where: s ~ f'null'
123
- select: nm
124
- }`).malloyResultMatches(abc, [{nm: '2 - null'}]);
125
- });
126
- test('-null', async () => {
127
- await expect(`
128
- run: abc -> {
129
- where: s ~ f'-null'
130
- select: nm; order_by: nm asc
131
- }`).malloyResultMatches(abc, [
132
- {nm: '0 - abc'},
133
- {nm: '1 - def'},
134
- {nm: '3 - empty'},
135
- ]);
136
- });
137
- test('starts', async () => {
138
- await expect(`
139
- run: abc -> {
140
- where: s ~ f'a%';
141
- select: s
142
- }`).malloyResultMatches(abc, [{s: 'abc'}]);
143
- });
144
- test('contains', async () => {
145
- await expect(`
146
- run: abc -> {
147
- where: s ~ f'%b%,%e%';
148
- select: s; order_by: s asc
149
- }`).malloyResultMatches(abc, [{s: 'abc'}, {s: 'def'}]);
150
- });
151
- test('ends', async () => {
152
- await expect(`
153
- run: abc -> {
154
- where: s ~ f'%c';
155
- select: s
156
- }`).malloyResultMatches(abc, [{s: 'abc'}]);
157
- });
158
- });