@carto/api-client 0.4.0-alpha.6 → 0.4.1-alpha.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/CHANGELOG.md +8 -0
- package/build/api/query.d.ts +1 -1
- package/build/api-client.cjs +221 -35
- package/build/api-client.cjs.map +1 -1
- package/build/api-client.modern.js +229 -51
- package/build/api-client.modern.js.map +1 -1
- package/build/models/model.d.ts +7 -1
- package/build/sources/types.d.ts +36 -41
- package/build/spatial-index.d.ts +11 -0
- package/build/utils.d.ts +1 -1
- package/build/widget-sources/types.d.ts +8 -1
- package/build/widget-sources/widget-base-source.d.ts +0 -1
- package/package.json +2 -3
- package/src/api/query.ts +1 -2
- package/src/models/model.ts +47 -24
- package/src/sources/h3-query-source.ts +7 -1
- package/src/sources/h3-table-source.ts +6 -1
- package/src/sources/quadbin-query-source.ts +6 -1
- package/src/sources/quadbin-table-source.ts +6 -1
- package/src/sources/types.ts +41 -45
- package/src/sources/vector-query-source.ts +4 -1
- package/src/sources/vector-table-source.ts +5 -1
- package/src/spatial-index.ts +119 -0
- package/src/utils.ts +1 -1
- package/src/widget-sources/types.ts +9 -1
- package/src/widget-sources/widget-base-source.ts +185 -19
package/src/utils.ts
CHANGED
|
@@ -57,7 +57,7 @@ export function normalizeObjectKeys<T, R extends Row<T>>(el: R): R {
|
|
|
57
57
|
}
|
|
58
58
|
|
|
59
59
|
/** @internalRemarks Source: @carto/react-core */
|
|
60
|
-
export function assert(condition: unknown, message: string) {
|
|
60
|
+
export function assert(condition: unknown, message: string): asserts condition {
|
|
61
61
|
if (!condition) {
|
|
62
62
|
throw new Error(message);
|
|
63
63
|
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {TileResolution} from '../sources/types';
|
|
1
|
+
import {SpatialFilterPolyfillMode, TileResolution} from '../sources/types';
|
|
2
2
|
import {
|
|
3
3
|
GroupDateType,
|
|
4
4
|
SortColumnType,
|
|
@@ -10,11 +10,19 @@ import {
|
|
|
10
10
|
* WIDGET API REQUESTS
|
|
11
11
|
*/
|
|
12
12
|
|
|
13
|
+
export interface ViewState {
|
|
14
|
+
zoom: number;
|
|
15
|
+
latitude: number;
|
|
16
|
+
longitude: number;
|
|
17
|
+
}
|
|
18
|
+
|
|
13
19
|
/** Common options for {@link WidgetBaseSource} requests. */
|
|
14
20
|
interface BaseRequestOptions {
|
|
15
21
|
spatialFilter?: SpatialFilter;
|
|
22
|
+
spatialFiltersMode?: SpatialFilterPolyfillMode;
|
|
16
23
|
abortController?: AbortController;
|
|
17
24
|
filterOwner?: string;
|
|
25
|
+
viewState?: ViewState;
|
|
18
26
|
}
|
|
19
27
|
|
|
20
28
|
/** Options for {@link WidgetBaseSource#getCategories}. */
|
|
@@ -16,9 +16,10 @@ import {
|
|
|
16
16
|
TableResponse,
|
|
17
17
|
TimeSeriesRequestOptions,
|
|
18
18
|
TimeSeriesResponse,
|
|
19
|
+
ViewState,
|
|
19
20
|
} from './types.js';
|
|
20
21
|
import {FilterLogicalOperator, Filter} from '../types.js';
|
|
21
|
-
import {getApplicableFilters, normalizeObjectKeys} from '../utils.js';
|
|
22
|
+
import {assert, getApplicableFilters, normalizeObjectKeys} from '../utils.js';
|
|
22
23
|
import {getClient} from '../client.js';
|
|
23
24
|
import {ModelSource} from '../models/model.js';
|
|
24
25
|
import {SourceOptions} from '../sources/index.js';
|
|
@@ -27,10 +28,10 @@ import {
|
|
|
27
28
|
DEFAULT_GEO_COLUMN,
|
|
28
29
|
DEFAULT_TILE_RESOLUTION,
|
|
29
30
|
} from '../constants-internal.js';
|
|
31
|
+
import {getSpatialFiltersResolution} from '../spatial-index.js';
|
|
30
32
|
|
|
31
33
|
export interface WidgetBaseSourceProps extends Omit<SourceOptions, 'filters'> {
|
|
32
34
|
apiVersion?: ApiVersion;
|
|
33
|
-
geoColumn?: string;
|
|
34
35
|
filters?: Record<string, Filter>;
|
|
35
36
|
filtersLogicalOperator?: FilterLogicalOperator;
|
|
36
37
|
}
|
|
@@ -51,7 +52,6 @@ export abstract class WidgetBaseSource<Props extends WidgetBaseSourceProps> {
|
|
|
51
52
|
clientId: getClient(),
|
|
52
53
|
filters: {},
|
|
53
54
|
filtersLogicalOperator: 'and',
|
|
54
|
-
geoColumn: DEFAULT_GEO_COLUMN,
|
|
55
55
|
};
|
|
56
56
|
|
|
57
57
|
constructor(props: Props) {
|
|
@@ -78,7 +78,8 @@ export abstract class WidgetBaseSource<Props extends WidgetBaseSourceProps> {
|
|
|
78
78
|
connectionName: props.connectionName,
|
|
79
79
|
filters: getApplicableFilters(owner, props.filters),
|
|
80
80
|
filtersLogicalOperator: props.filtersLogicalOperator,
|
|
81
|
-
|
|
81
|
+
spatialDataType: props.spatialDataType,
|
|
82
|
+
spatialDataColumn: props.spatialDataColumn,
|
|
82
83
|
};
|
|
83
84
|
}
|
|
84
85
|
|
|
@@ -93,14 +94,35 @@ export abstract class WidgetBaseSource<Props extends WidgetBaseSourceProps> {
|
|
|
93
94
|
async getCategories(
|
|
94
95
|
options: CategoryRequestOptions
|
|
95
96
|
): Promise<CategoryResponse> {
|
|
96
|
-
const {
|
|
97
|
+
const {
|
|
98
|
+
filterOwner,
|
|
99
|
+
spatialFilter,
|
|
100
|
+
spatialFiltersMode,
|
|
101
|
+
abortController,
|
|
102
|
+
viewState,
|
|
103
|
+
...params
|
|
104
|
+
} = options;
|
|
97
105
|
const {column, operation, operationColumn} = params;
|
|
106
|
+
const source = this.getModelSource(filterOwner);
|
|
107
|
+
|
|
108
|
+
let spatialFiltersResolution: number | undefined;
|
|
109
|
+
if (spatialFilter && source.spatialDataType !== 'geo') {
|
|
110
|
+
spatialFiltersResolution = getSpatialFiltersResolution({
|
|
111
|
+
source,
|
|
112
|
+
viewState,
|
|
113
|
+
});
|
|
114
|
+
}
|
|
98
115
|
|
|
99
116
|
type CategoriesModelResponse = {rows: {name: string; value: number}[]};
|
|
100
117
|
|
|
101
118
|
return executeModel({
|
|
102
119
|
model: 'category',
|
|
103
|
-
source: {
|
|
120
|
+
source: {
|
|
121
|
+
...source,
|
|
122
|
+
spatialFiltersResolution,
|
|
123
|
+
spatialFiltersMode,
|
|
124
|
+
spatialFilter,
|
|
125
|
+
},
|
|
104
126
|
params: {
|
|
105
127
|
column,
|
|
106
128
|
operation,
|
|
@@ -125,14 +147,35 @@ export abstract class WidgetBaseSource<Props extends WidgetBaseSourceProps> {
|
|
|
125
147
|
async getFeatures(
|
|
126
148
|
options: FeaturesRequestOptions
|
|
127
149
|
): Promise<FeaturesResponse> {
|
|
128
|
-
const {
|
|
150
|
+
const {
|
|
151
|
+
filterOwner,
|
|
152
|
+
spatialFilter,
|
|
153
|
+
spatialFiltersMode,
|
|
154
|
+
abortController,
|
|
155
|
+
viewState,
|
|
156
|
+
...params
|
|
157
|
+
} = options;
|
|
129
158
|
const {columns, dataType, featureIds, z, limit, tileResolution} = params;
|
|
159
|
+
const source = this.getModelSource(filterOwner);
|
|
160
|
+
|
|
161
|
+
let spatialFiltersResolution: number | undefined;
|
|
162
|
+
if (spatialFilter && source.spatialDataType !== 'geo') {
|
|
163
|
+
spatialFiltersResolution = getSpatialFiltersResolution({
|
|
164
|
+
source,
|
|
165
|
+
viewState,
|
|
166
|
+
});
|
|
167
|
+
}
|
|
130
168
|
|
|
131
169
|
type FeaturesModelResponse = {rows: Record<string, unknown>[]};
|
|
132
170
|
|
|
133
171
|
return executeModel({
|
|
134
172
|
model: 'pick',
|
|
135
|
-
source: {
|
|
173
|
+
source: {
|
|
174
|
+
...source,
|
|
175
|
+
spatialFiltersResolution,
|
|
176
|
+
spatialFiltersMode,
|
|
177
|
+
spatialFilter,
|
|
178
|
+
},
|
|
136
179
|
params: {
|
|
137
180
|
columns,
|
|
138
181
|
dataType,
|
|
@@ -159,17 +202,33 @@ export abstract class WidgetBaseSource<Props extends WidgetBaseSourceProps> {
|
|
|
159
202
|
const {
|
|
160
203
|
filterOwner,
|
|
161
204
|
spatialFilter,
|
|
205
|
+
spatialFiltersMode,
|
|
162
206
|
abortController,
|
|
163
207
|
operationExp,
|
|
208
|
+
viewState,
|
|
164
209
|
...params
|
|
165
210
|
} = options;
|
|
166
211
|
const {column, operation} = params;
|
|
212
|
+
const source = this.getModelSource(filterOwner);
|
|
213
|
+
|
|
214
|
+
let spatialFiltersResolution: number | undefined;
|
|
215
|
+
if (spatialFilter && source.spatialDataType !== 'geo') {
|
|
216
|
+
spatialFiltersResolution = getSpatialFiltersResolution({
|
|
217
|
+
source,
|
|
218
|
+
viewState,
|
|
219
|
+
});
|
|
220
|
+
}
|
|
167
221
|
|
|
168
222
|
type FormulaModelResponse = {rows: {value: number}[]};
|
|
169
223
|
|
|
170
224
|
return executeModel({
|
|
171
225
|
model: 'formula',
|
|
172
|
-
source: {
|
|
226
|
+
source: {
|
|
227
|
+
...source,
|
|
228
|
+
spatialFiltersResolution,
|
|
229
|
+
spatialFiltersMode,
|
|
230
|
+
spatialFilter,
|
|
231
|
+
},
|
|
173
232
|
params: {column: column ?? '*', operation, operationExp},
|
|
174
233
|
opts: {abortController},
|
|
175
234
|
}).then((res: FormulaModelResponse) => normalizeObjectKeys(res.rows[0]));
|
|
@@ -186,14 +245,35 @@ export abstract class WidgetBaseSource<Props extends WidgetBaseSourceProps> {
|
|
|
186
245
|
async getHistogram(
|
|
187
246
|
options: HistogramRequestOptions
|
|
188
247
|
): Promise<HistogramResponse> {
|
|
189
|
-
const {
|
|
248
|
+
const {
|
|
249
|
+
filterOwner,
|
|
250
|
+
spatialFilter,
|
|
251
|
+
spatialFiltersMode,
|
|
252
|
+
abortController,
|
|
253
|
+
viewState,
|
|
254
|
+
...params
|
|
255
|
+
} = options;
|
|
190
256
|
const {column, operation, ticks} = params;
|
|
257
|
+
const source = this.getModelSource(filterOwner);
|
|
258
|
+
|
|
259
|
+
let spatialFiltersResolution: number | undefined;
|
|
260
|
+
if (spatialFilter && source.spatialDataType !== 'geo') {
|
|
261
|
+
spatialFiltersResolution = getSpatialFiltersResolution({
|
|
262
|
+
source,
|
|
263
|
+
viewState,
|
|
264
|
+
});
|
|
265
|
+
}
|
|
191
266
|
|
|
192
267
|
type HistogramModelResponse = {rows: {tick: number; value: number}[]};
|
|
193
268
|
|
|
194
269
|
const data = await executeModel({
|
|
195
270
|
model: 'histogram',
|
|
196
|
-
source: {
|
|
271
|
+
source: {
|
|
272
|
+
...source,
|
|
273
|
+
spatialFiltersResolution,
|
|
274
|
+
spatialFiltersMode,
|
|
275
|
+
spatialFilter,
|
|
276
|
+
},
|
|
197
277
|
params: {column, operation, ticks},
|
|
198
278
|
opts: {abortController},
|
|
199
279
|
}).then((res: HistogramModelResponse) => normalizeObjectKeys(res.rows));
|
|
@@ -221,14 +301,35 @@ export abstract class WidgetBaseSource<Props extends WidgetBaseSourceProps> {
|
|
|
221
301
|
* or rendering a range slider UI for filtering.
|
|
222
302
|
*/
|
|
223
303
|
async getRange(options: RangeRequestOptions): Promise<RangeResponse> {
|
|
224
|
-
const {
|
|
304
|
+
const {
|
|
305
|
+
filterOwner,
|
|
306
|
+
spatialFilter,
|
|
307
|
+
spatialFiltersMode,
|
|
308
|
+
abortController,
|
|
309
|
+
viewState,
|
|
310
|
+
...params
|
|
311
|
+
} = options;
|
|
225
312
|
const {column} = params;
|
|
313
|
+
const source = this.getModelSource(filterOwner);
|
|
314
|
+
|
|
315
|
+
let spatialFiltersResolution: number | undefined;
|
|
316
|
+
if (spatialFilter && source.spatialDataType !== 'geo') {
|
|
317
|
+
spatialFiltersResolution = getSpatialFiltersResolution({
|
|
318
|
+
source,
|
|
319
|
+
viewState,
|
|
320
|
+
});
|
|
321
|
+
}
|
|
226
322
|
|
|
227
323
|
type RangeModelResponse = {rows: {min: number; max: number}[]};
|
|
228
324
|
|
|
229
325
|
return executeModel({
|
|
230
326
|
model: 'range',
|
|
231
|
-
source: {
|
|
327
|
+
source: {
|
|
328
|
+
...source,
|
|
329
|
+
spatialFiltersResolution,
|
|
330
|
+
spatialFiltersMode,
|
|
331
|
+
spatialFilter,
|
|
332
|
+
},
|
|
232
333
|
params: {column},
|
|
233
334
|
opts: {abortController},
|
|
234
335
|
}).then((res: RangeModelResponse) => normalizeObjectKeys(res.rows[0]));
|
|
@@ -243,10 +344,27 @@ export abstract class WidgetBaseSource<Props extends WidgetBaseSourceProps> {
|
|
|
243
344
|
* values. Suitable for rendering scatter plots.
|
|
244
345
|
*/
|
|
245
346
|
async getScatter(options: ScatterRequestOptions): Promise<ScatterResponse> {
|
|
246
|
-
const {
|
|
347
|
+
const {
|
|
348
|
+
filterOwner,
|
|
349
|
+
spatialFilter,
|
|
350
|
+
spatialFiltersMode,
|
|
351
|
+
abortController,
|
|
352
|
+
viewState,
|
|
353
|
+
...params
|
|
354
|
+
} = options;
|
|
247
355
|
const {xAxisColumn, xAxisJoinOperation, yAxisColumn, yAxisJoinOperation} =
|
|
248
356
|
params;
|
|
249
357
|
|
|
358
|
+
const source = this.getModelSource(filterOwner);
|
|
359
|
+
|
|
360
|
+
let spatialFiltersResolution: number | undefined;
|
|
361
|
+
if (spatialFilter && source.spatialDataType !== 'geo') {
|
|
362
|
+
spatialFiltersResolution = getSpatialFiltersResolution({
|
|
363
|
+
source,
|
|
364
|
+
viewState,
|
|
365
|
+
});
|
|
366
|
+
}
|
|
367
|
+
|
|
250
368
|
// Make sure this is sync with the same constant in cloud-native/maps-api
|
|
251
369
|
const HARD_LIMIT = 500;
|
|
252
370
|
|
|
@@ -254,7 +372,12 @@ export abstract class WidgetBaseSource<Props extends WidgetBaseSourceProps> {
|
|
|
254
372
|
|
|
255
373
|
return executeModel({
|
|
256
374
|
model: 'scatterplot',
|
|
257
|
-
source: {
|
|
375
|
+
source: {
|
|
376
|
+
...source,
|
|
377
|
+
spatialFiltersResolution,
|
|
378
|
+
spatialFiltersMode,
|
|
379
|
+
spatialFilter,
|
|
380
|
+
},
|
|
258
381
|
params: {
|
|
259
382
|
xAxisColumn,
|
|
260
383
|
xAxisJoinOperation,
|
|
@@ -277,8 +400,24 @@ export abstract class WidgetBaseSource<Props extends WidgetBaseSourceProps> {
|
|
|
277
400
|
* sorting. Suitable for displaying tables and lists.
|
|
278
401
|
*/
|
|
279
402
|
async getTable(options: TableRequestOptions): Promise<TableResponse> {
|
|
280
|
-
const {
|
|
403
|
+
const {
|
|
404
|
+
filterOwner,
|
|
405
|
+
spatialFilter,
|
|
406
|
+
spatialFiltersMode,
|
|
407
|
+
abortController,
|
|
408
|
+
viewState,
|
|
409
|
+
...params
|
|
410
|
+
} = options;
|
|
281
411
|
const {columns, sortBy, sortDirection, offset = 0, limit = 10} = params;
|
|
412
|
+
const source = this.getModelSource(filterOwner);
|
|
413
|
+
|
|
414
|
+
let spatialFiltersResolution: number | undefined;
|
|
415
|
+
if (spatialFilter && source.spatialDataType !== 'geo') {
|
|
416
|
+
spatialFiltersResolution = getSpatialFiltersResolution({
|
|
417
|
+
source,
|
|
418
|
+
viewState,
|
|
419
|
+
});
|
|
420
|
+
}
|
|
282
421
|
|
|
283
422
|
type TableModelResponse = {
|
|
284
423
|
rows: Record<string, number | string>[];
|
|
@@ -287,7 +426,12 @@ export abstract class WidgetBaseSource<Props extends WidgetBaseSourceProps> {
|
|
|
287
426
|
|
|
288
427
|
return executeModel({
|
|
289
428
|
model: 'table',
|
|
290
|
-
source: {
|
|
429
|
+
source: {
|
|
430
|
+
...source,
|
|
431
|
+
spatialFiltersResolution,
|
|
432
|
+
spatialFiltersMode,
|
|
433
|
+
spatialFilter,
|
|
434
|
+
},
|
|
291
435
|
params: {
|
|
292
436
|
column: columns,
|
|
293
437
|
sortBy,
|
|
@@ -314,7 +458,14 @@ export abstract class WidgetBaseSource<Props extends WidgetBaseSourceProps> {
|
|
|
314
458
|
async getTimeSeries(
|
|
315
459
|
options: TimeSeriesRequestOptions
|
|
316
460
|
): Promise<TimeSeriesResponse> {
|
|
317
|
-
const {
|
|
461
|
+
const {
|
|
462
|
+
filterOwner,
|
|
463
|
+
abortController,
|
|
464
|
+
spatialFilter,
|
|
465
|
+
spatialFiltersMode,
|
|
466
|
+
viewState,
|
|
467
|
+
...params
|
|
468
|
+
} = options;
|
|
318
469
|
const {
|
|
319
470
|
column,
|
|
320
471
|
operationColumn,
|
|
@@ -327,6 +478,16 @@ export abstract class WidgetBaseSource<Props extends WidgetBaseSourceProps> {
|
|
|
327
478
|
splitByCategoryValues,
|
|
328
479
|
} = params;
|
|
329
480
|
|
|
481
|
+
const source = this.getModelSource(filterOwner);
|
|
482
|
+
|
|
483
|
+
let spatialFiltersResolution: number | undefined;
|
|
484
|
+
if (spatialFilter && source.spatialDataType !== 'geo') {
|
|
485
|
+
spatialFiltersResolution = getSpatialFiltersResolution({
|
|
486
|
+
source,
|
|
487
|
+
viewState,
|
|
488
|
+
});
|
|
489
|
+
}
|
|
490
|
+
|
|
330
491
|
type TimeSeriesModelResponse = {
|
|
331
492
|
rows: {name: string; value: number}[];
|
|
332
493
|
metadata: {categories: string[]};
|
|
@@ -334,7 +495,12 @@ export abstract class WidgetBaseSource<Props extends WidgetBaseSourceProps> {
|
|
|
334
495
|
|
|
335
496
|
return executeModel({
|
|
336
497
|
model: 'timeseries',
|
|
337
|
-
source: {
|
|
498
|
+
source: {
|
|
499
|
+
...source,
|
|
500
|
+
spatialFiltersResolution,
|
|
501
|
+
spatialFiltersMode,
|
|
502
|
+
spatialFilter,
|
|
503
|
+
},
|
|
338
504
|
params: {
|
|
339
505
|
column,
|
|
340
506
|
stepSize,
|