@malloydata/malloy-tests 0.0.135 → 0.0.136-dev240326234246
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/dist/api.spec.d.ts +1 -0
- package/dist/api.spec.js +113 -0
- package/dist/api.spec.js.map +1 -0
- package/dist/databases/all/db_index.spec.d.ts +1 -0
- package/dist/databases/all/db_index.spec.js +126 -0
- package/dist/databases/all/db_index.spec.js.map +1 -0
- package/dist/databases/all/expr.spec.d.ts +1 -0
- package/dist/databases/all/expr.spec.js +652 -0
- package/dist/databases/all/expr.spec.js.map +1 -0
- package/dist/databases/all/functions.spec.d.ts +1 -0
- package/dist/databases/all/functions.spec.js +1180 -0
- package/dist/databases/all/functions.spec.js.map +1 -0
- package/dist/databases/all/join.spec.d.ts +1 -0
- package/dist/databases/all/join.spec.js +255 -0
- package/dist/databases/all/join.spec.js.map +1 -0
- package/dist/databases/all/lenses.spec.d.ts +1 -0
- package/dist/databases/all/lenses.spec.js +374 -0
- package/dist/databases/all/lenses.spec.js.map +1 -0
- package/dist/databases/all/nomodel.spec.d.ts +1 -0
- package/dist/databases/all/nomodel.spec.js +1070 -0
- package/dist/databases/all/nomodel.spec.js.map +1 -0
- package/dist/databases/all/orderby.spec.d.ts +1 -0
- package/dist/databases/all/orderby.spec.js +170 -0
- package/dist/databases/all/orderby.spec.js.map +1 -0
- package/dist/databases/all/problems.spec.d.ts +1 -0
- package/dist/databases/all/problems.spec.js +106 -0
- package/dist/databases/all/problems.spec.js.map +1 -0
- package/dist/databases/all/sql_expressions.spec.d.ts +1 -0
- package/dist/databases/all/sql_expressions.spec.js +73 -0
- package/dist/databases/all/sql_expressions.spec.js.map +1 -0
- package/dist/databases/all/time.spec.d.ts +1 -0
- package/dist/databases/all/time.spec.js +602 -0
- package/dist/databases/all/time.spec.js.map +1 -0
- package/dist/databases/bigquery/double_truncation.spec.d.ts +1 -0
- package/dist/databases/bigquery/double_truncation.spec.js +50 -0
- package/dist/databases/bigquery/double_truncation.spec.js.map +1 -0
- package/dist/databases/bigquery/handexpr.spec.d.ts +1 -0
- package/dist/databases/bigquery/handexpr.spec.js +723 -0
- package/dist/databases/bigquery/handexpr.spec.js.map +1 -0
- package/dist/databases/bigquery/injestion_time_partitioning.spec.d.ts +1 -0
- package/dist/databases/bigquery/injestion_time_partitioning.spec.js +235 -0
- package/dist/databases/bigquery/injestion_time_partitioning.spec.js.map +1 -0
- package/dist/databases/bigquery/joined_filters.spec.d.ts +1 -0
- package/dist/databases/bigquery/joined_filters.spec.js +72 -0
- package/dist/databases/bigquery/joined_filters.spec.js.map +1 -0
- package/dist/databases/bigquery/json.spec.d.ts +1 -0
- package/dist/databases/bigquery/json.spec.js +66 -0
- package/dist/databases/bigquery/json.spec.js.map +1 -0
- package/dist/databases/bigquery/malloy_query.spec.d.ts +1 -0
- package/dist/databases/bigquery/malloy_query.spec.js +840 -0
- package/dist/databases/bigquery/malloy_query.spec.js.map +1 -0
- package/dist/databases/bigquery/performance.skipped.spec.d.ts +1 -0
- package/dist/databases/bigquery/performance.skipped.spec.js +70 -0
- package/dist/databases/bigquery/performance.skipped.spec.js.map +1 -0
- package/dist/databases/bigquery/time.spec.d.ts +1 -0
- package/dist/databases/bigquery/time.spec.js +52 -0
- package/dist/databases/bigquery/time.spec.js.map +1 -0
- package/dist/databases/bigquery/wildcard_table_names.spec.d.ts +1 -0
- package/dist/databases/bigquery/wildcard_table_names.spec.js +212 -0
- package/dist/databases/bigquery/wildcard_table_names.spec.js.map +1 -0
- package/dist/databases/bigquery-duckdb/nested_source_table.spec.d.ts +1 -0
- package/dist/databases/bigquery-duckdb/nested_source_table.spec.js +213 -0
- package/dist/databases/bigquery-duckdb/nested_source_table.spec.js.map +1 -0
- package/dist/databases/duckdb/duckdb.spec.d.ts +1 -0
- package/dist/databases/duckdb/duckdb.spec.js +124 -0
- package/dist/databases/duckdb/duckdb.spec.js.map +1 -0
- package/dist/databases/duckdb/streaming.spec.d.ts +1 -0
- package/dist/databases/duckdb/streaming.spec.js +142 -0
- package/dist/databases/duckdb/streaming.spec.js.map +1 -0
- package/dist/databases/multi-connection/multi_connection.spec.d.ts +1 -0
- package/dist/databases/multi-connection/multi_connection.spec.js +120 -0
- package/dist/databases/multi-connection/multi_connection.spec.js.map +1 -0
- package/dist/databases/postgres/postgres.spec.d.ts +1 -0
- package/dist/databases/postgres/postgres.spec.js +140 -0
- package/dist/databases/postgres/postgres.spec.js.map +1 -0
- package/dist/databases/shared/test_list.d.ts +3 -0
- package/dist/databases/shared/test_list.js +5 -0
- package/dist/databases/shared/test_list.js.map +1 -0
- package/dist/databases/streaming/streaming.spec.d.ts +1 -0
- package/dist/databases/streaming/streaming.spec.js +93 -0
- package/dist/databases/streaming/streaming.spec.js.map +1 -0
- package/dist/dependencies.spec.d.ts +1 -0
- package/dist/dependencies.spec.js +63 -0
- package/dist/dependencies.spec.js.map +1 -0
- package/dist/index.d.ts +4 -0
- package/dist/index.js +49 -0
- package/dist/index.js.map +1 -0
- package/dist/jestMatcher.spec.d.ts +1 -0
- package/dist/jestMatcher.spec.js +81 -0
- package/dist/jestMatcher.spec.js.map +1 -0
- package/dist/model/sql_source.spec.d.ts +1 -0
- package/dist/model/sql_source.spec.js +47 -0
- package/dist/model/sql_source.spec.js.map +1 -0
- package/dist/models/faa_model.d.ts +5 -0
- package/dist/models/faa_model.js +997 -0
- package/dist/models/faa_model.js.map +1 -0
- package/dist/models/medicare_model.d.ts +4 -0
- package/dist/models/medicare_model.js +259 -0
- package/dist/models/medicare_model.js.map +1 -0
- package/dist/render/drill.spec.d.ts +1 -0
- package/dist/render/drill.spec.js +107 -0
- package/dist/render/drill.spec.js.map +1 -0
- package/dist/render/render.spec.d.ts +1 -0
- package/dist/render/render.spec.js +548 -0
- package/dist/render/render.spec.js.map +1 -0
- package/dist/runtimes.d.ts +35 -0
- package/dist/runtimes.js +180 -0
- package/dist/runtimes.js.map +1 -0
- package/dist/tags.spec.d.ts +8 -0
- package/dist/tags.spec.js +490 -0
- package/dist/tags.spec.js.map +1 -0
- package/dist/util/db-jest-matchers.d.ts +30 -0
- package/dist/util/db-jest-matchers.js +157 -0
- package/dist/util/db-jest-matchers.js.map +1 -0
- package/dist/util/index.d.ts +15 -0
- package/dist/util/index.js +182 -0
- package/dist/util/index.js.map +1 -0
- package/package.json +8 -8
|
@@ -0,0 +1,840 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/*
|
|
3
|
+
* Copyright 2023 Google LLC
|
|
4
|
+
*
|
|
5
|
+
* Permission is hereby granted, free of charge, to any person obtaining
|
|
6
|
+
* a copy of this software and associated documentation files
|
|
7
|
+
* (the "Software"), to deal in the Software without restriction,
|
|
8
|
+
* including without limitation the rights to use, copy, modify, merge,
|
|
9
|
+
* publish, distribute, sublicense, and/or sell copies of the Software,
|
|
10
|
+
* and to permit persons to whom the Software is furnished to do so,
|
|
11
|
+
* subject to the following conditions:
|
|
12
|
+
*
|
|
13
|
+
* The above copyright notice and this permission notice shall be
|
|
14
|
+
* included in all copies or substantial portions of the Software.
|
|
15
|
+
*
|
|
16
|
+
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
|
17
|
+
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
|
18
|
+
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
|
19
|
+
* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
|
|
20
|
+
* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
|
|
21
|
+
* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
|
|
22
|
+
* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
|
23
|
+
*/
|
|
24
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
25
|
+
if (k2 === undefined) k2 = k;
|
|
26
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
27
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
28
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
29
|
+
}
|
|
30
|
+
Object.defineProperty(o, k2, desc);
|
|
31
|
+
}) : (function(o, m, k, k2) {
|
|
32
|
+
if (k2 === undefined) k2 = k;
|
|
33
|
+
o[k2] = m[k];
|
|
34
|
+
}));
|
|
35
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
36
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
37
|
+
}) : function(o, v) {
|
|
38
|
+
o["default"] = v;
|
|
39
|
+
});
|
|
40
|
+
var __importStar = (this && this.__importStar) || function (mod) {
|
|
41
|
+
if (mod && mod.__esModule) return mod;
|
|
42
|
+
var result = {};
|
|
43
|
+
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
|
|
44
|
+
__setModuleDefault(result, mod);
|
|
45
|
+
return result;
|
|
46
|
+
};
|
|
47
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
48
|
+
const globals_1 = require("@jest/globals");
|
|
49
|
+
const malloy = __importStar(require("@malloydata/malloy"));
|
|
50
|
+
const faa_model_1 = require("../../models/faa_model");
|
|
51
|
+
const runtimes_1 = require("../../runtimes");
|
|
52
|
+
const util_1 = require("../../util");
|
|
53
|
+
require("../../util/db-jest-matchers");
|
|
54
|
+
const runtimeList = new runtimes_1.RuntimeList(['bigquery']);
|
|
55
|
+
const runtime = runtimeList.runtimeMap.get('bigquery');
|
|
56
|
+
if (runtime === undefined) {
|
|
57
|
+
throw new Error("Couldn't build runtime");
|
|
58
|
+
}
|
|
59
|
+
const bq = runtime.connection;
|
|
60
|
+
function compileQueryFromQueryDef(model, query) {
|
|
61
|
+
return model._loadQueryFromQueryDef(query).getSQL();
|
|
62
|
+
}
|
|
63
|
+
async function compileQuery(model, query) {
|
|
64
|
+
return await model.loadQuery(query).getSQL();
|
|
65
|
+
}
|
|
66
|
+
async function runQuery(model, query) {
|
|
67
|
+
return await model.loadQuery(query).run();
|
|
68
|
+
}
|
|
69
|
+
async function bqCompile(sql) {
|
|
70
|
+
try {
|
|
71
|
+
await bq.executeSQLRaw(`WITH test AS(\n${sql}) SELECT 1 as one`);
|
|
72
|
+
}
|
|
73
|
+
catch (e) {
|
|
74
|
+
malloy.Malloy.log.error(`SQL: didn't compile\n=============\n${sql}`);
|
|
75
|
+
throw e;
|
|
76
|
+
}
|
|
77
|
+
return true;
|
|
78
|
+
}
|
|
79
|
+
const [describe] = (0, util_1.describeIfDatabaseAvailable)(['bigquery']);
|
|
80
|
+
describe('BigQuery expression tests', () => {
|
|
81
|
+
const faa = runtime._loadModelFromModelDef(faa_model_1.testModel);
|
|
82
|
+
// EXPLORE flights
|
|
83
|
+
// ->{
|
|
84
|
+
// carrier,
|
|
85
|
+
// flight_count,
|
|
86
|
+
// routes is { origin_code, destination_code, route_flights is flight_count
|
|
87
|
+
// ORDER BY route_flights DESC
|
|
88
|
+
// LIMIT 5 )
|
|
89
|
+
// | PROJECT
|
|
90
|
+
// carrier,
|
|
91
|
+
// routes.origin_code,
|
|
92
|
+
// routes.route_flights,
|
|
93
|
+
// flight_count / routes.route_flights as percent_of_carrier_flights
|
|
94
|
+
it('turtle_requery', async () => {
|
|
95
|
+
const sql = await compileQueryFromQueryDef(faa, {
|
|
96
|
+
structRef: 'flights',
|
|
97
|
+
pipeline: [
|
|
98
|
+
// top 5 routes per carrier
|
|
99
|
+
{
|
|
100
|
+
type: 'reduce',
|
|
101
|
+
queryFields: (0, util_1.fToQF)([
|
|
102
|
+
'carrier',
|
|
103
|
+
'flight_count',
|
|
104
|
+
{
|
|
105
|
+
type: 'turtle',
|
|
106
|
+
name: 'routes',
|
|
107
|
+
pipeline: [
|
|
108
|
+
{
|
|
109
|
+
type: 'reduce',
|
|
110
|
+
queryFields: (0, util_1.fToQF)([
|
|
111
|
+
'origin_code',
|
|
112
|
+
'destination_code',
|
|
113
|
+
'flight_count',
|
|
114
|
+
{
|
|
115
|
+
type: 'number',
|
|
116
|
+
name: 'route_flights',
|
|
117
|
+
expressionType: 'aggregate',
|
|
118
|
+
e: [
|
|
119
|
+
{
|
|
120
|
+
type: 'aggregate',
|
|
121
|
+
function: 'count',
|
|
122
|
+
e: [],
|
|
123
|
+
},
|
|
124
|
+
],
|
|
125
|
+
},
|
|
126
|
+
]),
|
|
127
|
+
},
|
|
128
|
+
],
|
|
129
|
+
},
|
|
130
|
+
]),
|
|
131
|
+
limit: 5,
|
|
132
|
+
orderBy: [{ dir: 'desc', field: 'carrier' }],
|
|
133
|
+
},
|
|
134
|
+
// carrier top routes
|
|
135
|
+
{
|
|
136
|
+
type: 'project',
|
|
137
|
+
queryFields: (0, util_1.fToQF)([
|
|
138
|
+
'carrier',
|
|
139
|
+
'flight_count',
|
|
140
|
+
'routes.origin_code',
|
|
141
|
+
'routes.route_flights',
|
|
142
|
+
]),
|
|
143
|
+
},
|
|
144
|
+
],
|
|
145
|
+
});
|
|
146
|
+
await bqCompile(sql);
|
|
147
|
+
});
|
|
148
|
+
it('step_0', async () => {
|
|
149
|
+
const sql = await compileQueryFromQueryDef(faa, {
|
|
150
|
+
structRef: 'flights',
|
|
151
|
+
pipeline: [
|
|
152
|
+
{ type: 'reduce', queryFields: (0, util_1.fToQF)(['carriers.name', 'flight_count']) },
|
|
153
|
+
],
|
|
154
|
+
});
|
|
155
|
+
await bqCompile(sql);
|
|
156
|
+
});
|
|
157
|
+
it('filtered_measures', async () => {
|
|
158
|
+
const sql = await compileQueryFromQueryDef(faa, {
|
|
159
|
+
structRef: 'flights',
|
|
160
|
+
filterList: [
|
|
161
|
+
(0, util_1.fStringEq)('origin.state', 'CA'),
|
|
162
|
+
(0, util_1.fStringEq)('destination.state', 'NY'),
|
|
163
|
+
],
|
|
164
|
+
pipeline: [
|
|
165
|
+
{ type: 'reduce', queryFields: (0, util_1.fToQF)(['carriers.name', 'flight_count']) },
|
|
166
|
+
],
|
|
167
|
+
});
|
|
168
|
+
await bqCompile(sql);
|
|
169
|
+
});
|
|
170
|
+
it('timestamp', async () => {
|
|
171
|
+
const sql = await compileQueryFromQueryDef(faa, {
|
|
172
|
+
structRef: 'flights',
|
|
173
|
+
pipeline: [
|
|
174
|
+
{
|
|
175
|
+
queryFields: [
|
|
176
|
+
{
|
|
177
|
+
as: 'dep_year',
|
|
178
|
+
name: 'dep_time',
|
|
179
|
+
timeframe: 'year',
|
|
180
|
+
type: 'timestamp',
|
|
181
|
+
},
|
|
182
|
+
{
|
|
183
|
+
as: 'dep_month',
|
|
184
|
+
name: 'dep_time',
|
|
185
|
+
timeframe: 'month',
|
|
186
|
+
type: 'timestamp',
|
|
187
|
+
},
|
|
188
|
+
{
|
|
189
|
+
as: 'dep_week',
|
|
190
|
+
name: 'dep_time',
|
|
191
|
+
timeframe: 'week',
|
|
192
|
+
type: 'timestamp',
|
|
193
|
+
},
|
|
194
|
+
{
|
|
195
|
+
as: 'dep_date',
|
|
196
|
+
name: 'dep_time',
|
|
197
|
+
timeframe: 'day',
|
|
198
|
+
type: 'timestamp',
|
|
199
|
+
},
|
|
200
|
+
{
|
|
201
|
+
as: 'dep_hour',
|
|
202
|
+
name: 'dep_time',
|
|
203
|
+
timeframe: 'hour',
|
|
204
|
+
type: 'timestamp',
|
|
205
|
+
},
|
|
206
|
+
{
|
|
207
|
+
as: 'dep_minute',
|
|
208
|
+
name: 'dep_time',
|
|
209
|
+
timeframe: 'minute',
|
|
210
|
+
type: 'timestamp',
|
|
211
|
+
},
|
|
212
|
+
{
|
|
213
|
+
as: 'dep_second',
|
|
214
|
+
name: 'dep_time',
|
|
215
|
+
timeframe: 'second',
|
|
216
|
+
type: 'timestamp',
|
|
217
|
+
},
|
|
218
|
+
{
|
|
219
|
+
type: 'number',
|
|
220
|
+
name: 'total_distance_ca',
|
|
221
|
+
expressionType: 'aggregate',
|
|
222
|
+
e: [
|
|
223
|
+
{
|
|
224
|
+
type: 'filterExpression',
|
|
225
|
+
filterList: [(0, util_1.fStringEq)('origin.state', 'CA')],
|
|
226
|
+
e: [
|
|
227
|
+
{
|
|
228
|
+
type: 'aggregate',
|
|
229
|
+
function: 'sum',
|
|
230
|
+
e: [{ type: 'field', path: ['distance'] }],
|
|
231
|
+
},
|
|
232
|
+
],
|
|
233
|
+
},
|
|
234
|
+
],
|
|
235
|
+
},
|
|
236
|
+
],
|
|
237
|
+
limit: 20,
|
|
238
|
+
type: 'reduce',
|
|
239
|
+
},
|
|
240
|
+
],
|
|
241
|
+
});
|
|
242
|
+
await bqCompile(sql);
|
|
243
|
+
});
|
|
244
|
+
it('bucket_test', async () => {
|
|
245
|
+
const sql = await compileQueryFromQueryDef(faa, {
|
|
246
|
+
pipeline: [
|
|
247
|
+
{
|
|
248
|
+
queryFields: (0, util_1.fToQF)([
|
|
249
|
+
{
|
|
250
|
+
bucketFilter: 'AA,WN,DL',
|
|
251
|
+
bucketOther: 'Other Carrier',
|
|
252
|
+
name: 'carrier',
|
|
253
|
+
type: 'string',
|
|
254
|
+
},
|
|
255
|
+
'flight_count',
|
|
256
|
+
]),
|
|
257
|
+
orderBy: [{ dir: 'asc', field: 2 }],
|
|
258
|
+
type: 'reduce',
|
|
259
|
+
},
|
|
260
|
+
],
|
|
261
|
+
structRef: 'flights',
|
|
262
|
+
});
|
|
263
|
+
await bqCompile(sql);
|
|
264
|
+
});
|
|
265
|
+
it('flights_by_carrier', async () => {
|
|
266
|
+
const sql = await compileQuery(faa, 'run: flights->flights_by_carrier');
|
|
267
|
+
await bqCompile(sql);
|
|
268
|
+
});
|
|
269
|
+
it('simple_reduce', async () => {
|
|
270
|
+
const sql = await compileQueryFromQueryDef(faa, {
|
|
271
|
+
structRef: 'flights',
|
|
272
|
+
pipeline: [
|
|
273
|
+
{ type: 'reduce', queryFields: (0, util_1.fToQF)(['carrier', 'flight_count']) },
|
|
274
|
+
],
|
|
275
|
+
});
|
|
276
|
+
await bqCompile(sql);
|
|
277
|
+
});
|
|
278
|
+
it('two_sums', async () => {
|
|
279
|
+
const sql = await compileQueryFromQueryDef(faa, {
|
|
280
|
+
structRef: 'flights',
|
|
281
|
+
pipeline: [
|
|
282
|
+
{
|
|
283
|
+
type: 'reduce',
|
|
284
|
+
queryFields: (0, util_1.fToQF)([
|
|
285
|
+
{
|
|
286
|
+
type: 'number',
|
|
287
|
+
expressionType: 'aggregate',
|
|
288
|
+
name: 'total_distance',
|
|
289
|
+
e: [
|
|
290
|
+
{
|
|
291
|
+
type: 'aggregate',
|
|
292
|
+
function: 'sum',
|
|
293
|
+
e: [{ type: 'field', path: ['distance'] }],
|
|
294
|
+
},
|
|
295
|
+
],
|
|
296
|
+
},
|
|
297
|
+
'aircraft.aircraft_models.total_seats',
|
|
298
|
+
]),
|
|
299
|
+
},
|
|
300
|
+
],
|
|
301
|
+
});
|
|
302
|
+
await bqCompile(sql);
|
|
303
|
+
});
|
|
304
|
+
it('first_fragment', async () => {
|
|
305
|
+
const sql = await compileQueryFromQueryDef(faa, {
|
|
306
|
+
structRef: 'flights',
|
|
307
|
+
pipeline: [
|
|
308
|
+
{
|
|
309
|
+
type: 'reduce',
|
|
310
|
+
queryFields: (0, util_1.fToQF)([
|
|
311
|
+
{
|
|
312
|
+
type: 'string',
|
|
313
|
+
name: 'carrier',
|
|
314
|
+
e: [
|
|
315
|
+
'UPPER(',
|
|
316
|
+
{ type: 'field', path: ['carriers', 'nickname'] },
|
|
317
|
+
')',
|
|
318
|
+
],
|
|
319
|
+
},
|
|
320
|
+
'flight_count',
|
|
321
|
+
]),
|
|
322
|
+
},
|
|
323
|
+
],
|
|
324
|
+
});
|
|
325
|
+
await bqCompile(sql);
|
|
326
|
+
});
|
|
327
|
+
it('sum_in_expr', async () => {
|
|
328
|
+
const sql = await compileQueryFromQueryDef(faa, {
|
|
329
|
+
structRef: 'flights',
|
|
330
|
+
pipeline: [
|
|
331
|
+
{
|
|
332
|
+
queryFields: (0, util_1.fToQF)([
|
|
333
|
+
'carriers.name',
|
|
334
|
+
{
|
|
335
|
+
type: 'number',
|
|
336
|
+
expressionType: 'aggregate',
|
|
337
|
+
name: 'total_distance',
|
|
338
|
+
e: [
|
|
339
|
+
{
|
|
340
|
+
type: 'aggregate',
|
|
341
|
+
function: 'sum',
|
|
342
|
+
e: [{ type: 'field', path: ['distance'] }],
|
|
343
|
+
},
|
|
344
|
+
],
|
|
345
|
+
},
|
|
346
|
+
]),
|
|
347
|
+
type: 'reduce',
|
|
348
|
+
},
|
|
349
|
+
],
|
|
350
|
+
});
|
|
351
|
+
await bqCompile(sql);
|
|
352
|
+
});
|
|
353
|
+
it('filtered_sum_in_expr', async () => {
|
|
354
|
+
const sql = await compileQueryFromQueryDef(faa, {
|
|
355
|
+
structRef: 'flights',
|
|
356
|
+
pipeline: [
|
|
357
|
+
{
|
|
358
|
+
type: 'reduce',
|
|
359
|
+
queryFields: (0, util_1.fToQF)([
|
|
360
|
+
'aircraft.aircraft_models.manufacturer',
|
|
361
|
+
{
|
|
362
|
+
type: 'number',
|
|
363
|
+
expressionType: 'aggregate',
|
|
364
|
+
name: 'total_distance',
|
|
365
|
+
e: [
|
|
366
|
+
{
|
|
367
|
+
type: 'filterExpression',
|
|
368
|
+
filterList: [(0, util_1.fStringEq)('origin_code', 'SFO')],
|
|
369
|
+
e: [
|
|
370
|
+
{
|
|
371
|
+
type: 'aggregate',
|
|
372
|
+
function: 'sum',
|
|
373
|
+
e: [{ type: 'field', path: ['distance'] }],
|
|
374
|
+
},
|
|
375
|
+
],
|
|
376
|
+
},
|
|
377
|
+
],
|
|
378
|
+
},
|
|
379
|
+
]),
|
|
380
|
+
},
|
|
381
|
+
],
|
|
382
|
+
});
|
|
383
|
+
await bqCompile(sql);
|
|
384
|
+
});
|
|
385
|
+
it('dynamic_measure', async () => {
|
|
386
|
+
const sql = await compileQueryFromQueryDef(faa, {
|
|
387
|
+
structRef: 'flights',
|
|
388
|
+
pipeline: [
|
|
389
|
+
{
|
|
390
|
+
type: 'reduce',
|
|
391
|
+
queryFields: (0, util_1.fToQF)([
|
|
392
|
+
'origin.state',
|
|
393
|
+
'flight_count',
|
|
394
|
+
{
|
|
395
|
+
type: 'number',
|
|
396
|
+
expressionType: 'aggregate',
|
|
397
|
+
name: 'total_distance',
|
|
398
|
+
e: [
|
|
399
|
+
{
|
|
400
|
+
type: 'filterExpression',
|
|
401
|
+
filterList: [(0, util_1.fStringEq)('origin_code', 'SFO')],
|
|
402
|
+
e: [
|
|
403
|
+
{
|
|
404
|
+
type: 'aggregate',
|
|
405
|
+
function: 'sum',
|
|
406
|
+
e: [{ type: 'field', path: ['distance'] }],
|
|
407
|
+
},
|
|
408
|
+
],
|
|
409
|
+
},
|
|
410
|
+
],
|
|
411
|
+
},
|
|
412
|
+
]),
|
|
413
|
+
filterList: [(0, util_1.fStringEq)('carriers.code', 'WN')],
|
|
414
|
+
},
|
|
415
|
+
],
|
|
416
|
+
});
|
|
417
|
+
await bqCompile(sql);
|
|
418
|
+
});
|
|
419
|
+
it('flights.flights_by_model', async () => {
|
|
420
|
+
const sql = await compileQuery(faa, 'run: flights->flights_by_model');
|
|
421
|
+
await bqCompile(sql);
|
|
422
|
+
});
|
|
423
|
+
it('flights.aircraft_facts_test', async () => {
|
|
424
|
+
const sql = await compileQuery(faa, 'run: flights->aircraft_facts_test');
|
|
425
|
+
await bqCompile(sql);
|
|
426
|
+
});
|
|
427
|
+
it('flights.measures_first', async () => {
|
|
428
|
+
const sql = await compileQuery(faa, 'run:flights->measures_first');
|
|
429
|
+
await bqCompile(sql);
|
|
430
|
+
});
|
|
431
|
+
it('flights.carriers_by_total_engines', async () => {
|
|
432
|
+
const sql = await compileQuery(faa, 'run: flights->carriers_by_total_engines');
|
|
433
|
+
await bqCompile(sql);
|
|
434
|
+
});
|
|
435
|
+
it('flights.first_turtle', async () => {
|
|
436
|
+
const sql = await compileQuery(faa, 'run: flights->first_turtle');
|
|
437
|
+
await bqCompile(sql);
|
|
438
|
+
});
|
|
439
|
+
it('flights.top_5_routes_carriers', async () => {
|
|
440
|
+
const sql = await compileQuery(faa, 'run: flights->top_5_routes_carriers');
|
|
441
|
+
await bqCompile(sql);
|
|
442
|
+
});
|
|
443
|
+
it('flights.new_york_airports', async () => {
|
|
444
|
+
const sql = await compileQuery(faa, 'run: flights->new_york_airports');
|
|
445
|
+
await bqCompile(sql);
|
|
446
|
+
});
|
|
447
|
+
it('flights.flights_by_carrier_with_totals', async () => {
|
|
448
|
+
const sql = await compileQuery(faa, 'run: flights->flights_by_carrier_with_totals');
|
|
449
|
+
await bqCompile(sql);
|
|
450
|
+
});
|
|
451
|
+
it('lotsoturtles', async () => {
|
|
452
|
+
const sql = await compileQueryFromQueryDef(faa, {
|
|
453
|
+
structRef: 'flights',
|
|
454
|
+
pipeline: [
|
|
455
|
+
{
|
|
456
|
+
queryFields: (0, util_1.fToQF)([
|
|
457
|
+
'origin.state',
|
|
458
|
+
'flight_count',
|
|
459
|
+
'flights_by_model',
|
|
460
|
+
'flights_by_carrier',
|
|
461
|
+
'measures_first',
|
|
462
|
+
'first_turtle',
|
|
463
|
+
]),
|
|
464
|
+
type: 'reduce',
|
|
465
|
+
},
|
|
466
|
+
],
|
|
467
|
+
});
|
|
468
|
+
await bqCompile(sql);
|
|
469
|
+
});
|
|
470
|
+
it('flights.search_index', async () => {
|
|
471
|
+
const sql = await compileQuery(faa, 'run: flights->search_index');
|
|
472
|
+
await bqCompile(sql);
|
|
473
|
+
});
|
|
474
|
+
it('turtle_turtle_filter', async () => {
|
|
475
|
+
const result = await runQuery(faa, `
|
|
476
|
+
run: bigquery.table('malloytest.airports')->{
|
|
477
|
+
where: faa_region ? ~'A%'
|
|
478
|
+
order_by: 1
|
|
479
|
+
group_by: faa_region
|
|
480
|
+
aggregate: airport_count is count()
|
|
481
|
+
nest: state is {
|
|
482
|
+
where: state ?'CA'|'NY'
|
|
483
|
+
group_by: state
|
|
484
|
+
nest: code is {
|
|
485
|
+
where: major='Y'
|
|
486
|
+
top: 10
|
|
487
|
+
order_by: 1
|
|
488
|
+
group_by: code
|
|
489
|
+
}
|
|
490
|
+
}
|
|
491
|
+
}
|
|
492
|
+
-> {
|
|
493
|
+
where: state.code.code != null
|
|
494
|
+
group_by: state.code.code
|
|
495
|
+
}
|
|
496
|
+
`);
|
|
497
|
+
expect(result.data.value[0]['code']).toBe('ACV');
|
|
498
|
+
});
|
|
499
|
+
it('flights.search_index', async () => {
|
|
500
|
+
const sql = await compileQuery(faa, 'run: flights->search_index');
|
|
501
|
+
await bqCompile(sql);
|
|
502
|
+
});
|
|
503
|
+
it('medicare_test.turtle_city_zip', async () => {
|
|
504
|
+
const sql = await compileQuery(faa, 'run: medicare_test->turtle_city_zip');
|
|
505
|
+
await bqCompile(sql);
|
|
506
|
+
});
|
|
507
|
+
it('medicare_test.triple_turtle', async () => {
|
|
508
|
+
const sql = await compileQuery(faa, 'run: medicare_test->triple_turtle');
|
|
509
|
+
await bqCompile(sql);
|
|
510
|
+
});
|
|
511
|
+
it('medicare_test.rollup_by_location', async () => {
|
|
512
|
+
const sql = await compileQuery(faa, 'run: medicare_test->rollup_by_location');
|
|
513
|
+
await bqCompile(sql);
|
|
514
|
+
});
|
|
515
|
+
it('flights.flights_routes_sessionized', async () => {
|
|
516
|
+
const sql = await compileQuery(faa, 'run: flights->flights_routes_sessionized');
|
|
517
|
+
await bqCompile(sql);
|
|
518
|
+
});
|
|
519
|
+
it('flights.flights_aircraft_sessionized', async () => {
|
|
520
|
+
const sql = await compileQuery(faa, 'run: flights->flights_aircraft_sessionized');
|
|
521
|
+
await bqCompile(sql);
|
|
522
|
+
});
|
|
523
|
+
it('flights.flights_by_manufacturer', async () => {
|
|
524
|
+
const sql = await compileQuery(faa, 'run: flights->flights_by_manufacturer');
|
|
525
|
+
await bqCompile(sql);
|
|
526
|
+
});
|
|
527
|
+
it('flights.flights_by_carrier_2001_2002', async () => {
|
|
528
|
+
const sql = await compileQuery(faa, 'run: flights->flights_by_carrier_2001_2002');
|
|
529
|
+
await bqCompile(sql);
|
|
530
|
+
});
|
|
531
|
+
it('timeframes aliased', async () => {
|
|
532
|
+
const sql = await compileQuery(faa, `
|
|
533
|
+
run: flights->{
|
|
534
|
+
group_by: mon is dep_time.month
|
|
535
|
+
}
|
|
536
|
+
`);
|
|
537
|
+
await bqCompile(sql);
|
|
538
|
+
});
|
|
539
|
+
it('count distinct', async () => {
|
|
540
|
+
const sql = await compileQuery(faa, `
|
|
541
|
+
run: flights->{
|
|
542
|
+
aggregate: carrier_count is count(carrier)
|
|
543
|
+
}
|
|
544
|
+
`);
|
|
545
|
+
// console.log(result.sql);
|
|
546
|
+
await bqCompile(sql);
|
|
547
|
+
});
|
|
548
|
+
it('table_base_on_query', async () => {
|
|
549
|
+
const result = await faa
|
|
550
|
+
._loadQueryFromQueryDef({
|
|
551
|
+
structRef: 'medicare_state_facts',
|
|
552
|
+
pipeline: [
|
|
553
|
+
{
|
|
554
|
+
type: 'reduce',
|
|
555
|
+
queryFields: (0, util_1.fToQF)(['provider_state', 'num_providers']),
|
|
556
|
+
orderBy: [{ dir: 'desc', field: 2 }],
|
|
557
|
+
},
|
|
558
|
+
],
|
|
559
|
+
})
|
|
560
|
+
.run();
|
|
561
|
+
expect(result.data.value[0]['num_providers']).toBe(296);
|
|
562
|
+
});
|
|
563
|
+
});
|
|
564
|
+
const airportModelText = `
|
|
565
|
+
source: airports is bigquery.table('malloy-data.malloytest.airports') extend {
|
|
566
|
+
primary_key: code
|
|
567
|
+
measure: airport_count is count()
|
|
568
|
+
|
|
569
|
+
view: by_fac_type is {
|
|
570
|
+
group_by: fac_type
|
|
571
|
+
aggregate: airport_count
|
|
572
|
+
}
|
|
573
|
+
|
|
574
|
+
view: by_state is {
|
|
575
|
+
group_by: state
|
|
576
|
+
aggregate: airport_count
|
|
577
|
+
}
|
|
578
|
+
|
|
579
|
+
view: by_county is {
|
|
580
|
+
group_by: county
|
|
581
|
+
aggregate: airport_count
|
|
582
|
+
}
|
|
583
|
+
}
|
|
584
|
+
|
|
585
|
+
query: ca_airports is airports->by_fac_type + { where: state ? 'CA' | 'NY'}
|
|
586
|
+
`;
|
|
587
|
+
describe('airport_tests', () => {
|
|
588
|
+
let model;
|
|
589
|
+
beforeAll(async () => {
|
|
590
|
+
model = runtime.loadModel(airportModelText);
|
|
591
|
+
});
|
|
592
|
+
it('airport_count', async () => {
|
|
593
|
+
const result = await runQuery(model, `
|
|
594
|
+
run: airports->{
|
|
595
|
+
aggregate: a is count()
|
|
596
|
+
}
|
|
597
|
+
`);
|
|
598
|
+
expect(result.data.value[0]['a']).toBe(19793);
|
|
599
|
+
});
|
|
600
|
+
it('turtle_from_hell', async () => {
|
|
601
|
+
const result = await runQuery(model, `
|
|
602
|
+
run: airports-> {
|
|
603
|
+
nest: zero is {
|
|
604
|
+
nest: by_faa_region_i is { where: county ~'I%' and state != NULL
|
|
605
|
+
group_by: faa_region
|
|
606
|
+
aggregate: airport_count
|
|
607
|
+
nest: by_state is {
|
|
608
|
+
group_by: state
|
|
609
|
+
aggregate: airport_count
|
|
610
|
+
nest: by_county is {
|
|
611
|
+
group_by: county
|
|
612
|
+
aggregate: airport_count
|
|
613
|
+
}
|
|
614
|
+
}
|
|
615
|
+
}
|
|
616
|
+
nest: by_faa_region_Z is { where: county ~'Z%' and state !=NULL
|
|
617
|
+
group_by: faa_region
|
|
618
|
+
aggregate: airport_count
|
|
619
|
+
nest: by_state is {
|
|
620
|
+
group_by: state
|
|
621
|
+
aggregate: airport_count
|
|
622
|
+
nest: by_county is {
|
|
623
|
+
group_by: county
|
|
624
|
+
aggregate: airport_count
|
|
625
|
+
}
|
|
626
|
+
}
|
|
627
|
+
}
|
|
628
|
+
}
|
|
629
|
+
} -> { limit: 1
|
|
630
|
+
select: zero.by_faa_region_Z.by_state.by_county.county
|
|
631
|
+
}
|
|
632
|
+
|
|
633
|
+
`);
|
|
634
|
+
expect(result.data.value[0]['county']).toBe('ZAVALA');
|
|
635
|
+
});
|
|
636
|
+
it('nested_project', async () => {
|
|
637
|
+
const result = await runQuery(model, `
|
|
638
|
+
run: airports -> {
|
|
639
|
+
group_by: county
|
|
640
|
+
nest: stuff is {
|
|
641
|
+
select: elevation
|
|
642
|
+
order_by: 1 desc
|
|
643
|
+
limit: 10
|
|
644
|
+
}
|
|
645
|
+
order_by: 1
|
|
646
|
+
limit: 1
|
|
647
|
+
} -> {
|
|
648
|
+
select: stuff.elevation
|
|
649
|
+
order_by: 1 desc
|
|
650
|
+
limit: 1
|
|
651
|
+
}
|
|
652
|
+
`);
|
|
653
|
+
expect(result.data.value[0]['elevation']).toBe(1836);
|
|
654
|
+
});
|
|
655
|
+
it('nested_sums', async () => {
|
|
656
|
+
const result = await runQuery(model, `
|
|
657
|
+
run: airports->{
|
|
658
|
+
aggregate: airport_count
|
|
659
|
+
nest: by_state is {
|
|
660
|
+
group_by: state
|
|
661
|
+
aggregate: airport_count
|
|
662
|
+
nest: by_fac_type is {
|
|
663
|
+
group_by: fac_type
|
|
664
|
+
aggregate: airport_count
|
|
665
|
+
}
|
|
666
|
+
}
|
|
667
|
+
} -> {
|
|
668
|
+
group_by: airport_count
|
|
669
|
+
aggregate:
|
|
670
|
+
sum_state is by_state.sum(by_state.airport_count),
|
|
671
|
+
sum_fac is by_state.by_fac_type.sum(by_state.by_fac_type.airport_count)
|
|
672
|
+
}
|
|
673
|
+
`);
|
|
674
|
+
// console.log(result.sql);
|
|
675
|
+
expect(result.data.value[0]['sum_state']).toBe(19793);
|
|
676
|
+
expect(result.data.value[0]['sum_fac']).toBe(19793);
|
|
677
|
+
});
|
|
678
|
+
it('pipeline_as_declared_turtle', async () => {
|
|
679
|
+
const result = await runQuery(model, `
|
|
680
|
+
source: my_airports is airports extend {
|
|
681
|
+
view: pipe_turtle is {
|
|
682
|
+
aggregate: a is airport_count
|
|
683
|
+
} -> {
|
|
684
|
+
select: a
|
|
685
|
+
}
|
|
686
|
+
}
|
|
687
|
+
run: my_airports->pipe_turtle
|
|
688
|
+
`);
|
|
689
|
+
expect(result.data.value[0]['a']).toBe(19793);
|
|
690
|
+
});
|
|
691
|
+
it('pipeline Turtle', async () => {
|
|
692
|
+
const result = await runQuery(model, `
|
|
693
|
+
run: bigquery.table('malloytest.airports')->{
|
|
694
|
+
aggregate: airport_count is count()
|
|
695
|
+
nest: pipe_turtle is {
|
|
696
|
+
group_by:
|
|
697
|
+
state
|
|
698
|
+
county
|
|
699
|
+
aggregate: a is count()
|
|
700
|
+
} -> {
|
|
701
|
+
select:
|
|
702
|
+
state is upper(state)
|
|
703
|
+
a
|
|
704
|
+
} -> {
|
|
705
|
+
group_by: state
|
|
706
|
+
aggregate: total_airports is a.sum()
|
|
707
|
+
}
|
|
708
|
+
}
|
|
709
|
+
`);
|
|
710
|
+
expect(
|
|
711
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
712
|
+
result.data.value[0].pipe_turtle[0].total_airports).toBe(1845);
|
|
713
|
+
});
|
|
714
|
+
it.skip('crossjoined turtles', async () => {
|
|
715
|
+
// const result = await runQuery(model,`
|
|
716
|
+
// explore airports
|
|
717
|
+
// ->{
|
|
718
|
+
// top_seaplane is { limit 5 : [fac_type: 'SEAPLANE BASE']
|
|
719
|
+
// state
|
|
720
|
+
// airport_count
|
|
721
|
+
// )
|
|
722
|
+
// by_state is {
|
|
723
|
+
// state
|
|
724
|
+
// airport_count
|
|
725
|
+
// )
|
|
726
|
+
// | project : [top_seaplane.state = by_state.state]
|
|
727
|
+
// by_state.*
|
|
728
|
+
// `);
|
|
729
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
730
|
+
// expect((result.data.value[0] as any).pipe_turtle[0].total_airports).toBe(1845);
|
|
731
|
+
});
|
|
732
|
+
it.skip('crossjoined turtles as turtle', async () => {
|
|
733
|
+
// const result = await runQuery(model,`
|
|
734
|
+
// explore airports
|
|
735
|
+
// ->{
|
|
736
|
+
// airport_count
|
|
737
|
+
// tp is {
|
|
738
|
+
// top_seaplane is { limit 5 : [fac_type: 'SEAPLANE BASE']
|
|
739
|
+
// state
|
|
740
|
+
// airport_count
|
|
741
|
+
// )
|
|
742
|
+
// by_state is {
|
|
743
|
+
// state
|
|
744
|
+
// airport_count
|
|
745
|
+
// )
|
|
746
|
+
// | project : [top_seaplane.state = by_state.state]
|
|
747
|
+
// by_state.*
|
|
748
|
+
// )
|
|
749
|
+
// `);
|
|
750
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
751
|
+
// expect((result.data.value[0] as any).pipe_turtle[0].total_airports).toBe(1845);
|
|
752
|
+
});
|
|
753
|
+
it('string_expressions', async () => {
|
|
754
|
+
const result = await runQuery(model, `
|
|
755
|
+
run: airports->{
|
|
756
|
+
group_by: lower_state is lower(state)
|
|
757
|
+
order_by: 1 DESC
|
|
758
|
+
limit: 10
|
|
759
|
+
}
|
|
760
|
+
`);
|
|
761
|
+
expect(result.data.value[0]['lower_state']).toBe('wy');
|
|
762
|
+
});
|
|
763
|
+
it('half_count', async () => {
|
|
764
|
+
const result = await runQuery(model, `
|
|
765
|
+
run: airports->{
|
|
766
|
+
aggregate: half is airport_count/2.0
|
|
767
|
+
}
|
|
768
|
+
`);
|
|
769
|
+
expect(result.data.value[0]['half']).toBe(9896.5);
|
|
770
|
+
});
|
|
771
|
+
});
|
|
772
|
+
describe('sql injection tests', () => {
|
|
773
|
+
const model = runtime._loadModelFromModelDef(faa_model_1.testModel);
|
|
774
|
+
jest.setTimeout(100000);
|
|
775
|
+
(0, globals_1.test)('string literal escapes quotes', async () => {
|
|
776
|
+
const result = await runQuery(model, `
|
|
777
|
+
run: bigquery.table('malloytest.state_facts')->{ group_by: test is 'foo\\''
|
|
778
|
+
}
|
|
779
|
+
`);
|
|
780
|
+
expect(result.data.value[0]['test']).toBe("foo'");
|
|
781
|
+
});
|
|
782
|
+
(0, globals_1.test)('string filter escapes quotes', async () => {
|
|
783
|
+
const result = await runQuery(model, `
|
|
784
|
+
run: bigquery.table('malloytest.state_facts')->{ aggregate: test is count() { where: state ? 'foo\\'' } }
|
|
785
|
+
`);
|
|
786
|
+
expect(result.data.value[0]['test']).toBe(0);
|
|
787
|
+
});
|
|
788
|
+
(0, globals_1.test)('string literal escapes backslashes', async () => {
|
|
789
|
+
const result = await runQuery(model, `
|
|
790
|
+
run: bigquery.table('malloytest.state_facts')->{ group_by: test is 'foo\\\\\\''
|
|
791
|
+
}
|
|
792
|
+
`);
|
|
793
|
+
expect(result.data.value[0]['test']).toBe("foo\\'");
|
|
794
|
+
});
|
|
795
|
+
(0, globals_1.test)('string filter escapes backslashes', async () => {
|
|
796
|
+
const result = await runQuery(model, `
|
|
797
|
+
run: bigquery.table('malloytest.state_facts')->{ aggregate: test is count() { where: state ? 'foo\\\\\\'' }}
|
|
798
|
+
`);
|
|
799
|
+
expect(result.data.value[0]['test']).toBe(0);
|
|
800
|
+
});
|
|
801
|
+
(0, globals_1.test)('comment in string', async () => {
|
|
802
|
+
const result = await runQuery(model, `
|
|
803
|
+
run: bigquery.table('malloytest.state_facts')->{ group_by: test is 'foo \\\\'--'
|
|
804
|
+
}
|
|
805
|
+
`);
|
|
806
|
+
expect(result.data.value[0]['test']).toBe('foo \\');
|
|
807
|
+
});
|
|
808
|
+
(0, globals_1.test)('comment in string filter', async () => {
|
|
809
|
+
let error;
|
|
810
|
+
try {
|
|
811
|
+
await runQuery(model, `
|
|
812
|
+
run: bigquery.table('malloytest.state_facts')->{ aggregate: test is count() { where: state ? 'foo \\\\' THEN 0 else 1 END) as test--'
|
|
813
|
+
}} `);
|
|
814
|
+
}
|
|
815
|
+
catch (e) {
|
|
816
|
+
error = e;
|
|
817
|
+
}
|
|
818
|
+
expect(error).not.toBeUndefined();
|
|
819
|
+
});
|
|
820
|
+
globals_1.test.todo("'malloytest\\'.tables' produces the wrong error...");
|
|
821
|
+
(0, globals_1.test)('comment in literal', async () => {
|
|
822
|
+
const result = await runQuery(model, `
|
|
823
|
+
run: flights->{ group_by: test is 'foo \\\\'--'
|
|
824
|
+
}
|
|
825
|
+
`);
|
|
826
|
+
expect(result.data.value[0]['test']).toBe('foo \\');
|
|
827
|
+
});
|
|
828
|
+
});
|
|
829
|
+
describe('unsupported type tests', () => {
|
|
830
|
+
it('can read unsupported types in schema', async () => {
|
|
831
|
+
const result = await runtime
|
|
832
|
+
.loadQuery(`run:
|
|
833
|
+
bigquery.sql("SELECT ST_GEOGFROMTEXT('LINESTRING(1 2, 3 4)') as geo")
|
|
834
|
+
-> { select: geo }
|
|
835
|
+
`)
|
|
836
|
+
.run();
|
|
837
|
+
expect(result.data.value[0]['geo']).toBeDefined();
|
|
838
|
+
});
|
|
839
|
+
});
|
|
840
|
+
//# sourceMappingURL=malloy_query.spec.js.map
|