@malloydata/db-snowflake 0.0.375 → 0.0.377
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/index.js +29 -2
- package/dist/index.js.map +1 -1
- package/dist/snowflake_connection.d.ts +48 -13
- package/dist/snowflake_connection.js +144 -228
- package/dist/snowflake_connection.js.map +1 -1
- package/dist/snowflake_connection.spec.js +179 -14
- package/dist/snowflake_connection.spec.js.map +1 -1
- package/dist/snowflake_sample_strategy.spec.js +97 -0
- package/dist/snowflake_sample_strategy.spec.js.map +1 -0
- package/dist/snowflake_table_name.d.ts +19 -0
- package/dist/snowflake_table_name.js +80 -0
- package/dist/snowflake_table_name.js.map +1 -0
- package/dist/snowflake_variant_schema.d.ts +43 -0
- package/dist/snowflake_variant_schema.js +203 -0
- package/dist/snowflake_variant_schema.js.map +1 -0
- package/dist/snowflake_variant_schema.spec.js +150 -0
- package/dist/snowflake_variant_schema.spec.js.map +1 -0
- package/package.json +2 -2
- package/src/index.ts +34 -1
- package/src/snowflake_connection.spec.ts +219 -15
- package/src/snowflake_connection.ts +218 -262
- package/src/snowflake_sample_strategy.spec.ts +130 -0
- package/src/snowflake_table_name.ts +94 -0
- package/src/snowflake_variant_schema.spec.ts +188 -0
- package/src/snowflake_variant_schema.ts +301 -0
- package/dist/snowflake_executor.spec.js +0 -89
- package/dist/snowflake_executor.spec.js.map +0 -1
- package/dist/snowflake_setup.spec.js +0 -76
- package/dist/snowflake_setup.spec.js.map +0 -1
- package/src/snowflake_executor.spec.ts +0 -103
- package/src/snowflake_setup.spec.ts +0 -56
- /package/dist/{snowflake_executor.spec.d.ts → snowflake_sample_strategy.spec.d.ts} +0 -0
- /package/dist/{snowflake_setup.spec.d.ts → snowflake_variant_schema.spec.d.ts} +0 -0
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
import type { Dialect, FieldDef } from '@malloydata/malloy';
|
|
2
|
+
import { TinyParser } from '@malloydata/malloy/internal';
|
|
3
|
+
export type NestedColumnKind = 'variant' | 'array' | 'object';
|
|
4
|
+
export interface NestedColumn {
|
|
5
|
+
kind: NestedColumnKind;
|
|
6
|
+
name: string;
|
|
7
|
+
}
|
|
8
|
+
export type Segment = {
|
|
9
|
+
kind: 'name';
|
|
10
|
+
name: string;
|
|
11
|
+
} | {
|
|
12
|
+
kind: 'array';
|
|
13
|
+
};
|
|
14
|
+
export type Shape = {
|
|
15
|
+
kind: 'object';
|
|
16
|
+
} | {
|
|
17
|
+
kind: 'array';
|
|
18
|
+
} | {
|
|
19
|
+
kind: 'leaf';
|
|
20
|
+
type: string;
|
|
21
|
+
} | {
|
|
22
|
+
kind: 'variant';
|
|
23
|
+
};
|
|
24
|
+
export type PrefixKey = string;
|
|
25
|
+
export interface Children {
|
|
26
|
+
elem?: PrefixKey;
|
|
27
|
+
named: Map<string, PrefixKey>;
|
|
28
|
+
}
|
|
29
|
+
export interface VariantSchemaState {
|
|
30
|
+
children: Map<PrefixKey, Children>;
|
|
31
|
+
seededTopLevels: Set<PrefixKey>;
|
|
32
|
+
shapes: Map<PrefixKey, Shape>;
|
|
33
|
+
}
|
|
34
|
+
export declare class PathParser extends TinyParser {
|
|
35
|
+
constructor(pathName: string);
|
|
36
|
+
getName(): string;
|
|
37
|
+
segments(): Segment[];
|
|
38
|
+
}
|
|
39
|
+
export declare function createVariantSchemaState(): VariantSchemaState;
|
|
40
|
+
export declare function mergeShape(existing: Shape | undefined, incoming: Shape): Shape;
|
|
41
|
+
export declare function seedTopLevelShape(state: VariantSchemaState, nestedColumn: NestedColumn): void;
|
|
42
|
+
export declare function accumulateVariantPath(state: VariantSchemaState, segments: Segment[], fieldType: string): void;
|
|
43
|
+
export declare function buildTopLevelField(nestedColumn: NestedColumn, state: VariantSchemaState, dialect: Dialect): FieldDef;
|
|
@@ -0,0 +1,203 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/*
|
|
3
|
+
* Copyright Contributors to the Malloy project
|
|
4
|
+
* SPDX-License-Identifier: MIT
|
|
5
|
+
*/
|
|
6
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
7
|
+
exports.PathParser = void 0;
|
|
8
|
+
exports.createVariantSchemaState = createVariantSchemaState;
|
|
9
|
+
exports.mergeShape = mergeShape;
|
|
10
|
+
exports.seedTopLevelShape = seedTopLevelShape;
|
|
11
|
+
exports.accumulateVariantPath = accumulateVariantPath;
|
|
12
|
+
exports.buildTopLevelField = buildTopLevelField;
|
|
13
|
+
const internal_1 = require("@malloydata/malloy/internal");
|
|
14
|
+
class PathParser extends internal_1.TinyParser {
|
|
15
|
+
constructor(pathName) {
|
|
16
|
+
super(pathName, {
|
|
17
|
+
quoted: /^'(\\'|[^'])*'/,
|
|
18
|
+
array_of: /^\[\*]/,
|
|
19
|
+
char: /^[[.\]]/,
|
|
20
|
+
number: /^\d+/,
|
|
21
|
+
word: /^\w+/,
|
|
22
|
+
});
|
|
23
|
+
}
|
|
24
|
+
getName() {
|
|
25
|
+
const word = this.match('word');
|
|
26
|
+
if (word)
|
|
27
|
+
return word.text;
|
|
28
|
+
if (this.match('[')) {
|
|
29
|
+
const quotedName = this.expect('quoted');
|
|
30
|
+
this.expect(']');
|
|
31
|
+
return quotedName.text;
|
|
32
|
+
}
|
|
33
|
+
throw this.parseError('Expected column name');
|
|
34
|
+
}
|
|
35
|
+
segments() {
|
|
36
|
+
const segments = [{ kind: 'name', name: this.getName() }];
|
|
37
|
+
while (!this.eof()) {
|
|
38
|
+
if (this.match('.')) {
|
|
39
|
+
segments.push({ kind: 'name', name: this.expect('word').text });
|
|
40
|
+
}
|
|
41
|
+
else if (this.match('array_of')) {
|
|
42
|
+
segments.push({ kind: 'array' });
|
|
43
|
+
}
|
|
44
|
+
else if (this.match('[')) {
|
|
45
|
+
const quoted = this.expect('quoted');
|
|
46
|
+
this.expect(']');
|
|
47
|
+
segments.push({ kind: 'name', name: quoted.text });
|
|
48
|
+
}
|
|
49
|
+
else {
|
|
50
|
+
throw this.parseError(`Unexpected ${this.peek().type}`);
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
return segments;
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
exports.PathParser = PathParser;
|
|
57
|
+
function createVariantSchemaState() {
|
|
58
|
+
return {
|
|
59
|
+
children: new Map(),
|
|
60
|
+
seededTopLevels: new Set(),
|
|
61
|
+
shapes: new Map(),
|
|
62
|
+
};
|
|
63
|
+
}
|
|
64
|
+
// The single consistency-policy point: any shape conflict across samples
|
|
65
|
+
// collapses to `variant`, and `variant` is absorbing (monotonic).
|
|
66
|
+
function mergeShape(existing, incoming) {
|
|
67
|
+
if (existing === undefined) {
|
|
68
|
+
return incoming;
|
|
69
|
+
}
|
|
70
|
+
if (existing.kind === 'variant' || incoming.kind === 'variant') {
|
|
71
|
+
return { kind: 'variant' };
|
|
72
|
+
}
|
|
73
|
+
if (existing.kind !== incoming.kind) {
|
|
74
|
+
return { kind: 'variant' };
|
|
75
|
+
}
|
|
76
|
+
if (existing.kind === 'leaf' &&
|
|
77
|
+
incoming.kind === 'leaf' &&
|
|
78
|
+
existing.type !== incoming.type) {
|
|
79
|
+
return { kind: 'variant' };
|
|
80
|
+
}
|
|
81
|
+
return existing;
|
|
82
|
+
}
|
|
83
|
+
function seedTopLevelShape(state, nestedColumn) {
|
|
84
|
+
const key = prefixKey([{ kind: 'name', name: nestedColumn.name }]);
|
|
85
|
+
if (nestedColumn.kind === 'array' || nestedColumn.kind === 'object') {
|
|
86
|
+
state.seededTopLevels.add(key);
|
|
87
|
+
state.shapes.set(key, { kind: nestedColumn.kind });
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
function accumulateVariantPath(state, segments, fieldType) {
|
|
91
|
+
if (segments.length === 0) {
|
|
92
|
+
return;
|
|
93
|
+
}
|
|
94
|
+
const topLevelKey = prefixKey(segments.slice(0, 1));
|
|
95
|
+
const topLevelShape = state.shapes.get(topLevelKey);
|
|
96
|
+
const topLevelIncoming = segments.length === 1
|
|
97
|
+
? observedTypeToShape(fieldType)
|
|
98
|
+
: nextSegmentToShape(segments[1]);
|
|
99
|
+
if (state.seededTopLevels.has(topLevelKey) &&
|
|
100
|
+
topLevelShape &&
|
|
101
|
+
(topLevelShape.kind === 'array' || topLevelShape.kind === 'object') &&
|
|
102
|
+
topLevelShape.kind !== topLevelIncoming.kind) {
|
|
103
|
+
// Rule 1: top-level ARRAY/OBJECT from DESCRIBE are authoritative.
|
|
104
|
+
// Ignore impossible sample rows rather than letting them override the seed.
|
|
105
|
+
return;
|
|
106
|
+
}
|
|
107
|
+
let parentKey;
|
|
108
|
+
for (let i = 0; i < segments.length; i++) {
|
|
109
|
+
const prefixSegments = segments.slice(0, i + 1);
|
|
110
|
+
const key = prefixKey(prefixSegments);
|
|
111
|
+
const impliedShape = i === segments.length - 1
|
|
112
|
+
? observedTypeToShape(fieldType)
|
|
113
|
+
: nextSegmentToShape(segments[i + 1]);
|
|
114
|
+
state.shapes.set(key, mergeShape(state.shapes.get(key), impliedShape));
|
|
115
|
+
if (parentKey !== undefined) {
|
|
116
|
+
recordChild(state, parentKey, segments[i], key);
|
|
117
|
+
}
|
|
118
|
+
parentKey = key;
|
|
119
|
+
}
|
|
120
|
+
}
|
|
121
|
+
function buildTopLevelField(nestedColumn, state, dialect) {
|
|
122
|
+
// Snowflake nested-schema inference follows these rules:
|
|
123
|
+
// - top-level ARRAY/OBJECT from DESCRIBE are authoritative
|
|
124
|
+
// - descendant paths imply ancestor shape
|
|
125
|
+
// - conflicting shapes degrade only that prefix to variant
|
|
126
|
+
// - every top-level nested column still produces a field
|
|
127
|
+
//
|
|
128
|
+
// Snowflake-specific semantic note: reconstructing object shape from
|
|
129
|
+
// descendant paths is safe because path access on an incompatible VARIANT
|
|
130
|
+
// value yields NULL rather than raising an error.
|
|
131
|
+
const key = prefixKey([{ kind: 'name', name: nestedColumn.name }]);
|
|
132
|
+
const shape = state.shapes.get(key);
|
|
133
|
+
if (shape === undefined) {
|
|
134
|
+
// Top-level ARRAY with no usable descendants still stays queryable as
|
|
135
|
+
// array<variant>; top-level OBJECT/VARIANT degrades to opaque variant.
|
|
136
|
+
return (0, internal_1.mkFieldDef)(nestedColumn.kind === 'array'
|
|
137
|
+
? (0, internal_1.mkArrayTypeDef)(opaqueVariantType())
|
|
138
|
+
: opaqueVariantType(), nestedColumn.name);
|
|
139
|
+
}
|
|
140
|
+
return (0, internal_1.mkFieldDef)(buildTypeForKey(key, state, dialect), nestedColumn.name);
|
|
141
|
+
}
|
|
142
|
+
function buildTypeForKey(key, state, dialect) {
|
|
143
|
+
var _a, _b;
|
|
144
|
+
const shape = state.shapes.get(key);
|
|
145
|
+
if (shape === undefined || shape.kind === 'variant') {
|
|
146
|
+
return opaqueVariantType();
|
|
147
|
+
}
|
|
148
|
+
if (shape.kind === 'leaf') {
|
|
149
|
+
return dialect.sqlTypeToMalloyType(shape.type);
|
|
150
|
+
}
|
|
151
|
+
if (shape.kind === 'object') {
|
|
152
|
+
const namedChildren = (_a = state.children.get(key)) === null || _a === void 0 ? void 0 : _a.named;
|
|
153
|
+
if (!namedChildren || namedChildren.size === 0) {
|
|
154
|
+
return opaqueVariantType();
|
|
155
|
+
}
|
|
156
|
+
return {
|
|
157
|
+
type: 'record',
|
|
158
|
+
fields: [...namedChildren.entries()].map(([childName, childKey]) => (0, internal_1.mkFieldDef)(buildTypeForKey(childKey, state, dialect), childName)),
|
|
159
|
+
};
|
|
160
|
+
}
|
|
161
|
+
const elemKey = (_b = state.children.get(key)) === null || _b === void 0 ? void 0 : _b.elem;
|
|
162
|
+
const elementType = elemKey
|
|
163
|
+
? buildTypeForKey(elemKey, state, dialect)
|
|
164
|
+
: opaqueVariantType();
|
|
165
|
+
return (0, internal_1.mkArrayTypeDef)(elementType);
|
|
166
|
+
}
|
|
167
|
+
function nextSegmentToShape(segment) {
|
|
168
|
+
return segment.kind === 'array' ? { kind: 'array' } : { kind: 'object' };
|
|
169
|
+
}
|
|
170
|
+
function observedTypeToShape(fieldType) {
|
|
171
|
+
// Defensive: production callers only pass Snowflake TYPEOF() results, which
|
|
172
|
+
// are expected to be array/object or scalar leaf types, not "variant".
|
|
173
|
+
if (fieldType === 'array' ||
|
|
174
|
+
fieldType === 'object' ||
|
|
175
|
+
fieldType === 'variant') {
|
|
176
|
+
return { kind: fieldType };
|
|
177
|
+
}
|
|
178
|
+
return { kind: 'leaf', type: fieldType };
|
|
179
|
+
}
|
|
180
|
+
function recordChild(state, parentKey, segment, childKey) {
|
|
181
|
+
let children = state.children.get(parentKey);
|
|
182
|
+
if (children === undefined) {
|
|
183
|
+
children = { named: new Map() };
|
|
184
|
+
state.children.set(parentKey, children);
|
|
185
|
+
}
|
|
186
|
+
if (segment.kind === 'array') {
|
|
187
|
+
children.elem = childKey;
|
|
188
|
+
}
|
|
189
|
+
else {
|
|
190
|
+
children.named.set(segment.name, childKey);
|
|
191
|
+
}
|
|
192
|
+
}
|
|
193
|
+
function opaqueVariantType() {
|
|
194
|
+
return { type: 'sql native', rawType: 'variant' };
|
|
195
|
+
}
|
|
196
|
+
function prefixKey(segments) {
|
|
197
|
+
const [first, ...rest] = segments;
|
|
198
|
+
if ((first === null || first === void 0 ? void 0 : first.kind) !== 'name') {
|
|
199
|
+
throw new Error('Snowflake schema path must start with a named segment');
|
|
200
|
+
}
|
|
201
|
+
return (0, internal_1.pathToKey)(first.name, rest.map(segment => (segment.kind === 'array' ? '[*]' : segment.name)));
|
|
202
|
+
}
|
|
203
|
+
//# sourceMappingURL=snowflake_variant_schema.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"snowflake_variant_schema.js","sourceRoot":"","sources":["../src/snowflake_variant_schema.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/*
|
|
3
|
+
* Copyright Contributors to the Malloy project
|
|
4
|
+
* SPDX-License-Identifier: MIT
|
|
5
|
+
*/
|
|
6
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
7
|
+
const malloy_1 = require("@malloydata/malloy");
|
|
8
|
+
const snowflake_variant_schema_1 = require("./snowflake_variant_schema");
|
|
9
|
+
describe('snowflake variant schema helper', () => {
|
|
10
|
+
const dialect = new malloy_1.SnowflakeDialect();
|
|
11
|
+
function inferField(nestedColumn, rows) {
|
|
12
|
+
const state = (0, snowflake_variant_schema_1.createVariantSchemaState)();
|
|
13
|
+
(0, snowflake_variant_schema_1.seedTopLevelShape)(state, nestedColumn);
|
|
14
|
+
for (const row of rows) {
|
|
15
|
+
(0, snowflake_variant_schema_1.accumulateVariantPath)(state, new snowflake_variant_schema_1.PathParser(row.path).segments(), row.type);
|
|
16
|
+
}
|
|
17
|
+
return (0, snowflake_variant_schema_1.buildTopLevelField)(nestedColumn, state, dialect);
|
|
18
|
+
}
|
|
19
|
+
test('reconstructs object shape from descendant-only evidence', () => {
|
|
20
|
+
expect(inferField({ kind: 'variant', name: 'BASE_TOUCHPOINT' }, [
|
|
21
|
+
{ path: 'BASE_TOUCHPOINT.NETWORK', type: 'varchar' },
|
|
22
|
+
{ path: 'BASE_TOUCHPOINT.PLATFORM', type: 'varchar' },
|
|
23
|
+
])).toEqual({
|
|
24
|
+
type: 'record',
|
|
25
|
+
name: 'BASE_TOUCHPOINT',
|
|
26
|
+
join: 'one',
|
|
27
|
+
fields: [
|
|
28
|
+
{ name: 'NETWORK', type: 'string' },
|
|
29
|
+
{ name: 'PLATFORM', type: 'string' },
|
|
30
|
+
],
|
|
31
|
+
});
|
|
32
|
+
});
|
|
33
|
+
test('degrades object-array conflict at a shared prefix', () => {
|
|
34
|
+
expect(inferField({ kind: 'variant', name: 'X' }, [
|
|
35
|
+
{ path: 'X.Y', type: 'varchar' },
|
|
36
|
+
{ path: 'X[*].Z', type: 'decimal' },
|
|
37
|
+
])).toEqual({
|
|
38
|
+
type: 'sql native',
|
|
39
|
+
rawType: 'variant',
|
|
40
|
+
name: 'X',
|
|
41
|
+
});
|
|
42
|
+
});
|
|
43
|
+
test('builds array of records from stable descendants', () => {
|
|
44
|
+
expect(inferField({ kind: 'variant', name: 'ITEMS' }, [
|
|
45
|
+
{ path: 'ITEMS[*].FOO', type: 'varchar' },
|
|
46
|
+
{ path: 'ITEMS[*].BAR', type: 'boolean' },
|
|
47
|
+
])).toEqual({
|
|
48
|
+
type: 'array',
|
|
49
|
+
name: 'ITEMS',
|
|
50
|
+
join: 'many',
|
|
51
|
+
elementTypeDef: { type: 'record_element' },
|
|
52
|
+
fields: [
|
|
53
|
+
{ name: 'FOO', type: 'string' },
|
|
54
|
+
{ name: 'BAR', type: 'boolean' },
|
|
55
|
+
],
|
|
56
|
+
});
|
|
57
|
+
});
|
|
58
|
+
test('top-level array with no descendants becomes array of variant', () => {
|
|
59
|
+
expect(inferField({ kind: 'array', name: 'DIMENSION_SET_IDS' }, [])).toEqual({
|
|
60
|
+
type: 'array',
|
|
61
|
+
name: 'DIMENSION_SET_IDS',
|
|
62
|
+
join: 'many',
|
|
63
|
+
elementTypeDef: { type: 'sql native', rawType: 'variant' },
|
|
64
|
+
fields: [
|
|
65
|
+
{ name: 'value', type: 'sql native', rawType: 'variant' },
|
|
66
|
+
{
|
|
67
|
+
name: 'each',
|
|
68
|
+
type: 'sql native',
|
|
69
|
+
rawType: 'variant',
|
|
70
|
+
e: { node: 'field', path: ['value'] },
|
|
71
|
+
},
|
|
72
|
+
],
|
|
73
|
+
});
|
|
74
|
+
});
|
|
75
|
+
test('top-level DESCRIBE seed stays authoritative over conflicting sample', () => {
|
|
76
|
+
expect(inferField({ kind: 'array', name: 'DIMENSION_SET_IDS' }, [
|
|
77
|
+
{ path: 'DIMENSION_SET_IDS.foo', type: 'varchar' },
|
|
78
|
+
])).toEqual({
|
|
79
|
+
type: 'array',
|
|
80
|
+
name: 'DIMENSION_SET_IDS',
|
|
81
|
+
join: 'many',
|
|
82
|
+
elementTypeDef: { type: 'sql native', rawType: 'variant' },
|
|
83
|
+
fields: [
|
|
84
|
+
{ name: 'value', type: 'sql native', rawType: 'variant' },
|
|
85
|
+
{
|
|
86
|
+
name: 'each',
|
|
87
|
+
type: 'sql native',
|
|
88
|
+
rawType: 'variant',
|
|
89
|
+
e: { node: 'field', path: ['value'] },
|
|
90
|
+
},
|
|
91
|
+
],
|
|
92
|
+
});
|
|
93
|
+
});
|
|
94
|
+
test('top-level object with no descendants becomes opaque variant', () => {
|
|
95
|
+
expect(inferField({ kind: 'object', name: 'PAYLOAD' }, [])).toEqual({
|
|
96
|
+
type: 'sql native',
|
|
97
|
+
rawType: 'variant',
|
|
98
|
+
name: 'PAYLOAD',
|
|
99
|
+
});
|
|
100
|
+
});
|
|
101
|
+
test('quoted path names with punctuation are preserved', () => {
|
|
102
|
+
expect(inferField({ kind: 'variant', name: 'DATA' }, [
|
|
103
|
+
{ path: "DATA['a.b'][*]['c[d]']", type: 'varchar' },
|
|
104
|
+
])).toEqual({
|
|
105
|
+
type: 'record',
|
|
106
|
+
name: 'DATA',
|
|
107
|
+
join: 'one',
|
|
108
|
+
fields: [
|
|
109
|
+
{
|
|
110
|
+
type: 'array',
|
|
111
|
+
name: 'a.b',
|
|
112
|
+
join: 'many',
|
|
113
|
+
elementTypeDef: { type: 'record_element' },
|
|
114
|
+
fields: [{ name: 'c[d]', type: 'string' }],
|
|
115
|
+
},
|
|
116
|
+
],
|
|
117
|
+
});
|
|
118
|
+
});
|
|
119
|
+
test('leaf-type conflicts degrade to variant', () => {
|
|
120
|
+
const first = { kind: 'leaf', type: 'varchar' };
|
|
121
|
+
const second = { kind: 'leaf', type: 'decimal' };
|
|
122
|
+
expect((0, snowflake_variant_schema_1.mergeShape)(first, second)).toEqual({ kind: 'variant' });
|
|
123
|
+
});
|
|
124
|
+
test('scalar-vs-object at same path degrades that field only', () => {
|
|
125
|
+
// The sample emits both the scalar observation and the object
|
|
126
|
+
// observation (same path, two rows from the distinct (path, type)
|
|
127
|
+
// query). mergeShape collapses DATA.foo to variant; the parent
|
|
128
|
+
// DATA stays a record and siblings keep their types.
|
|
129
|
+
expect(inferField({ kind: 'variant', name: 'DATA' }, [
|
|
130
|
+
{ path: 'DATA.foo', type: 'object' },
|
|
131
|
+
{ path: 'DATA.foo', type: 'varchar' },
|
|
132
|
+
{ path: 'DATA.foo.bar', type: 'decimal' },
|
|
133
|
+
{ path: 'DATA.sib', type: 'varchar' },
|
|
134
|
+
])).toEqual({
|
|
135
|
+
type: 'record',
|
|
136
|
+
name: 'DATA',
|
|
137
|
+
join: 'one',
|
|
138
|
+
fields: [
|
|
139
|
+
{ type: 'sql native', rawType: 'variant', name: 'foo' },
|
|
140
|
+
{ type: 'string', name: 'sib' },
|
|
141
|
+
],
|
|
142
|
+
});
|
|
143
|
+
});
|
|
144
|
+
test('variant shape is monotonic', () => {
|
|
145
|
+
expect((0, snowflake_variant_schema_1.mergeShape)({ kind: 'variant' }, { kind: 'object' })).toEqual({
|
|
146
|
+
kind: 'variant',
|
|
147
|
+
});
|
|
148
|
+
});
|
|
149
|
+
});
|
|
150
|
+
//# sourceMappingURL=snowflake_variant_schema.spec.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"snowflake_variant_schema.spec.js","sourceRoot":"","sources":["../src/snowflake_variant_schema.spec.ts"],"names":[],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@malloydata/db-snowflake",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.377",
|
|
4
4
|
"license": "MIT",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"types": "dist/index.d.ts",
|
|
@@ -22,7 +22,7 @@
|
|
|
22
22
|
"prepublishOnly": "npm run build"
|
|
23
23
|
},
|
|
24
24
|
"dependencies": {
|
|
25
|
-
"@malloydata/malloy": "0.0.
|
|
25
|
+
"@malloydata/malloy": "0.0.377",
|
|
26
26
|
"generic-pool": "^3.9.0",
|
|
27
27
|
"snowflake-sdk": "2.3.1",
|
|
28
28
|
"toml": "^3.0.0"
|
package/src/index.ts
CHANGED
|
@@ -37,6 +37,8 @@ registerConnectionType('snowflake', {
|
|
|
37
37
|
setupSQL,
|
|
38
38
|
timeoutMs,
|
|
39
39
|
schemaSampleTimeoutMs,
|
|
40
|
+
schemaSampleRowLimit,
|
|
41
|
+
schemaSampleFullScanMaxBytes,
|
|
40
42
|
...props
|
|
41
43
|
} = config;
|
|
42
44
|
// ConnectionConfig values are trusted to match ConnectionOptions fields
|
|
@@ -60,6 +62,18 @@ registerConnectionType('snowflake', {
|
|
|
60
62
|
: typeof schemaSampleTimeoutMs === 'string'
|
|
61
63
|
? parseInt(schemaSampleTimeoutMs, 10)
|
|
62
64
|
: undefined,
|
|
65
|
+
schemaSampleRowLimit:
|
|
66
|
+
typeof schemaSampleRowLimit === 'number'
|
|
67
|
+
? schemaSampleRowLimit
|
|
68
|
+
: typeof schemaSampleRowLimit === 'string'
|
|
69
|
+
? parseInt(schemaSampleRowLimit, 10)
|
|
70
|
+
: undefined,
|
|
71
|
+
schemaSampleFullScanMaxBytes:
|
|
72
|
+
typeof schemaSampleFullScanMaxBytes === 'number'
|
|
73
|
+
? schemaSampleFullScanMaxBytes
|
|
74
|
+
: typeof schemaSampleFullScanMaxBytes === 'string'
|
|
75
|
+
? parseInt(schemaSampleFullScanMaxBytes, 10)
|
|
76
|
+
: undefined,
|
|
63
77
|
});
|
|
64
78
|
},
|
|
65
79
|
properties: [
|
|
@@ -101,14 +115,33 @@ registerConnectionType('snowflake', {
|
|
|
101
115
|
displayName: 'Timeout (ms)',
|
|
102
116
|
type: 'number',
|
|
103
117
|
optional: true,
|
|
118
|
+
default: 600000,
|
|
104
119
|
},
|
|
105
120
|
{
|
|
106
121
|
name: 'schemaSampleTimeoutMs',
|
|
107
122
|
displayName: 'Schema Sample Timeout (ms)',
|
|
108
123
|
type: 'number',
|
|
109
124
|
optional: true,
|
|
125
|
+
default: 15000,
|
|
126
|
+
description:
|
|
127
|
+
'Timeout for the query that samples variant columns to detect their schema.',
|
|
128
|
+
},
|
|
129
|
+
{
|
|
130
|
+
name: 'schemaSampleRowLimit',
|
|
131
|
+
displayName: 'Schema Sample Row Limit',
|
|
132
|
+
type: 'number',
|
|
133
|
+
optional: true,
|
|
134
|
+
default: 1000,
|
|
135
|
+
description:
|
|
136
|
+
'Row limit for the variant schema sample. Ignored for tables small enough to full-scan.',
|
|
137
|
+
},
|
|
138
|
+
{
|
|
139
|
+
name: 'schemaSampleFullScanMaxBytes',
|
|
140
|
+
displayName: 'Schema Full-Scan Max Bytes',
|
|
141
|
+
type: 'number',
|
|
142
|
+
optional: true,
|
|
110
143
|
description:
|
|
111
|
-
'
|
|
144
|
+
'Tables with BYTES at or below this value are full-scanned during variant schema inference instead of sampled. When unset, the connection uses an internal threshold; picking a value here is a policy choice tied to the size-probe behavior.',
|
|
112
145
|
},
|
|
113
146
|
{
|
|
114
147
|
name: 'setupSQL',
|