@checkdigit/eslint-plugin 7.18.0-PR.143-c73c → 7.18.0-PR.143-9235
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-mjs/athena/validate.mjs +31 -31
- package/package.json +1 -1
- package/src/athena/validate.ts +37 -35
|
@@ -40,6 +40,7 @@ function offsetToLoc(text, offset) {
|
|
|
40
40
|
return { line: lines.length, column: lines[lines.length - 1]?.length ?? 0 };
|
|
41
41
|
}
|
|
42
42
|
var log = debug("eslint-plugin:athena");
|
|
43
|
+
var ANONYMOUS_TABLE = "<anonymous>";
|
|
43
44
|
function resolvedCol(name, schema, ast) {
|
|
44
45
|
return ast !== void 0 ? { name, schema, ast } : { name, schema };
|
|
45
46
|
}
|
|
@@ -52,6 +53,9 @@ function getApiSchemas(serviceName, ctx) {
|
|
|
52
53
|
return schemas;
|
|
53
54
|
}
|
|
54
55
|
function lookupTables(nameOrAlias, ctx) {
|
|
56
|
+
if (ctx.tables.has(nameOrAlias)) {
|
|
57
|
+
return ctx.tables.get(nameOrAlias) ?? [];
|
|
58
|
+
}
|
|
55
59
|
const canonical = ctx.aliases.get(nameOrAlias) ?? nameOrAlias;
|
|
56
60
|
return ctx.tables.get(canonical) ?? [];
|
|
57
61
|
}
|
|
@@ -64,15 +68,16 @@ function fromClauseItems(select) {
|
|
|
64
68
|
}
|
|
65
69
|
return [];
|
|
66
70
|
}
|
|
67
|
-
function resolveServiceTable(select, item, ctx) {
|
|
71
|
+
function resolveServiceTable(select, item, ctx, storageKey) {
|
|
68
72
|
const { table: tableName } = item;
|
|
73
|
+
const key = storageKey ?? tableName;
|
|
69
74
|
try {
|
|
70
75
|
const apiSchemas = getApiSchemas(tableName, ctx);
|
|
71
76
|
if (apiSchemas.length === 0) {
|
|
72
77
|
throw new AthenaError(ATHENA_ERROR, `service not found: "${tableName}" (no swagger schema located)`, item);
|
|
73
78
|
}
|
|
74
79
|
const operations = matchApi(select, item, apiSchemas) ?? [];
|
|
75
|
-
ctx.tables.set(
|
|
80
|
+
ctx.tables.set(key, buildServiceTables(tableName, operations));
|
|
76
81
|
} catch (error) {
|
|
77
82
|
if (error instanceof AthenaError) {
|
|
78
83
|
throw error;
|
|
@@ -84,6 +89,9 @@ function restrictToFromClause(select, ctx) {
|
|
|
84
89
|
const fromNames = /* @__PURE__ */ new Set();
|
|
85
90
|
for (const item of fromClauseItems(select)) {
|
|
86
91
|
if (isBaseFrom(item) || isJoin(item)) {
|
|
92
|
+
if (item.as !== null) {
|
|
93
|
+
fromNames.add(item.as);
|
|
94
|
+
}
|
|
87
95
|
fromNames.add(item.table);
|
|
88
96
|
} else if (isTableExpr(item)) {
|
|
89
97
|
fromNames.add(typeof item.as === "string" ? item.as : "<subquery>");
|
|
@@ -95,37 +103,30 @@ function restrictToFromClause(select, ctx) {
|
|
|
95
103
|
}
|
|
96
104
|
}
|
|
97
105
|
}
|
|
106
|
+
function tableIsResolved(tableName, storageKey, ctx) {
|
|
107
|
+
return ctx.tables.has(storageKey) || ctx.tables.has(tableName);
|
|
108
|
+
}
|
|
109
|
+
function resolveTableOrJoinItem(select, item, ctx) {
|
|
110
|
+
const { table: tableName, as: alias } = item;
|
|
111
|
+
if (alias !== null) {
|
|
112
|
+
ctx.aliases.set(alias, tableName);
|
|
113
|
+
}
|
|
114
|
+
const storageKey = alias ?? tableName;
|
|
115
|
+
if (!tableIsResolved(tableName, storageKey, ctx)) {
|
|
116
|
+
resolveServiceTable(select, item, ctx, alias ?? void 0);
|
|
117
|
+
}
|
|
118
|
+
}
|
|
98
119
|
function resolveFromClause(select, ctx) {
|
|
99
120
|
for (const item of fromClauseItems(select)) {
|
|
100
121
|
if (isUnnestFrom(item)) {
|
|
101
122
|
continue;
|
|
102
123
|
}
|
|
103
124
|
if (isTableExpr(item)) {
|
|
104
|
-
const
|
|
105
|
-
checkSelect(item.expr.ast, ctx,
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
if (isJoin(item)) {
|
|
109
|
-
const { table: tableName2, as: alias2 } = item;
|
|
110
|
-
if (alias2 !== null) {
|
|
111
|
-
ctx.aliases.set(alias2, tableName2);
|
|
112
|
-
}
|
|
113
|
-
if (!ctx.tables.has(tableName2)) {
|
|
114
|
-
resolveServiceTable(select, item, ctx);
|
|
115
|
-
}
|
|
116
|
-
continue;
|
|
117
|
-
}
|
|
118
|
-
if (!isBaseFrom(item)) {
|
|
119
|
-
continue;
|
|
120
|
-
}
|
|
121
|
-
const { table: tableName, as: alias } = item;
|
|
122
|
-
if (alias !== null) {
|
|
123
|
-
ctx.aliases.set(alias, tableName);
|
|
124
|
-
}
|
|
125
|
-
if (ctx.tables.has(tableName)) {
|
|
126
|
-
continue;
|
|
125
|
+
const alias = typeof item.as === "string" ? item.as : "<subquery>";
|
|
126
|
+
checkSelect(item.expr.ast, ctx, alias);
|
|
127
|
+
} else if (isJoin(item) || isBaseFrom(item)) {
|
|
128
|
+
resolveTableOrJoinItem(select, item, ctx);
|
|
127
129
|
}
|
|
128
|
-
resolveServiceTable(select, item, ctx);
|
|
129
130
|
}
|
|
130
131
|
}
|
|
131
132
|
function extractUnnestMappings(select) {
|
|
@@ -158,7 +159,7 @@ function applyUnnestPre(mappings, ctx) {
|
|
|
158
159
|
}
|
|
159
160
|
const sourceColumns = ownerTable.columns.get(fromColumn) ?? [];
|
|
160
161
|
const sourceSchema = sourceColumns[0]?.schema;
|
|
161
|
-
const unnestTableName = `${ownerTable.name ??
|
|
162
|
+
const unnestTableName = `${ownerTable.name ?? ANONYMOUS_TABLE}:<unnested>`;
|
|
162
163
|
const apiOperation = ownerTable.apiOperation !== void 0 ? { apiOperation: ownerTable.apiOperation } : {};
|
|
163
164
|
if (sourceSchema?.type === "array") {
|
|
164
165
|
const [toColumn] = toColumns;
|
|
@@ -286,7 +287,7 @@ function lookupColumnOrThrow(colRef, ref, referencedTables) {
|
|
|
286
287
|
const resolvedColumns = referencedTables.flatMap((table) => table.columns.get(colRef) ?? []);
|
|
287
288
|
if (resolvedColumns.length === 0) {
|
|
288
289
|
const tableNames = [
|
|
289
|
-
...new Set(referencedTables.map((referenceTable) => referenceTable.name ??
|
|
290
|
+
...new Set(referencedTables.map((referenceTable) => referenceTable.name ?? ANONYMOUS_TABLE))
|
|
290
291
|
].join(", ");
|
|
291
292
|
const availableCols = [...new Set(referencedTables.flatMap((table) => [...table.columns.keys()]))].join(", ");
|
|
292
293
|
throw new AthenaError(
|
|
@@ -341,10 +342,9 @@ function resolveSingleColumnRef(columnAST, columnAlias, indexedName, ref, allTab
|
|
|
341
342
|
assert.ok(colRef !== void 0, "column_ref must have a string column name");
|
|
342
343
|
const referencedTables = tableRef !== void 0 ? lookupTables(tableRef, ctx) : allTables;
|
|
343
344
|
if (referencedTables.length === 0) {
|
|
344
|
-
const tableNames = [...ctx.tables.keys()].join(", ");
|
|
345
345
|
throw new AthenaError(
|
|
346
346
|
ATHENA_ERROR,
|
|
347
|
-
`unknown table or alias '${tableRef ?? colRef}'; known tables: ${
|
|
347
|
+
`unknown table or alias '${tableRef ?? colRef}'; known tables: ${[...ctx.tables.keys()].join(", ")}`,
|
|
348
348
|
ref
|
|
349
349
|
);
|
|
350
350
|
}
|
|
@@ -477,4 +477,4 @@ export {
|
|
|
477
477
|
checkAthenaAst,
|
|
478
478
|
offsetToLoc
|
|
479
479
|
};
|
|
480
|
-
//# sourceMappingURL=data:application/json;base64,ewogICJ2ZXJzaW9uIjogMywKICAic291cmNlcyI6IFsiLi4vLi4vc3JjL2F0aGVuYS92YWxpZGF0ZS50cyJdLAogICJtYXBwaW5ncyI6ICI7QUFVQSxTQUFTLFVBQVUsY0FBYztBQUVqQyxPQUFPLFdBQVc7QUFDbEIsU0FBUyxnQkFBZ0I7QUFJekIsU0FBUyxnQkFBZ0I7QUFDekIsU0FBUyxpQkFBaUI7QUFDMUIsU0FBUywwQkFBc0Y7QUFDL0YsU0FBUywwQkFBMEI7QUFDbkM7QUFBQSxFQUNFO0FBQUEsRUFDQTtBQUFBLEVBQ0E7QUFBQSxFQUNBO0FBQUEsRUFDQTtBQUFBLEVBQ0E7QUFBQSxFQUNBO0FBQUEsRUFDQTtBQUFBLEVBQ0E7QUFBQSxFQUNBO0FBQUEsRUFDQTtBQUFBLEVBQ0E7QUFBQSxPQUNLO0FBRUEsSUFBTSxnQkFBZ0I7QUFDdEIsSUFBTSxlQUFlO0FBRXJCLElBQU0sY0FBTixjQUEwQixNQUFNO0FBQUEsRUFDOUI7QUFBQSxFQUNBO0FBQUEsRUFDUCxZQUFZLE1BQWMsU0FBaUIsS0FBYztBQUN2RCxVQUFNLE9BQU87QUFDYixTQUFLLE9BQU87QUFDWixTQUFLLE9BQU87QUFDWixRQUFJLFFBQVEsUUFBVztBQUNyQixXQUFLLE1BQU07QUFBQSxJQUNiO0FBQUEsRUFDRjtBQUNGO0FBR08sU0FBUyxZQUFZLE1BQWMsUUFBa0Q7QUFDMUYsUUFBTSxTQUFTLEtBQUssTUFBTSxHQUFHLE1BQU07QUFDbkMsUUFBTSxRQUFRLE9BQU8sTUFBTSxJQUFJO0FBQy9CLFNBQU8sRUFBRSxNQUFNLE1BQU0sUUFBUSxRQUFRLE1BQU0sTUFBTSxTQUFTLENBQUMsR0FBRyxVQUFVLEVBQUU7QUFDNUU7QUFFQSxJQUFNLE1BQU0sTUFBTSxzQkFBc0I7QUFNeEMsU0FBUyxZQUFZLE1BQWMsUUFBc0IsS0FBOEI7QUFDckYsU0FBTyxRQUFRLFNBQVksRUFBRSxNQUFNLFFBQVEsSUFBSSxJQUFJLEVBQUUsTUFBTSxPQUFPO0FBQ3BFO0FBRUEsU0FBUyxjQUFjLGFBQXFCLEtBQW1CO0FBQzdELE1BQUksVUFB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QVM7QUFDdkQsb0NBQWdDLE9BQU8sT0FBTyxXQUFXLFNBQVM7QUFBQSxFQUNwRTtBQUNBLE1BQUksT0FBTyxXQUFXLE1BQU07QUFDMUIseUJBQXFCLE9BQU8sUUFBUSxXQUFXLFdBQVcsT0FBTztBQUNqRSxvQ0FBZ0MsT0FBTyxRQUFRLFdBQVcsU0FBUztBQUFBLEVBQ3JFO0FBQ0EsYUFBVyxhQUFhLE9BQU8sV0FBVyxDQUFDLEdBQUc7QUFDNUMseUJBQXFCLFVBQVUsTUFBTSxXQUFXLFdBQVcsT0FBTztBQUNsRSxvQ0FBZ0MsVUFBVSxNQUFNLFdBQVcsU0FBUztBQUFBLEVBQ3RFO0FBQ0EsTUFBSSxPQUFPLFNBQVMsWUFBWSxRQUFXO0FBQ3pDLGVBQVcsWUFBWSxPQUFPLFFBQVEsU0FBUztBQUM3QywyQkFBcUIsVUFBVSxXQUFXLFdBQVcsT0FBTztBQUM1RCxzQ0FBZ0MsVUFBVSxXQUFXLFNBQVM7QUFBQSxJQUNoRTtBQUFBLEVBQ0Y7QUFFQSxNQUFJLE9BQU8sVUFBVSxRQUFXO0FBQzlCLFVBQU0sY0FBYyxZQUFZLE9BQU8sT0FBTyxLQUFLLGFBQWE7QUFDaEUsVUFBTSxzQkFBc0IsUUFBUTtBQUNwQyxVQUFNLG1CQUFtQixZQUFZO0FBQ3JDLFFBQUksd0JBQXdCLGtCQUFrQjtBQUM1QyxZQUFNLElBQUk7QUFBQSxRQUNSO0FBQUEsUUFDQSxxREFBcUQsb0JBQW9CLFNBQVMsQ0FBQyxPQUFPLGlCQUFpQixTQUFTLENBQUM7QUFBQSxRQUNySCxPQUFPO0FBQUEsTUFDVDtBQUFBLElBQ0Y7QUFBQSxFQUNGO0FBRUEsTUFBSSxrQkFBa0IsUUFBVztBQUMvQixVQUFNLGdCQUErQixFQUFFLE1BQU0sZUFBZSxRQUFRO0FBQ3BFLFFBQUksT0FBTyxJQUFJLGVBQWUsQ0FBQyxhQUFhLENBQUM7QUFBQSxFQUMvQztBQUVBLFNBQU87QUFDVDtBQUVPLFNBQVMsZUFBZSxLQUFVLEtBQXlCO0FBQ2hFLFNBQU8sR0FBRyxJQUFJLFNBQVMsUUFBUTtBQUMvQixRQUFNLFNBQVM7QUFFZixNQUFJLE9BQU8sU0FBUyxNQUFNO0FBQ3hCLGVBQVcsWUFBWSxPQUFPLE1BQU07QUFDbEMsa0JBQVksU0FBUyxLQUFLLEtBQUssS0FBSyxTQUFTLEtBQUssS0FBSztBQUFBLElBQ3pEO0FBQ0EsV0FBTyxPQUFPO0FBQUEsRUFDaEI7QUFFQSxjQUFZLFFBQVEsR0FBRztBQUN6QjsiLAogICJuYW1lcyI6IFsiYWxpYXMiLCAidGFibGVOYW1lIl0KfQo=
|
|
480
|
+
//# sourceMappingURL=data:application/json;base64,ewogICJ2ZXJzaW9uIjogMywKICAic291cmNlcyI6IFsiLi4vLi4vc3JjL2F0aGVuYS92YWxpZGF0ZS50cyJdLAogICJtYXBwaW5ncyI6ICI7QUFVQSxTQUFTLFVBQVUsY0FBYztBQUVqQyxPQUFPLFdBQVc7QUFDbEIsU0FBUyxnQkFBZ0I7QUFJekIsU0FBUyxnQkFBZ0I7QUFDekIsU0FBUyxpQkFBaUI7QUFDMUIsU0FBUywwQkFBc0Y7QUFDL0YsU0FBUywwQkFBMEI7QUFDbkM7QUFBQSxFQUNFO0FBQUEsRUFDQTtBQUFBLEVBQ0E7QUFBQSxFQUNBO0FBQUEsRUFDQTtBQUFBLEVBQ0E7QUFBQSxFQUNBO0FBQUEsRUFDQTtBQUFBLEVBQ0E7QUFBQSxFQUNBO0FBQUEsRUFDQTtBQUFBLEVBQ0E7QUFBQSxPQUNLO0FBRUEsSUFBTSxnQkFBZ0I7QUFDdEIsSUFBTSxlQUFlO0FBRXJCLElBQU0sY0FBTixjQUEwQixNQUFNO0FBQUEsRUFDOUI7QUFBQSxFQUNBO0FBQUEsRUFDUCxZQUFZLE1BQWMsU0FBaUIsS0FBYztBQUN2RCxVQUFNLE9BQU87QUFDYixTQUFLLE9BQU87QUFDWixTQUFLLE9BQU87QUFDWixRQUFJLFFBQVEsUUFBVztBQUNyQixXQUFLLE1BQU07QUFBQSxJQUNiO0FBQUEsRUFDRjtBQUNGO0FBR08sU0FBUyxZQUFZLE1BQWMsUUFBa0Q7QUFDMUYsUUFBTSxTQUFTLEtBQUssTUFBTSxHQUFHLE1BQU07QUFDbkMsUUFBTSxRQUFRLE9BQU8sTUFBTSxJQUFJO0FBQy9CLFNBQU8sRUFBRSxNQUFNLE1BQU0sUUFBUSxRQUFRLE1BQU0sTUFBTSxTQUFTLENBQUMsR0FBRyxVQUFVLEVBQUU7QUFDNUU7QUFFQSxJQUFNLE1BQU0sTUFBTSxzQkFBc0I7QUFDeEMsSUFBTSxrQkFBa0I7QUFNeEIsU0FBUyxZQUFZLE1BQWMsUUFBc0IsS0FBOEI7QUFDckYsU0FBTyxRQUFRLFNBQVksRUFBRSxNQUFNLFFBQVEsSUFBSSxJQUFJLEVBQUUsTUFBTSxPQUFPO0FBQ3BFO0FBRUEsU0FBUyxjQUFjLGFBQXFCLEtB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
|
package/package.json
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"name":"@checkdigit/eslint-plugin","version":"7.18.0-PR.143-
|
|
1
|
+
{"name":"@checkdigit/eslint-plugin","version":"7.18.0-PR.143-9235","description":"Check Digit eslint plugins","keywords":["eslint","eslintplugin"],"homepage":"https://github.com/checkdigit/eslint-plugin#readme","bugs":{"url":"https://github.com/checkdigit/eslint-plugin/issues"},"repository":{"type":"git","url":"https://github.com/checkdigit/eslint-plugin"},"license":"MIT","author":"Check Digit, LLC","sideEffects":false,"type":"module","exports":{".":{"types":"./dist-types/index.d.ts","import":"./dist-mjs/index.mjs","default":"./dist-mjs/index.mjs"}},"files":["src","dist-types","dist-mjs","!src/**/test/**","!src/**/*.test.ts","!src/**/*.spec.ts","!dist-types/**/test/**","!dist-types/**/*.test.d.ts","!dist-types/**/*.spec.d.ts","!dist-mjs/**/test/**","!dist-mjs/**/*.test.mjs","!dist-mjs/**/*.spec.mjs","SECURITY.md"],"scripts":{"build:dist-mjs":"rimraf dist-mjs && npx builder --type=module --sourceMap --outDir=dist-mjs && node dist-mjs/index.mjs","build:dist-types":"rimraf dist-types && npx builder --type=types --outDir=dist-types","ci:compile":"tsc --noEmit","ci:coverage":"NODE_OPTIONS=\"--disable-warning ExperimentalWarning --experimental-vm-modules\" jest --coverage=true","ci:lint":"npm run lint","ci:style":"npm run prettier","ci:test":"NODE_OPTIONS=\"--disable-warning ExperimentalWarning --experimental-vm-modules\" jest --coverage=false","lint":"eslint --max-warnings 0 .","lint:fix":"eslint --max-warnings 0 --fix .","peggy":"for file in ./src/peggy/*.peggy; do peggy \"$file\" --format es --output \"${file%.peggy}-peggy.ts\"; done","peggy-watch":"for file in ./src/peggy/*.peggy; do peggy \"$file\" --format=es --watch --output=\"${file%.peggy}-peggy.ts\"; done","prepare":"","prepublishOnly":"npm run build:dist-types && npm run build:dist-mjs","prettier":"prettier --ignore-path .gitignore --list-different .","prettier:fix":"prettier --ignore-path .gitignore --write .","test":"npm run ci:compile && npm run ci:test && npm run ci:lint && npm run ci:style"},"prettier":"@checkdigit/prettier-config","jest":{"preset":"@checkdigit/jest-config"},"dependencies":{"@apidevtools/json-schema-ref-parser":"^15.3.5","@typescript-eslint/type-utils":"^8.60.1","@typescript-eslint/utils":"^8.60.1","ajv":"^8.20.0","debug":"^4.4.3","glob":"^13.0.6","http-status-codes":"^2.3.0","js-yaml":"^4.2.0","json-pointer":"^0.6.2","jsonpath-plus":"^10.4.0","ts-api-utils":"^2.5.0"},"devDependencies":{"@checkdigit/jest-config":"^6.0.2","@checkdigit/prettier-config":"^6.1.0","@checkdigit/typescript-config":"10.0.0","@eslint/js":"^9.37.0","@types/debug":"^4.1.13","@types/eslint":"^9.6.1","@types/eslint-config-prettier":"^6.11.3","@types/js-yaml":"^4.0.9","@types/json-pointer":"^1.0.34","@typescript-eslint/parser":"^8.60.1","@typescript-eslint/rule-tester":"^8.60.1","eslint":"^9.37.0","eslint-config-prettier":"^10.1.8","eslint-import-resolver-typescript":"^4.4.5","eslint-plugin-eslint-plugin":"^6.4.0","eslint-plugin-import":"^2.32.0","eslint-plugin-no-only-tests":"^3.4.0","eslint-plugin-no-secrets":"^2.3.3","eslint-plugin-node":"^11.1.0","eslint-plugin-sonarjs":"^1.0.4","openapi-types":"^12.1.3","peggy":"^4.2.0","rimraf":"^6.1.3","typescript-eslint":"^8.60.1"},"peerDependencies":{"eslint":">=9 <10"},"engines":{"node":">=24.14.1"},"service":{"api":{"root":"src","endpoints":["api/v1"]}}}
|
package/src/athena/validate.ts
CHANGED
|
@@ -58,6 +58,7 @@ export function offsetToLoc(text: string, offset: number): { line: number; colum
|
|
|
58
58
|
}
|
|
59
59
|
|
|
60
60
|
const log = debug('eslint-plugin:athena');
|
|
61
|
+
const ANONYMOUS_TABLE = '<anonymous>';
|
|
61
62
|
|
|
62
63
|
// ---------------------------------------------------------------------------
|
|
63
64
|
// Helpers
|
|
@@ -77,6 +78,10 @@ function getApiSchemas(serviceName: string, ctx: VisitContext) {
|
|
|
77
78
|
}
|
|
78
79
|
|
|
79
80
|
function lookupTables(nameOrAlias: string, ctx: VisitContext): ResolvedTable[] {
|
|
81
|
+
// Direct hit first: aliases are now stored under their alias key in ctx.tables.
|
|
82
|
+
if (ctx.tables.has(nameOrAlias)) {
|
|
83
|
+
return ctx.tables.get(nameOrAlias) ?? [];
|
|
84
|
+
}
|
|
80
85
|
const canonical = ctx.aliases.get(nameOrAlias) ?? nameOrAlias;
|
|
81
86
|
return ctx.tables.get(canonical) ?? [];
|
|
82
87
|
}
|
|
@@ -95,15 +100,18 @@ function fromClauseItems(select: Select): From[] {
|
|
|
95
100
|
// Pass 1 — Resolve FROM clause: service tables → ctx.tables + ctx.aliases
|
|
96
101
|
// ---------------------------------------------------------------------------
|
|
97
102
|
|
|
98
|
-
function resolveServiceTable(select: Select, item: BaseFrom, ctx: VisitContext): void {
|
|
103
|
+
function resolveServiceTable(select: Select, item: BaseFrom, ctx: VisitContext, storageKey?: string): void {
|
|
99
104
|
const { table: tableName } = item;
|
|
105
|
+
const key = storageKey ?? tableName;
|
|
100
106
|
try {
|
|
101
107
|
const apiSchemas = getApiSchemas(tableName, ctx);
|
|
102
108
|
if (apiSchemas.length === 0) {
|
|
103
109
|
throw new AthenaError(ATHENA_ERROR, `service not found: "${tableName}" (no swagger schema located)`, item);
|
|
104
110
|
}
|
|
105
111
|
const operations = matchApi(select, item, apiSchemas) ?? [];
|
|
106
|
-
|
|
112
|
+
// Always use the canonical table name for ResolvedTable.name so that error messages
|
|
113
|
+
// ("in tables: …") show the service name, not the alias.
|
|
114
|
+
ctx.tables.set(key, buildServiceTables(tableName, operations));
|
|
107
115
|
} catch (error) {
|
|
108
116
|
if (error instanceof AthenaError) {
|
|
109
117
|
throw error;
|
|
@@ -116,6 +124,11 @@ function restrictToFromClause(select: Select, ctx: VisitContext): void {
|
|
|
116
124
|
const fromNames = new Set<string>();
|
|
117
125
|
for (const item of fromClauseItems(select)) {
|
|
118
126
|
if (isBaseFrom(item) || isJoin(item)) {
|
|
127
|
+
// Service tables are stored under the alias key; CTEs are stored under the
|
|
128
|
+
// canonical name. Add both so either lookup survives the prune.
|
|
129
|
+
if (item.as !== null) {
|
|
130
|
+
fromNames.add(item.as);
|
|
131
|
+
}
|
|
119
132
|
fromNames.add(item.table);
|
|
120
133
|
} else if (isTableExpr(item)) {
|
|
121
134
|
fromNames.add(typeof item.as === 'string' ? item.as : '<subquery>');
|
|
@@ -128,45 +141,35 @@ function restrictToFromClause(select: Select, ctx: VisitContext): void {
|
|
|
128
141
|
}
|
|
129
142
|
}
|
|
130
143
|
|
|
144
|
+
function tableIsResolved(tableName: string, storageKey: string, ctx: VisitContext): boolean {
|
|
145
|
+
return ctx.tables.has(storageKey) || ctx.tables.has(tableName);
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
// Shared resolution logic for BaseFrom and Join items (Join extends BaseFrom).
|
|
149
|
+
function resolveTableOrJoinItem(select: Select, item: BaseFrom, ctx: VisitContext): void {
|
|
150
|
+
const { table: tableName, as: alias } = item;
|
|
151
|
+
if (alias !== null) {
|
|
152
|
+
ctx.aliases.set(alias, tableName);
|
|
153
|
+
}
|
|
154
|
+
const storageKey = alias ?? tableName;
|
|
155
|
+
// Skip if already resolved: CTE stored under canonical name, or duplicate alias.
|
|
156
|
+
if (!tableIsResolved(tableName, storageKey, ctx)) {
|
|
157
|
+
resolveServiceTable(select, item, ctx, alias ?? undefined);
|
|
158
|
+
}
|
|
159
|
+
}
|
|
160
|
+
|
|
131
161
|
function resolveFromClause(select: Select, ctx: VisitContext): void {
|
|
132
162
|
for (const item of fromClauseItems(select)) {
|
|
133
163
|
if (isUnnestFrom(item)) {
|
|
134
164
|
continue;
|
|
135
165
|
}
|
|
136
|
-
|
|
137
166
|
if (isTableExpr(item)) {
|
|
138
167
|
const alias = typeof item.as === 'string' ? item.as : '<subquery>';
|
|
139
168
|
// eslint-disable-next-line no-use-before-define
|
|
140
169
|
checkSelect(item.expr.ast, ctx, alias);
|
|
141
|
-
|
|
170
|
+
} else if (isJoin(item) || isBaseFrom(item)) {
|
|
171
|
+
resolveTableOrJoinItem(select, item, ctx);
|
|
142
172
|
}
|
|
143
|
-
|
|
144
|
-
if (isJoin(item)) {
|
|
145
|
-
const { table: tableName, as: alias } = item;
|
|
146
|
-
if (alias !== null) {
|
|
147
|
-
ctx.aliases.set(alias, tableName);
|
|
148
|
-
}
|
|
149
|
-
if (!ctx.tables.has(tableName)) {
|
|
150
|
-
resolveServiceTable(select, item, ctx);
|
|
151
|
-
}
|
|
152
|
-
continue;
|
|
153
|
-
}
|
|
154
|
-
|
|
155
|
-
if (!isBaseFrom(item)) {
|
|
156
|
-
continue;
|
|
157
|
-
}
|
|
158
|
-
|
|
159
|
-
const { table: tableName, as: alias } = item;
|
|
160
|
-
|
|
161
|
-
if (alias !== null) {
|
|
162
|
-
ctx.aliases.set(alias, tableName);
|
|
163
|
-
}
|
|
164
|
-
|
|
165
|
-
if (ctx.tables.has(tableName)) {
|
|
166
|
-
continue;
|
|
167
|
-
}
|
|
168
|
-
|
|
169
|
-
resolveServiceTable(select, item, ctx);
|
|
170
173
|
}
|
|
171
174
|
}
|
|
172
175
|
|
|
@@ -219,7 +222,7 @@ function applyUnnestPre(mappings: UnnestMapping[], ctx: VisitContext): UnnestMap
|
|
|
219
222
|
|
|
220
223
|
const sourceColumns = ownerTable.columns.get(fromColumn) ?? [];
|
|
221
224
|
const sourceSchema = sourceColumns[0]?.schema;
|
|
222
|
-
const unnestTableName = `${ownerTable.name ??
|
|
225
|
+
const unnestTableName = `${ownerTable.name ?? ANONYMOUS_TABLE}:<unnested>`;
|
|
223
226
|
const apiOperation = ownerTable.apiOperation !== undefined ? { apiOperation: ownerTable.apiOperation } : {};
|
|
224
227
|
|
|
225
228
|
if (sourceSchema?.type === 'array') {
|
|
@@ -388,7 +391,7 @@ function lookupColumnOrThrow(colRef: string, ref: object, referencedTables: Reso
|
|
|
388
391
|
const resolvedColumns = referencedTables.flatMap((table) => table.columns.get(colRef) ?? []);
|
|
389
392
|
if (resolvedColumns.length === 0) {
|
|
390
393
|
const tableNames = [
|
|
391
|
-
...new Set(referencedTables.map((referenceTable) => referenceTable.name ??
|
|
394
|
+
...new Set(referencedTables.map((referenceTable) => referenceTable.name ?? ANONYMOUS_TABLE)),
|
|
392
395
|
].join(', ');
|
|
393
396
|
const availableCols = [...new Set(referencedTables.flatMap((table) => [...table.columns.keys()]))].join(', ');
|
|
394
397
|
throw new AthenaError(
|
|
@@ -460,10 +463,9 @@ function resolveSingleColumnRef(
|
|
|
460
463
|
|
|
461
464
|
const referencedTables = tableRef !== undefined ? lookupTables(tableRef, ctx) : allTables;
|
|
462
465
|
if (referencedTables.length === 0) {
|
|
463
|
-
const tableNames = [...ctx.tables.keys()].join(', ');
|
|
464
466
|
throw new AthenaError(
|
|
465
467
|
ATHENA_ERROR,
|
|
466
|
-
`unknown table or alias '${tableRef ?? colRef}'; known tables: ${
|
|
468
|
+
`unknown table or alias '${tableRef ?? colRef}'; known tables: ${[...ctx.tables.keys()].join(', ')}`,
|
|
467
469
|
ref,
|
|
468
470
|
);
|
|
469
471
|
}
|