@xylex-group/athena 2.6.0 → 2.8.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/README.md +210 -17
- package/dist/browser.cjs +2102 -527
- package/dist/browser.cjs.map +1 -1
- package/dist/browser.d.cts +8 -7
- package/dist/browser.d.ts +8 -7
- package/dist/browser.js +2096 -528
- package/dist/browser.js.map +1 -1
- package/dist/cli/index.cjs +2116 -559
- package/dist/cli/index.cjs.map +1 -1
- package/dist/cli/index.d.cts +3 -3
- package/dist/cli/index.d.ts +3 -3
- package/dist/cli/index.js +2116 -559
- package/dist/cli/index.js.map +1 -1
- package/dist/cookies.cjs +10 -3
- package/dist/cookies.cjs.map +1 -1
- package/dist/cookies.js +10 -3
- package/dist/cookies.js.map +1 -1
- package/dist/index.cjs +2694 -748
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +8 -7
- package/dist/index.d.ts +8 -7
- package/dist/index.js +2688 -749
- package/dist/index.js.map +1 -1
- package/dist/model-form-DMed05gE.d.cts +3037 -0
- package/dist/model-form-DXPlOnlI.d.ts +3037 -0
- package/dist/{pipeline-Ce3pTw5h.d.ts → pipeline-CkMnhwPI.d.ts} +1 -1
- package/dist/{pipeline-D1ZYeoH7.d.cts → pipeline-D4sJRKqN.d.cts} +1 -1
- package/dist/react-email-DZhDDlEl.d.cts +417 -0
- package/dist/react-email-Lrz9A-BW.d.ts +417 -0
- package/dist/react.cjs +178 -71
- package/dist/react.cjs.map +1 -1
- package/dist/react.d.cts +22 -5
- package/dist/react.d.ts +22 -5
- package/dist/react.js +92 -5
- package/dist/react.js.map +1 -1
- package/dist/{types-CUuo4NDi.d.cts → types-BzY6fETM.d.ts} +47 -5
- package/dist/{types-DapchQY5.d.ts → types-CAtTGGoz.d.cts} +47 -5
- package/dist/{types-DSX6AT5B.d.cts → types-vikz9YIO.d.cts} +23 -1
- package/dist/{types-DSX6AT5B.d.ts → types-vikz9YIO.d.ts} +23 -1
- package/package.json +194 -193
- package/dist/model-form-BaHWi3gm.d.cts +0 -1383
- package/dist/model-form-Dh6gWjL0.d.ts +0 -1383
- package/dist/react-email-B8O1Jeff.d.cts +0 -1230
- package/dist/react-email-CDEF0jij.d.ts +0 -1230
package/dist/cli/index.cjs
CHANGED
|
@@ -131,59 +131,6 @@ function escapeStringLiteral(value) {
|
|
|
131
131
|
return `'${value.replace(/\\/g, "\\\\").replace(/'/g, "\\'")}'`;
|
|
132
132
|
}
|
|
133
133
|
|
|
134
|
-
// src/generator/placeholders.ts
|
|
135
|
-
function createStyleTokens(prefix, value) {
|
|
136
|
-
return {
|
|
137
|
-
[prefix]: value,
|
|
138
|
-
[`${prefix}_camel`]: applyNamingStyle(value, "camel"),
|
|
139
|
-
[`${prefix}_pascal`]: applyNamingStyle(value, "pascal"),
|
|
140
|
-
[`${prefix}_snake`]: applyNamingStyle(value, "snake"),
|
|
141
|
-
[`${prefix}_kebab`]: applyNamingStyle(value, "kebab")
|
|
142
|
-
};
|
|
143
|
-
}
|
|
144
|
-
function renderTemplate(template, tokenMap) {
|
|
145
|
-
return template.replace(/\{([A-Za-z0-9_]+)\}/g, (_match, token) => {
|
|
146
|
-
if (!(token in tokenMap)) {
|
|
147
|
-
throw new Error(`Unknown placeholder token "${token}" in template "${template}"`);
|
|
148
|
-
}
|
|
149
|
-
return tokenMap[token];
|
|
150
|
-
});
|
|
151
|
-
}
|
|
152
|
-
function resolvePlaceholderMap(baseTokens, outputConfig) {
|
|
153
|
-
const resolved = {
|
|
154
|
-
...baseTokens
|
|
155
|
-
};
|
|
156
|
-
const reservedTokenKeys = new Set(Object.keys(baseTokens));
|
|
157
|
-
const entries = Object.entries(outputConfig.placeholderMap ?? {});
|
|
158
|
-
for (let index = 0; index < entries.length; index += 1) {
|
|
159
|
-
const [key, value] = entries[index];
|
|
160
|
-
if (reservedTokenKeys.has(key)) {
|
|
161
|
-
continue;
|
|
162
|
-
}
|
|
163
|
-
let current = value;
|
|
164
|
-
for (let depth = 0; depth < 8; depth += 1) {
|
|
165
|
-
const next = renderTemplate(current, resolved);
|
|
166
|
-
if (next === current) {
|
|
167
|
-
break;
|
|
168
|
-
}
|
|
169
|
-
current = next;
|
|
170
|
-
}
|
|
171
|
-
resolved[key] = current;
|
|
172
|
-
}
|
|
173
|
-
return resolved;
|
|
174
|
-
}
|
|
175
|
-
function renderOutputPath(template, context, outputConfig) {
|
|
176
|
-
const baseTokens = {
|
|
177
|
-
provider: context.provider,
|
|
178
|
-
kind: context.kind,
|
|
179
|
-
...createStyleTokens("database", context.database),
|
|
180
|
-
...createStyleTokens("schema", context.schema),
|
|
181
|
-
...createStyleTokens("model", context.model)
|
|
182
|
-
};
|
|
183
|
-
const tokens = resolvePlaceholderMap(baseTokens, outputConfig);
|
|
184
|
-
return renderTemplate(template, tokens);
|
|
185
|
-
}
|
|
186
|
-
|
|
187
134
|
// src/generator/postgres-type-mapping.ts
|
|
188
135
|
var NUMBER_TYPES = /* @__PURE__ */ new Set([
|
|
189
136
|
"int2",
|
|
@@ -757,6 +704,7 @@ var DEFAULT_TARGETS = {
|
|
|
757
704
|
database: "athena/relations.ts",
|
|
758
705
|
registry: "athena/config.ts"
|
|
759
706
|
};
|
|
707
|
+
var DEFAULT_OUTPUT_FORMAT = "define-model";
|
|
760
708
|
var DEFAULT_NAMING = {
|
|
761
709
|
modelType: "pascal",
|
|
762
710
|
modelConst: "camel",
|
|
@@ -772,6 +720,9 @@ var DEFAULT_EXPERIMENTAL_FLAGS = {
|
|
|
772
720
|
postgresGatewayIntrospection: false,
|
|
773
721
|
scyllaProviderContracts: true
|
|
774
722
|
};
|
|
723
|
+
var DEFAULT_INTERNAL_CONFIG = {
|
|
724
|
+
schemaVersion: 1
|
|
725
|
+
};
|
|
775
726
|
var PROJECT_ENV_FILENAMES = [".env", ".env.local"];
|
|
776
727
|
var DIRECT_CONNECTION_STRING_ENV_KEYS = [
|
|
777
728
|
"ATHENA_GENERATOR_PG_URL",
|
|
@@ -788,6 +739,27 @@ var GATEWAY_API_KEY_ENV_KEYS = [
|
|
|
788
739
|
"ATHENA_GATEWAY_API_KEY",
|
|
789
740
|
"ATHENA_GENERATOR_API_KEY"
|
|
790
741
|
];
|
|
742
|
+
var GENERATOR_SCHEMA_ENV_KEYS = ["ATHENA_GENERATOR_SCHEMAS"];
|
|
743
|
+
var OUTPUT_FORMAT_ENV_KEYS = ["ATHENA_GENERATOR_OUTPUT_FORMAT"];
|
|
744
|
+
var MODEL_TARGET_ENV_KEYS = ["ATHENA_GENERATOR_MODEL_TARGET"];
|
|
745
|
+
var SCHEMA_TARGET_ENV_KEYS = ["ATHENA_GENERATOR_SCHEMA_TARGET"];
|
|
746
|
+
var DATABASE_TARGET_ENV_KEYS = ["ATHENA_GENERATOR_DATABASE_TARGET"];
|
|
747
|
+
var REGISTRY_TARGET_ENV_KEYS = ["ATHENA_GENERATOR_REGISTRY_TARGET"];
|
|
748
|
+
var PLACEHOLDER_MAP_ENV_KEYS = ["ATHENA_GENERATOR_PLACEHOLDER_MAP"];
|
|
749
|
+
var MODEL_TYPE_ENV_KEYS = ["ATHENA_GENERATOR_MODEL_TYPE", "ATHENA_GENERATOR_MODEL_STYLE"];
|
|
750
|
+
var MODEL_CONST_ENV_KEYS = ["ATHENA_GENERATOR_MODEL_CONST"];
|
|
751
|
+
var SCHEMA_CONST_ENV_KEYS = ["ATHENA_GENERATOR_SCHEMA_CONST"];
|
|
752
|
+
var DATABASE_CONST_ENV_KEYS = ["ATHENA_GENERATOR_DATABASE_CONST"];
|
|
753
|
+
var REGISTRY_CONST_ENV_KEYS = ["ATHENA_GENERATOR_REGISTRY_CONST"];
|
|
754
|
+
var EMIT_RELATIONS_ENV_KEYS = ["ATHENA_GENERATOR_EMIT_RELATIONS"];
|
|
755
|
+
var EMIT_REGISTRY_ENV_KEYS = ["ATHENA_GENERATOR_EMIT_REGISTRY"];
|
|
756
|
+
var GATEWAY_BACKEND_ENV_KEYS = ["ATHENA_GENERATOR_BACKEND"];
|
|
757
|
+
var GATEWAY_EXPERIMENTAL_ENV_KEYS = ["ATHENA_GENERATOR_GATEWAY_EXPERIMENTAL"];
|
|
758
|
+
var SCYLLA_PROVIDER_CONTRACTS_ENV_KEYS = ["ATHENA_GENERATOR_SCYLLA_PROVIDER_CONTRACTS"];
|
|
759
|
+
var ENV_ONLY_CONFIG_PATH = "[environment defaults]";
|
|
760
|
+
var NAMING_STYLE_VALUES = ["preserve", "camel", "pascal", "snake", "kebab"];
|
|
761
|
+
var OUTPUT_FORMAT_VALUES = ["define-model", "table-builder"];
|
|
762
|
+
var BACKEND_TYPE_VALUES = ["athena", "postgrest", "postgresql", "scylladb"];
|
|
791
763
|
function normalizeRawEnvValue(rawValue) {
|
|
792
764
|
if (rawValue.startsWith('"') && rawValue.endsWith('"') && rawValue.length >= 2) {
|
|
793
765
|
const inner = rawValue.slice(1, -1);
|
|
@@ -879,6 +851,50 @@ function resolveFallbackValue(fallbackKeys) {
|
|
|
879
851
|
}
|
|
880
852
|
return void 0;
|
|
881
853
|
}
|
|
854
|
+
function normalizeOneOfValue(rawValue, allowedValues, envKeys) {
|
|
855
|
+
if (!rawValue) {
|
|
856
|
+
return void 0;
|
|
857
|
+
}
|
|
858
|
+
if (allowedValues.includes(rawValue)) {
|
|
859
|
+
return rawValue;
|
|
860
|
+
}
|
|
861
|
+
throw new Error(
|
|
862
|
+
`Generator config env vars ${envKeys.join(", ")} must resolve to one of: ${allowedValues.join(", ")}. Received: ${rawValue}.`
|
|
863
|
+
);
|
|
864
|
+
}
|
|
865
|
+
function resolveOptionalOneOf(envKeys, allowedValues) {
|
|
866
|
+
return normalizeOneOfValue(resolveFallbackValue(envKeys), allowedValues, envKeys);
|
|
867
|
+
}
|
|
868
|
+
function resolveOptionalBoolean(envKeys) {
|
|
869
|
+
const rawValue = resolveFallbackValue(envKeys);
|
|
870
|
+
return rawValue === void 0 ? void 0 : parseBooleanFlag2(rawValue, false);
|
|
871
|
+
}
|
|
872
|
+
function resolveOptionalJson(envKeys) {
|
|
873
|
+
const rawValue = resolveFallbackValue(envKeys);
|
|
874
|
+
if (rawValue === void 0) {
|
|
875
|
+
return void 0;
|
|
876
|
+
}
|
|
877
|
+
try {
|
|
878
|
+
return JSON.parse(rawValue);
|
|
879
|
+
} catch (error) {
|
|
880
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
881
|
+
throw new Error(
|
|
882
|
+
`Generator config env vars ${envKeys.join(", ")} must contain valid JSON. ${message}`
|
|
883
|
+
);
|
|
884
|
+
}
|
|
885
|
+
}
|
|
886
|
+
function deriveDatabaseNameFromConnectionString(connectionString) {
|
|
887
|
+
try {
|
|
888
|
+
const parsedUrl = new URL(connectionString);
|
|
889
|
+
if (!POSTGRES_PROTOCOLS.has(parsedUrl.protocol)) {
|
|
890
|
+
return void 0;
|
|
891
|
+
}
|
|
892
|
+
const pathname = parsedUrl.pathname.replace(/^\/+/, "").trim();
|
|
893
|
+
return pathname.length > 0 ? decodeURIComponent(pathname) : void 0;
|
|
894
|
+
} catch {
|
|
895
|
+
return void 0;
|
|
896
|
+
}
|
|
897
|
+
}
|
|
882
898
|
function normalizeOptionalString(value, fallbackKeys) {
|
|
883
899
|
if (typeof value === "string") {
|
|
884
900
|
const trimmed = value.trim();
|
|
@@ -952,12 +968,13 @@ function normalizeExperimentalFlags(input) {
|
|
|
952
968
|
}
|
|
953
969
|
function normalizeOutputConfig(output) {
|
|
954
970
|
return {
|
|
971
|
+
format: output?.format ?? DEFAULT_OUTPUT_FORMAT,
|
|
955
972
|
targets: {
|
|
956
973
|
...DEFAULT_TARGETS,
|
|
957
|
-
...output
|
|
974
|
+
...output?.targets ?? {}
|
|
958
975
|
},
|
|
959
976
|
placeholderMap: {
|
|
960
|
-
...output
|
|
977
|
+
...output?.placeholderMap ?? {}
|
|
961
978
|
}
|
|
962
979
|
};
|
|
963
980
|
}
|
|
@@ -968,7 +985,7 @@ function normalizeProviderConfig(provider) {
|
|
|
968
985
|
"provider.connectionString",
|
|
969
986
|
DIRECT_CONNECTION_STRING_ENV_KEYS
|
|
970
987
|
);
|
|
971
|
-
const database = normalizeOptionalString(provider.database, POSTGRES_DATABASE_ENV_KEYS);
|
|
988
|
+
const database = normalizeOptionalString(provider.database, POSTGRES_DATABASE_ENV_KEYS) ?? deriveDatabaseNameFromConnectionString(connectionString);
|
|
972
989
|
return {
|
|
973
990
|
...provider,
|
|
974
991
|
connectionString: applyPostgresPasswordFallback(connectionString),
|
|
@@ -987,11 +1004,7 @@ function normalizeProviderConfig(provider) {
|
|
|
987
1004
|
"provider.apiKey",
|
|
988
1005
|
GATEWAY_API_KEY_ENV_KEYS
|
|
989
1006
|
);
|
|
990
|
-
const database =
|
|
991
|
-
provider.database,
|
|
992
|
-
"provider.database",
|
|
993
|
-
POSTGRES_DATABASE_ENV_KEYS
|
|
994
|
-
);
|
|
1007
|
+
const database = normalizeOptionalString(provider.database, POSTGRES_DATABASE_ENV_KEYS) ?? "postgres";
|
|
995
1008
|
return {
|
|
996
1009
|
...provider,
|
|
997
1010
|
gatewayUrl,
|
|
@@ -1000,6 +1013,26 @@ function normalizeProviderConfig(provider) {
|
|
|
1000
1013
|
schemas: normalizeSchemaSelection(provider.schemas)
|
|
1001
1014
|
};
|
|
1002
1015
|
}
|
|
1016
|
+
if (provider.kind === "scylla" && provider.mode === "direct") {
|
|
1017
|
+
if (!provider.contactPoints?.length) {
|
|
1018
|
+
throw new Error(
|
|
1019
|
+
"Generator config is missing provider.contactPoints for scylla direct mode."
|
|
1020
|
+
);
|
|
1021
|
+
}
|
|
1022
|
+
const keyspace = normalizeOptionalString(provider.keyspace, []);
|
|
1023
|
+
if (!keyspace) {
|
|
1024
|
+
throw new Error(
|
|
1025
|
+
"Generator config is missing provider.keyspace for scylla direct mode."
|
|
1026
|
+
);
|
|
1027
|
+
}
|
|
1028
|
+
return {
|
|
1029
|
+
kind: "scylla",
|
|
1030
|
+
mode: "direct",
|
|
1031
|
+
contactPoints: provider.contactPoints.slice(),
|
|
1032
|
+
keyspace,
|
|
1033
|
+
datacenter: normalizeOptionalString(provider.datacenter, [])
|
|
1034
|
+
};
|
|
1035
|
+
}
|
|
1003
1036
|
return provider;
|
|
1004
1037
|
}
|
|
1005
1038
|
function isAthenaGeneratorConfig(value) {
|
|
@@ -1007,7 +1040,7 @@ function isAthenaGeneratorConfig(value) {
|
|
|
1007
1040
|
return false;
|
|
1008
1041
|
}
|
|
1009
1042
|
const record = value;
|
|
1010
|
-
return Boolean(record.provider && typeof record.provider === "object") &&
|
|
1043
|
+
return Boolean(record.provider && typeof record.provider === "object") && (record.output === void 0 || typeof record.output === "object");
|
|
1011
1044
|
}
|
|
1012
1045
|
function normalizeGeneratorConfig(input) {
|
|
1013
1046
|
return {
|
|
@@ -1018,7 +1051,10 @@ function normalizeGeneratorConfig(input) {
|
|
|
1018
1051
|
...input.naming ?? {}
|
|
1019
1052
|
},
|
|
1020
1053
|
features: normalizeFeatureFlags(input.features),
|
|
1021
|
-
experimental: normalizeExperimentalFlags(input.experimental)
|
|
1054
|
+
experimental: normalizeExperimentalFlags(input.experimental),
|
|
1055
|
+
internal: {
|
|
1056
|
+
...DEFAULT_INTERNAL_CONFIG
|
|
1057
|
+
}
|
|
1022
1058
|
};
|
|
1023
1059
|
}
|
|
1024
1060
|
function findGeneratorConfigPath(cwd = process.cwd()) {
|
|
@@ -1072,16 +1108,123 @@ function importConfigModule(moduleSpecifier) {
|
|
|
1072
1108
|
);
|
|
1073
1109
|
return runtimeImport(moduleSpecifier);
|
|
1074
1110
|
}
|
|
1111
|
+
function buildEnvironmentOutputConfig() {
|
|
1112
|
+
const format = resolveOptionalOneOf(OUTPUT_FORMAT_ENV_KEYS, OUTPUT_FORMAT_VALUES);
|
|
1113
|
+
const modelTarget = resolveFallbackValue(MODEL_TARGET_ENV_KEYS);
|
|
1114
|
+
const schemaTarget = resolveFallbackValue(SCHEMA_TARGET_ENV_KEYS);
|
|
1115
|
+
const databaseTarget = resolveFallbackValue(DATABASE_TARGET_ENV_KEYS);
|
|
1116
|
+
const registryTarget = resolveFallbackValue(REGISTRY_TARGET_ENV_KEYS);
|
|
1117
|
+
const placeholderMap = resolveOptionalJson(PLACEHOLDER_MAP_ENV_KEYS);
|
|
1118
|
+
if (format === void 0 && modelTarget === void 0 && schemaTarget === void 0 && databaseTarget === void 0 && registryTarget === void 0 && placeholderMap === void 0) {
|
|
1119
|
+
return void 0;
|
|
1120
|
+
}
|
|
1121
|
+
return {
|
|
1122
|
+
format,
|
|
1123
|
+
targets: {
|
|
1124
|
+
...modelTarget ? { model: modelTarget } : {},
|
|
1125
|
+
...schemaTarget ? { schema: schemaTarget } : {},
|
|
1126
|
+
...databaseTarget ? { database: databaseTarget } : {},
|
|
1127
|
+
...registryTarget ? { registry: registryTarget } : {}
|
|
1128
|
+
},
|
|
1129
|
+
placeholderMap
|
|
1130
|
+
};
|
|
1131
|
+
}
|
|
1132
|
+
function buildEnvironmentNamingConfig() {
|
|
1133
|
+
const modelType = resolveOptionalOneOf(MODEL_TYPE_ENV_KEYS, NAMING_STYLE_VALUES);
|
|
1134
|
+
const modelConst = resolveOptionalOneOf(MODEL_CONST_ENV_KEYS, NAMING_STYLE_VALUES);
|
|
1135
|
+
const schemaConst = resolveOptionalOneOf(SCHEMA_CONST_ENV_KEYS, NAMING_STYLE_VALUES);
|
|
1136
|
+
const databaseConst = resolveOptionalOneOf(DATABASE_CONST_ENV_KEYS, NAMING_STYLE_VALUES);
|
|
1137
|
+
const registryConst = resolveOptionalOneOf(REGISTRY_CONST_ENV_KEYS, NAMING_STYLE_VALUES);
|
|
1138
|
+
if (modelType === void 0 && modelConst === void 0 && schemaConst === void 0 && databaseConst === void 0 && registryConst === void 0) {
|
|
1139
|
+
return void 0;
|
|
1140
|
+
}
|
|
1141
|
+
return {
|
|
1142
|
+
...modelType ? { modelType } : {},
|
|
1143
|
+
...modelConst ? { modelConst } : {},
|
|
1144
|
+
...schemaConst ? { schemaConst } : {},
|
|
1145
|
+
...databaseConst ? { databaseConst } : {},
|
|
1146
|
+
...registryConst ? { registryConst } : {}
|
|
1147
|
+
};
|
|
1148
|
+
}
|
|
1149
|
+
function buildEnvironmentFeatureFlags() {
|
|
1150
|
+
const emitRelations = resolveOptionalBoolean(EMIT_RELATIONS_ENV_KEYS);
|
|
1151
|
+
const emitRegistry = resolveOptionalBoolean(EMIT_REGISTRY_ENV_KEYS);
|
|
1152
|
+
if (emitRelations === void 0 && emitRegistry === void 0) {
|
|
1153
|
+
return void 0;
|
|
1154
|
+
}
|
|
1155
|
+
return {
|
|
1156
|
+
...emitRelations !== void 0 ? { emitRelations } : {},
|
|
1157
|
+
...emitRegistry !== void 0 ? { emitRegistry } : {}
|
|
1158
|
+
};
|
|
1159
|
+
}
|
|
1160
|
+
function buildEnvironmentExperimentalFlags() {
|
|
1161
|
+
const postgresGatewayIntrospection = resolveOptionalBoolean(GATEWAY_EXPERIMENTAL_ENV_KEYS);
|
|
1162
|
+
const scyllaProviderContracts = resolveOptionalBoolean(SCYLLA_PROVIDER_CONTRACTS_ENV_KEYS);
|
|
1163
|
+
if (postgresGatewayIntrospection === void 0 && scyllaProviderContracts === void 0) {
|
|
1164
|
+
return void 0;
|
|
1165
|
+
}
|
|
1166
|
+
return {
|
|
1167
|
+
...postgresGatewayIntrospection !== void 0 ? { postgresGatewayIntrospection } : {},
|
|
1168
|
+
...scyllaProviderContracts !== void 0 ? { scyllaProviderContracts } : {}
|
|
1169
|
+
};
|
|
1170
|
+
}
|
|
1171
|
+
function buildEnvironmentProviderConfig() {
|
|
1172
|
+
const directConnectionString = resolveFallbackValue(DIRECT_CONNECTION_STRING_ENV_KEYS);
|
|
1173
|
+
if (directConnectionString) {
|
|
1174
|
+
return {
|
|
1175
|
+
kind: "postgres",
|
|
1176
|
+
mode: "direct",
|
|
1177
|
+
connectionString: directConnectionString,
|
|
1178
|
+
database: normalizeOptionalString(void 0, POSTGRES_DATABASE_ENV_KEYS),
|
|
1179
|
+
schemas: normalizeSchemaSelection(resolveFallbackValue(GENERATOR_SCHEMA_ENV_KEYS))
|
|
1180
|
+
};
|
|
1181
|
+
}
|
|
1182
|
+
const gatewayUrl = resolveFallbackValue(GATEWAY_URL_ENV_KEYS);
|
|
1183
|
+
const apiKey = resolveFallbackValue(GATEWAY_API_KEY_ENV_KEYS);
|
|
1184
|
+
if (gatewayUrl && apiKey) {
|
|
1185
|
+
const backend = resolveOptionalOneOf(GATEWAY_BACKEND_ENV_KEYS, BACKEND_TYPE_VALUES);
|
|
1186
|
+
return {
|
|
1187
|
+
kind: "postgres",
|
|
1188
|
+
mode: "gateway",
|
|
1189
|
+
gatewayUrl,
|
|
1190
|
+
apiKey,
|
|
1191
|
+
database: normalizeOptionalString(void 0, POSTGRES_DATABASE_ENV_KEYS),
|
|
1192
|
+
schemas: normalizeSchemaSelection(resolveFallbackValue(GENERATOR_SCHEMA_ENV_KEYS)),
|
|
1193
|
+
backend
|
|
1194
|
+
};
|
|
1195
|
+
}
|
|
1196
|
+
return void 0;
|
|
1197
|
+
}
|
|
1198
|
+
function createEnvironmentGeneratorConfig() {
|
|
1199
|
+
const provider = buildEnvironmentProviderConfig();
|
|
1200
|
+
if (!provider) {
|
|
1201
|
+
return void 0;
|
|
1202
|
+
}
|
|
1203
|
+
return {
|
|
1204
|
+
provider,
|
|
1205
|
+
output: buildEnvironmentOutputConfig(),
|
|
1206
|
+
naming: buildEnvironmentNamingConfig(),
|
|
1207
|
+
features: buildEnvironmentFeatureFlags(),
|
|
1208
|
+
experimental: buildEnvironmentExperimentalFlags()
|
|
1209
|
+
};
|
|
1210
|
+
}
|
|
1075
1211
|
async function loadGeneratorConfig(options = {}) {
|
|
1076
1212
|
const cwd = options.cwd ?? process.cwd();
|
|
1077
1213
|
const restoreProjectEnv = applyProjectEnv(cwd);
|
|
1078
|
-
const resolvedPath = options.configPath ? path.resolve(cwd, options.configPath) : findGeneratorConfigPath(cwd);
|
|
1079
|
-
if (!resolvedPath) {
|
|
1080
|
-
throw new Error(
|
|
1081
|
-
`No generator config found in ${cwd}. Expected one of: ${DEFAULT_CONFIG_CANDIDATES.join(", ")}`
|
|
1082
|
-
);
|
|
1083
|
-
}
|
|
1084
1214
|
try {
|
|
1215
|
+
const resolvedPath = options.configPath ? path.resolve(cwd, options.configPath) : findGeneratorConfigPath(cwd);
|
|
1216
|
+
if (!resolvedPath) {
|
|
1217
|
+
const environmentConfig = createEnvironmentGeneratorConfig();
|
|
1218
|
+
if (environmentConfig) {
|
|
1219
|
+
return {
|
|
1220
|
+
configPath: ENV_ONLY_CONFIG_PATH,
|
|
1221
|
+
config: normalizeGeneratorConfig(environmentConfig)
|
|
1222
|
+
};
|
|
1223
|
+
}
|
|
1224
|
+
throw new Error(
|
|
1225
|
+
`No generator config found in ${cwd}. Expected one of: ${DEFAULT_CONFIG_CANDIDATES.join(", ")}. To run without a config file, set DATABASE_URL (direct mode) or ATHENA_URL + ATHENA_API_KEY (gateway mode).`
|
|
1226
|
+
);
|
|
1227
|
+
}
|
|
1085
1228
|
const moduleUrl = url.pathToFileURL(resolvedPath);
|
|
1086
1229
|
const module = await importConfigModule(`${moduleUrl.href}?cacheBust=${Date.now()}`);
|
|
1087
1230
|
const rawConfig = extractConfigExport(module);
|
|
@@ -1094,7 +1237,60 @@ async function loadGeneratorConfig(options = {}) {
|
|
|
1094
1237
|
}
|
|
1095
1238
|
}
|
|
1096
1239
|
|
|
1097
|
-
// src/generator/
|
|
1240
|
+
// src/generator/placeholders.ts
|
|
1241
|
+
function createStyleTokens(prefix, value) {
|
|
1242
|
+
return {
|
|
1243
|
+
[prefix]: value,
|
|
1244
|
+
[`${prefix}_camel`]: applyNamingStyle(value, "camel"),
|
|
1245
|
+
[`${prefix}_pascal`]: applyNamingStyle(value, "pascal"),
|
|
1246
|
+
[`${prefix}_snake`]: applyNamingStyle(value, "snake"),
|
|
1247
|
+
[`${prefix}_kebab`]: applyNamingStyle(value, "kebab")
|
|
1248
|
+
};
|
|
1249
|
+
}
|
|
1250
|
+
function renderTemplate(template, tokenMap) {
|
|
1251
|
+
return template.replace(/\{([A-Za-z0-9_]+)\}/g, (_match, token) => {
|
|
1252
|
+
if (!(token in tokenMap)) {
|
|
1253
|
+
throw new Error(`Unknown placeholder token "${token}" in template "${template}"`);
|
|
1254
|
+
}
|
|
1255
|
+
return tokenMap[token];
|
|
1256
|
+
});
|
|
1257
|
+
}
|
|
1258
|
+
function resolvePlaceholderMap(baseTokens, outputConfig) {
|
|
1259
|
+
const resolved = {
|
|
1260
|
+
...baseTokens
|
|
1261
|
+
};
|
|
1262
|
+
const reservedTokenKeys = new Set(Object.keys(baseTokens));
|
|
1263
|
+
const entries = Object.entries(outputConfig.placeholderMap ?? {});
|
|
1264
|
+
for (let index = 0; index < entries.length; index += 1) {
|
|
1265
|
+
const [key, value] = entries[index];
|
|
1266
|
+
if (reservedTokenKeys.has(key)) {
|
|
1267
|
+
continue;
|
|
1268
|
+
}
|
|
1269
|
+
let current = value;
|
|
1270
|
+
for (let depth = 0; depth < 8; depth += 1) {
|
|
1271
|
+
const next = renderTemplate(current, resolved);
|
|
1272
|
+
if (next === current) {
|
|
1273
|
+
break;
|
|
1274
|
+
}
|
|
1275
|
+
current = next;
|
|
1276
|
+
}
|
|
1277
|
+
resolved[key] = current;
|
|
1278
|
+
}
|
|
1279
|
+
return resolved;
|
|
1280
|
+
}
|
|
1281
|
+
function renderOutputPath(template, context, outputConfig) {
|
|
1282
|
+
const baseTokens = {
|
|
1283
|
+
provider: context.provider,
|
|
1284
|
+
kind: context.kind,
|
|
1285
|
+
...createStyleTokens("database", context.database),
|
|
1286
|
+
...createStyleTokens("schema", context.schema),
|
|
1287
|
+
...createStyleTokens("model", context.model)
|
|
1288
|
+
};
|
|
1289
|
+
const tokens = resolvePlaceholderMap(baseTokens, outputConfig);
|
|
1290
|
+
return renderTemplate(template, tokens);
|
|
1291
|
+
}
|
|
1292
|
+
|
|
1293
|
+
// src/generator/render-shared.ts
|
|
1098
1294
|
function normalizePath(pathValue) {
|
|
1099
1295
|
return pathValue.replace(/\\/g, "/");
|
|
1100
1296
|
}
|
|
@@ -1107,11 +1303,13 @@ function toModuleImportPath(fromFile, targetFile) {
|
|
|
1107
1303
|
);
|
|
1108
1304
|
return relativePath.startsWith(".") ? relativePath : `./${relativePath}`;
|
|
1109
1305
|
}
|
|
1306
|
+
function resolveOutputPath(target, tokens, config) {
|
|
1307
|
+
return normalizePath(renderOutputPath(target, tokens, config.output));
|
|
1308
|
+
}
|
|
1110
1309
|
function renderObjectKey(key) {
|
|
1111
|
-
|
|
1112
|
-
return escaped.startsWith("'") ? escaped : escaped;
|
|
1310
|
+
return escapeTypePropertyName(key);
|
|
1113
1311
|
}
|
|
1114
|
-
function
|
|
1312
|
+
function renderRelationLiteral(relation) {
|
|
1115
1313
|
const through = relation.through ? `,
|
|
1116
1314
|
through: {
|
|
1117
1315
|
schema: ${escapeStringLiteral(relation.through.schema)},
|
|
@@ -1127,54 +1325,12 @@ function renderRelation(relation) {
|
|
|
1127
1325
|
targetColumns: [${relation.targetColumns.map((value) => escapeStringLiteral(value)).join(", ")}]${through}
|
|
1128
1326
|
}`;
|
|
1129
1327
|
}
|
|
1130
|
-
function renderModelArtifact(snapshot, descriptor, config) {
|
|
1131
|
-
const columnLines = Object.values(descriptor.table.columns).map((column) => {
|
|
1132
|
-
const propertyName = escapeTypePropertyName(column.name);
|
|
1133
|
-
const baseType = resolvePostgresColumnType(column);
|
|
1134
|
-
const isOptional = column.isNullable;
|
|
1135
|
-
const typeWithNullability = column.isNullable ? `${baseType} | null` : baseType;
|
|
1136
|
-
return ` ${propertyName}${isOptional ? "?" : ""}: ${typeWithNullability}`;
|
|
1137
|
-
}).join("\n");
|
|
1138
|
-
const nullableLines = Object.values(descriptor.table.columns).map((column) => ` ${renderObjectKey(column.name)}: ${column.isNullable ? "true" : "false"}`).join(",\n");
|
|
1139
|
-
const relationEntries = Object.entries(descriptor.table.relations);
|
|
1140
|
-
const relationBlock = config.features.emitRelations && relationEntries.length > 0 ? `,
|
|
1141
|
-
relations: {
|
|
1142
|
-
${relationEntries.map(([relationKey2, relationValue]) => ` ${renderObjectKey(relationKey2)}: ${renderRelation(relationValue)}`).join(",\n")}
|
|
1143
|
-
}` : "";
|
|
1144
|
-
const content = `import { defineModel } from '@xylex-group/athena'
|
|
1145
|
-
|
|
1146
|
-
export interface ${descriptor.rowTypeName} {
|
|
1147
|
-
${columnLines}
|
|
1148
|
-
}
|
|
1149
|
-
|
|
1150
|
-
export type ${descriptor.insertTypeName} = Partial<${descriptor.rowTypeName}>
|
|
1151
|
-
export type ${descriptor.updateTypeName} = Partial<${descriptor.insertTypeName}>
|
|
1152
|
-
|
|
1153
|
-
export const ${descriptor.modelConstName} = defineModel<${descriptor.rowTypeName}, ${descriptor.insertTypeName}, ${descriptor.updateTypeName}>({
|
|
1154
|
-
meta: {
|
|
1155
|
-
database: ${escapeStringLiteral(snapshot.database)},
|
|
1156
|
-
schema: ${escapeStringLiteral(descriptor.schemaName)},
|
|
1157
|
-
model: ${escapeStringLiteral(descriptor.tableName)},
|
|
1158
|
-
tableName: ${escapeStringLiteral(`${descriptor.schemaName}.${descriptor.tableName}`)},
|
|
1159
|
-
primaryKey: [${descriptor.table.primaryKey.map((value) => escapeStringLiteral(value)).join(", ")}],
|
|
1160
|
-
nullable: {
|
|
1161
|
-
${nullableLines}
|
|
1162
|
-
}${relationBlock}
|
|
1163
|
-
}
|
|
1164
|
-
})
|
|
1165
|
-
`;
|
|
1166
|
-
return {
|
|
1167
|
-
kind: "model",
|
|
1168
|
-
path: descriptor.filePath,
|
|
1169
|
-
content
|
|
1170
|
-
};
|
|
1171
|
-
}
|
|
1172
1328
|
function renderSchemaArtifact(descriptor) {
|
|
1173
1329
|
const importLines = descriptor.models.map((modelDescriptor) => {
|
|
1174
1330
|
const importPath = toModuleImportPath(descriptor.filePath, modelDescriptor.filePath);
|
|
1175
|
-
return `import { ${modelDescriptor.
|
|
1331
|
+
return `import { ${modelDescriptor.exportConstName} } from '${importPath}'`;
|
|
1176
1332
|
}).join("\n");
|
|
1177
|
-
const modelEntries = descriptor.models.map((modelDescriptor) => ` ${renderObjectKey(modelDescriptor.tableName)}: ${modelDescriptor.
|
|
1333
|
+
const modelEntries = descriptor.models.map((modelDescriptor) => ` ${renderObjectKey(modelDescriptor.tableName)}: ${modelDescriptor.exportConstName}`).join(",\n");
|
|
1178
1334
|
const content = `import { defineSchema } from '@xylex-group/athena'
|
|
1179
1335
|
${importLines ? `
|
|
1180
1336
|
${importLines}
|
|
@@ -1209,11 +1365,18 @@ ${schemaEntries}
|
|
|
1209
1365
|
content
|
|
1210
1366
|
};
|
|
1211
1367
|
}
|
|
1212
|
-
function renderRegistryArtifact(registryPath, databasePath, databaseConstName, registryConstName, databaseName) {
|
|
1368
|
+
function renderRegistryArtifact(registryPath, databasePath, databaseConstName, registryConstName, databaseName, generatedAt, outputFormat, schemaVersion) {
|
|
1213
1369
|
const databaseImportPath = toModuleImportPath(registryPath, databasePath);
|
|
1214
1370
|
const content = `import { defineRegistry } from '@xylex-group/athena'
|
|
1215
1371
|
import { ${databaseConstName} } from '${databaseImportPath}'
|
|
1216
1372
|
|
|
1373
|
+
export const __athena_schema_meta = {
|
|
1374
|
+
schemaVersion: ${schemaVersion},
|
|
1375
|
+
generatedAt: ${escapeStringLiteral(generatedAt)},
|
|
1376
|
+
database: ${escapeStringLiteral(databaseName)},
|
|
1377
|
+
outputFormat: ${escapeStringLiteral(outputFormat)},
|
|
1378
|
+
} as const
|
|
1379
|
+
|
|
1217
1380
|
export const ${registryConstName} = defineRegistry({
|
|
1218
1381
|
${renderObjectKey(databaseName)}: ${databaseConstName}
|
|
1219
1382
|
})
|
|
@@ -1292,123 +1455,332 @@ function scopeDuplicateDescriptorPathsBySchema(descriptors) {
|
|
|
1292
1455
|
}
|
|
1293
1456
|
return nextDescriptors;
|
|
1294
1457
|
}
|
|
1295
|
-
|
|
1296
|
-
|
|
1297
|
-
|
|
1298
|
-
|
|
1299
|
-
|
|
1300
|
-
|
|
1301
|
-
const
|
|
1302
|
-
const
|
|
1303
|
-
|
|
1304
|
-
|
|
1305
|
-
|
|
1306
|
-
|
|
1307
|
-
const table = schema.tables[tableName];
|
|
1308
|
-
const rowTypeName = `${toSafeIdentifier(`${schemaName} ${tableName}`, this.config.naming.modelType, "Model")}Row`;
|
|
1309
|
-
const insertTypeName = `${toSafeIdentifier(`${schemaName} ${tableName}`, this.config.naming.modelType, "Model")}Insert`;
|
|
1310
|
-
const updateTypeName = `${toSafeIdentifier(`${schemaName} ${tableName}`, this.config.naming.modelType, "Model")}Update`;
|
|
1311
|
-
const modelConstName = `${toSafeIdentifier(`${schemaName} ${tableName} model`, this.config.naming.modelConst, "model")}`;
|
|
1312
|
-
const modelPath = normalizePath(
|
|
1313
|
-
renderOutputPath(this.config.output.targets.model, {
|
|
1314
|
-
provider: providerName,
|
|
1315
|
-
kind: "model",
|
|
1316
|
-
database: databaseName,
|
|
1317
|
-
schema: schemaName,
|
|
1318
|
-
model: tableName
|
|
1319
|
-
}, this.config.output)
|
|
1320
|
-
);
|
|
1321
|
-
modelDescriptors.push({
|
|
1458
|
+
function composeGeneratorArtifacts(input) {
|
|
1459
|
+
const { snapshot, config, createModelDescriptor, renderModelArtifact: renderModelArtifact3 } = input;
|
|
1460
|
+
const providerName = snapshot.backend;
|
|
1461
|
+
const databaseName = snapshot.database;
|
|
1462
|
+
const modelDescriptors = [];
|
|
1463
|
+
for (const schemaName of Object.keys(snapshot.schemas).sort()) {
|
|
1464
|
+
const schema = snapshot.schemas[schemaName];
|
|
1465
|
+
for (const tableName of Object.keys(schema.tables).sort()) {
|
|
1466
|
+
modelDescriptors.push(
|
|
1467
|
+
createModelDescriptor({
|
|
1468
|
+
providerName,
|
|
1469
|
+
databaseName,
|
|
1322
1470
|
schemaName,
|
|
1323
1471
|
tableName,
|
|
1324
|
-
|
|
1325
|
-
|
|
1326
|
-
insertTypeName,
|
|
1327
|
-
updateTypeName,
|
|
1328
|
-
modelConstName,
|
|
1329
|
-
table
|
|
1330
|
-
});
|
|
1331
|
-
}
|
|
1332
|
-
}
|
|
1333
|
-
const scopedModelDescriptors = scopeDuplicateDescriptorPathsBySchema(modelDescriptors);
|
|
1334
|
-
let schemaDescriptors = Object.keys(this.snapshot.schemas).sort().map((schemaName) => {
|
|
1335
|
-
const schemaPath = normalizePath(
|
|
1336
|
-
renderOutputPath(this.config.output.targets.schema, {
|
|
1337
|
-
provider: providerName,
|
|
1338
|
-
kind: "schema",
|
|
1339
|
-
database: databaseName,
|
|
1340
|
-
schema: schemaName,
|
|
1341
|
-
model: "index"
|
|
1342
|
-
}, this.config.output)
|
|
1472
|
+
table: schema.tables[tableName]
|
|
1473
|
+
})
|
|
1343
1474
|
);
|
|
1344
|
-
|
|
1345
|
-
|
|
1346
|
-
|
|
1347
|
-
|
|
1348
|
-
|
|
1349
|
-
|
|
1350
|
-
|
|
1351
|
-
|
|
1352
|
-
models: scopedModelDescriptors.filter((model) => model.schemaName === schemaName)
|
|
1353
|
-
};
|
|
1354
|
-
});
|
|
1355
|
-
schemaDescriptors = scopeDuplicateDescriptorPathsBySchema(schemaDescriptors);
|
|
1356
|
-
const databasePath = normalizePath(
|
|
1357
|
-
renderOutputPath(this.config.output.targets.database, {
|
|
1475
|
+
}
|
|
1476
|
+
}
|
|
1477
|
+
const scopedModelDescriptors = scopeDuplicateDescriptorPathsBySchema(modelDescriptors);
|
|
1478
|
+
let schemaDescriptors = Object.keys(snapshot.schemas).sort().map((schemaName) => ({
|
|
1479
|
+
schemaName,
|
|
1480
|
+
filePath: resolveOutputPath(
|
|
1481
|
+
config.output.targets.schema,
|
|
1482
|
+
{
|
|
1358
1483
|
provider: providerName,
|
|
1359
|
-
kind: "
|
|
1484
|
+
kind: "schema",
|
|
1360
1485
|
database: databaseName,
|
|
1361
|
-
schema:
|
|
1486
|
+
schema: schemaName,
|
|
1362
1487
|
model: "index"
|
|
1363
|
-
},
|
|
1364
|
-
|
|
1365
|
-
|
|
1366
|
-
|
|
1367
|
-
|
|
1368
|
-
|
|
1369
|
-
|
|
1370
|
-
|
|
1371
|
-
|
|
1372
|
-
|
|
1373
|
-
|
|
1374
|
-
|
|
1375
|
-
|
|
1376
|
-
|
|
1377
|
-
|
|
1378
|
-
|
|
1379
|
-
|
|
1380
|
-
|
|
1381
|
-
|
|
1382
|
-
|
|
1383
|
-
|
|
1384
|
-
|
|
1385
|
-
|
|
1386
|
-
|
|
1387
|
-
|
|
1388
|
-
|
|
1389
|
-
|
|
1390
|
-
|
|
1391
|
-
|
|
1392
|
-
|
|
1393
|
-
|
|
1394
|
-
|
|
1395
|
-
|
|
1396
|
-
databaseDescriptor.databaseConstName,
|
|
1397
|
-
toSafeIdentifier("registry", this.config.naming.registryConst, "registry"),
|
|
1398
|
-
databaseName
|
|
1399
|
-
)
|
|
1400
|
-
);
|
|
1401
|
-
}
|
|
1402
|
-
assertNoDuplicatePaths(files);
|
|
1403
|
-
return {
|
|
1404
|
-
snapshot: this.snapshot,
|
|
1405
|
-
files
|
|
1406
|
-
};
|
|
1488
|
+
},
|
|
1489
|
+
config
|
|
1490
|
+
),
|
|
1491
|
+
schemaConstName: toSafeIdentifier(
|
|
1492
|
+
`${schemaName} schema`,
|
|
1493
|
+
config.naming.schemaConst,
|
|
1494
|
+
"schema"
|
|
1495
|
+
),
|
|
1496
|
+
models: scopedModelDescriptors.filter((model) => model.schemaName === schemaName)
|
|
1497
|
+
}));
|
|
1498
|
+
schemaDescriptors = scopeDuplicateDescriptorPathsBySchema(schemaDescriptors);
|
|
1499
|
+
const databaseDescriptor = {
|
|
1500
|
+
filePath: resolveOutputPath(
|
|
1501
|
+
config.output.targets.database,
|
|
1502
|
+
{
|
|
1503
|
+
provider: providerName,
|
|
1504
|
+
kind: "database",
|
|
1505
|
+
database: databaseName,
|
|
1506
|
+
schema: "index",
|
|
1507
|
+
model: "index"
|
|
1508
|
+
},
|
|
1509
|
+
config
|
|
1510
|
+
),
|
|
1511
|
+
databaseConstName: toSafeIdentifier(
|
|
1512
|
+
`${databaseName} database`,
|
|
1513
|
+
config.naming.databaseConst,
|
|
1514
|
+
"database"
|
|
1515
|
+
),
|
|
1516
|
+
schemas: schemaDescriptors
|
|
1517
|
+
};
|
|
1518
|
+
const files = [];
|
|
1519
|
+
for (const modelDescriptor of scopedModelDescriptors) {
|
|
1520
|
+
files.push(renderModelArtifact3(modelDescriptor));
|
|
1407
1521
|
}
|
|
1408
|
-
|
|
1522
|
+
for (const schemaDescriptor of schemaDescriptors) {
|
|
1523
|
+
files.push(renderSchemaArtifact(schemaDescriptor));
|
|
1524
|
+
}
|
|
1525
|
+
files.push(renderDatabaseArtifact(databaseDescriptor));
|
|
1526
|
+
if (config.features.emitRegistry) {
|
|
1527
|
+
const registryPath = resolveOutputPath(
|
|
1528
|
+
config.output.targets.registry,
|
|
1529
|
+
{
|
|
1530
|
+
provider: providerName,
|
|
1531
|
+
kind: "registry",
|
|
1532
|
+
database: databaseName,
|
|
1533
|
+
schema: "index",
|
|
1534
|
+
model: "index"
|
|
1535
|
+
},
|
|
1536
|
+
config
|
|
1537
|
+
);
|
|
1538
|
+
files.push(
|
|
1539
|
+
renderRegistryArtifact(
|
|
1540
|
+
registryPath,
|
|
1541
|
+
databaseDescriptor.filePath,
|
|
1542
|
+
databaseDescriptor.databaseConstName,
|
|
1543
|
+
toSafeIdentifier("registry", config.naming.registryConst, "registry"),
|
|
1544
|
+
databaseName,
|
|
1545
|
+
snapshot.generatedAt,
|
|
1546
|
+
config.output.format,
|
|
1547
|
+
config.internal.schemaVersion
|
|
1548
|
+
)
|
|
1549
|
+
);
|
|
1550
|
+
}
|
|
1551
|
+
assertNoDuplicatePaths(files);
|
|
1552
|
+
return {
|
|
1553
|
+
snapshot,
|
|
1554
|
+
files
|
|
1555
|
+
};
|
|
1556
|
+
}
|
|
1557
|
+
|
|
1558
|
+
// src/generator/table-builder-renderer.ts
|
|
1559
|
+
var SAFE_NUMBER_TYPES = /* @__PURE__ */ new Set([
|
|
1560
|
+
"int2",
|
|
1561
|
+
"int4",
|
|
1562
|
+
"float4",
|
|
1563
|
+
"float8",
|
|
1564
|
+
"smallint",
|
|
1565
|
+
"integer",
|
|
1566
|
+
"real",
|
|
1567
|
+
"double precision"
|
|
1568
|
+
]);
|
|
1569
|
+
var JSON_TYPES = /* @__PURE__ */ new Set(["json", "jsonb"]);
|
|
1570
|
+
var BOOLEAN_TYPES = /* @__PURE__ */ new Set(["bool", "boolean"]);
|
|
1571
|
+
var STRING_TYPES = /* @__PURE__ */ new Set([
|
|
1572
|
+
"int8",
|
|
1573
|
+
"bigint",
|
|
1574
|
+
"serial8",
|
|
1575
|
+
"bigserial",
|
|
1576
|
+
"numeric",
|
|
1577
|
+
"decimal",
|
|
1578
|
+
"money",
|
|
1579
|
+
"bytea"
|
|
1580
|
+
]);
|
|
1581
|
+
function normalizeTypeLabel2(column) {
|
|
1582
|
+
const preferred = (column.udtName || column.dataType).toLowerCase().trim();
|
|
1583
|
+
if (column.arrayDimensions > 0 && preferred.startsWith("_")) {
|
|
1584
|
+
return preferred.slice(1);
|
|
1585
|
+
}
|
|
1586
|
+
return preferred;
|
|
1587
|
+
}
|
|
1588
|
+
function renderColumnBuilder(column) {
|
|
1589
|
+
const label = normalizeTypeLabel2(column);
|
|
1590
|
+
let helper;
|
|
1591
|
+
let expression;
|
|
1592
|
+
if (column.typeKind === "enum" && column.enumValues && column.enumValues.length > 0) {
|
|
1593
|
+
helper = "enumeration";
|
|
1594
|
+
expression = `enumeration([${column.enumValues.map((value) => escapeStringLiteral(value)).join(", ")}] as const)`;
|
|
1595
|
+
} else if (column.arrayDimensions > 0 || JSON_TYPES.has(label) || column.typeKind === "composite") {
|
|
1596
|
+
helper = "json";
|
|
1597
|
+
expression = `json<${resolvePostgresColumnType(column)}>()`;
|
|
1598
|
+
} else if (BOOLEAN_TYPES.has(label)) {
|
|
1599
|
+
helper = "boolean";
|
|
1600
|
+
expression = "boolean()";
|
|
1601
|
+
} else if (SAFE_NUMBER_TYPES.has(label)) {
|
|
1602
|
+
helper = "number";
|
|
1603
|
+
expression = "number()";
|
|
1604
|
+
} else if (STRING_TYPES.has(label)) {
|
|
1605
|
+
helper = "string";
|
|
1606
|
+
expression = "string()";
|
|
1607
|
+
} else {
|
|
1608
|
+
helper = "string";
|
|
1609
|
+
expression = "string()";
|
|
1610
|
+
}
|
|
1611
|
+
if (column.isNullable) {
|
|
1612
|
+
expression = `${expression}.optional()`;
|
|
1613
|
+
}
|
|
1614
|
+
if (column.hasDefault) {
|
|
1615
|
+
expression = `${expression}.defaulted()`;
|
|
1616
|
+
}
|
|
1617
|
+
if (column.isGenerated) {
|
|
1618
|
+
expression = `${expression}.generated()`;
|
|
1619
|
+
}
|
|
1620
|
+
return { helper, expression };
|
|
1621
|
+
}
|
|
1622
|
+
function renderModelArtifact(descriptor, config) {
|
|
1623
|
+
const helperImports = /* @__PURE__ */ new Set(["table"]);
|
|
1624
|
+
const columnLines = Object.entries(descriptor.table.columns).map(([columnName, column]) => {
|
|
1625
|
+
const propertyName = escapeTypePropertyName(columnName);
|
|
1626
|
+
const rendered = renderColumnBuilder(column);
|
|
1627
|
+
helperImports.add(rendered.helper);
|
|
1628
|
+
return ` ${propertyName}: ${rendered.expression}`;
|
|
1629
|
+
}).join(",\n");
|
|
1630
|
+
const helperImportLine = Array.from(helperImports).sort().join(", ");
|
|
1631
|
+
const rowSchemaConstName = `${descriptor.tableConstName}_row_schema`;
|
|
1632
|
+
const insertSchemaConstName = `${descriptor.tableConstName}_insert_schema`;
|
|
1633
|
+
const updateSchemaConstName = `${descriptor.tableConstName}_update_schema`;
|
|
1634
|
+
const formSchemaConstName = `${descriptor.tableConstName}_form_schema`;
|
|
1635
|
+
const relationEntries = Object.entries(descriptor.table.relations);
|
|
1636
|
+
const relationsAssignment = config.features.emitRelations && relationEntries.length > 0 ? `
|
|
1637
|
+
Object.assign(${descriptor.tableConstName}.meta, {
|
|
1638
|
+
relations: {
|
|
1639
|
+
${relationEntries.map(([relationKey2, relationValue]) => ` ${renderObjectKey(relationKey2)}: ${renderRelationLiteral(relationValue)}`).join(",\n")}
|
|
1640
|
+
}
|
|
1641
|
+
})
|
|
1642
|
+
` : "";
|
|
1643
|
+
const content = `import { ${helperImportLine} } from '@xylex-group/athena'
|
|
1644
|
+
import type { FormValuesOf, InsertOf, RowOf, UpdateOf } from '@xylex-group/athena'
|
|
1645
|
+
|
|
1646
|
+
export const ${descriptor.tableConstName} = table(${escapeStringLiteral(descriptor.tableName)})
|
|
1647
|
+
.schema(${escapeStringLiteral(descriptor.schemaName)})
|
|
1648
|
+
.columns({
|
|
1649
|
+
${columnLines}
|
|
1650
|
+
})
|
|
1651
|
+
.primaryKey(${descriptor.table.primaryKey.map((value) => escapeStringLiteral(value)).join(", ")})
|
|
1652
|
+
${relationsAssignment ? `${relationsAssignment}` : ""}
|
|
1653
|
+
export type ${descriptor.rowTypeName} = RowOf<typeof ${descriptor.tableConstName}>
|
|
1654
|
+
export type ${descriptor.insertTypeName} = InsertOf<typeof ${descriptor.tableConstName}>
|
|
1655
|
+
export type ${descriptor.updateTypeName} = UpdateOf<typeof ${descriptor.tableConstName}>
|
|
1656
|
+
export type ${descriptor.formValuesTypeName} = FormValuesOf<typeof ${descriptor.tableConstName}>
|
|
1657
|
+
|
|
1658
|
+
export const ${rowSchemaConstName} = ${descriptor.tableConstName}.schemas.row
|
|
1659
|
+
export const ${insertSchemaConstName} = ${descriptor.tableConstName}.schemas.insert
|
|
1660
|
+
export const ${updateSchemaConstName} = ${descriptor.tableConstName}.schemas.update
|
|
1661
|
+
export const ${formSchemaConstName} = ${descriptor.tableConstName}.schemas.form
|
|
1662
|
+
`;
|
|
1663
|
+
return {
|
|
1664
|
+
kind: "model",
|
|
1665
|
+
path: descriptor.filePath,
|
|
1666
|
+
content
|
|
1667
|
+
};
|
|
1668
|
+
}
|
|
1669
|
+
function generateTableBuilderArtifactsFromSnapshot(snapshot, config) {
|
|
1670
|
+
const normalizedConfig = "internal" in config ? config : normalizeGeneratorConfig(config);
|
|
1671
|
+
return composeGeneratorArtifacts({
|
|
1672
|
+
snapshot,
|
|
1673
|
+
config: normalizedConfig,
|
|
1674
|
+
createModelDescriptor({ providerName, databaseName, schemaName, tableName, table }) {
|
|
1675
|
+
const tableConstName = toSafeIdentifier(tableName, "preserve", "table");
|
|
1676
|
+
return {
|
|
1677
|
+
schemaName,
|
|
1678
|
+
tableName,
|
|
1679
|
+
filePath: resolveOutputPath(
|
|
1680
|
+
normalizedConfig.output.targets.model,
|
|
1681
|
+
{
|
|
1682
|
+
provider: providerName,
|
|
1683
|
+
kind: "model",
|
|
1684
|
+
database: databaseName,
|
|
1685
|
+
schema: schemaName,
|
|
1686
|
+
model: tableName
|
|
1687
|
+
},
|
|
1688
|
+
normalizedConfig
|
|
1689
|
+
),
|
|
1690
|
+
rowTypeName: `${toSafeIdentifier(`${schemaName} ${tableName}`, normalizedConfig.naming.modelType, "Model")}Row`,
|
|
1691
|
+
insertTypeName: `${toSafeIdentifier(`${schemaName} ${tableName}`, normalizedConfig.naming.modelType, "Model")}Insert`,
|
|
1692
|
+
updateTypeName: `${toSafeIdentifier(`${schemaName} ${tableName}`, normalizedConfig.naming.modelType, "Model")}Update`,
|
|
1693
|
+
formValuesTypeName: `${toSafeIdentifier(`${schemaName} ${tableName}`, normalizedConfig.naming.modelType, "Model")}FormValues`,
|
|
1694
|
+
tableConstName,
|
|
1695
|
+
exportConstName: tableConstName,
|
|
1696
|
+
table
|
|
1697
|
+
};
|
|
1698
|
+
},
|
|
1699
|
+
renderModelArtifact: (descriptor) => renderModelArtifact(descriptor, normalizedConfig)
|
|
1700
|
+
});
|
|
1701
|
+
}
|
|
1702
|
+
|
|
1703
|
+
// src/generator/renderer.ts
|
|
1704
|
+
function renderModelArtifact2(databaseName, descriptor, config) {
|
|
1705
|
+
const columnLines = Object.values(descriptor.table.columns).map((column) => {
|
|
1706
|
+
const propertyName = escapeTypePropertyName(column.name);
|
|
1707
|
+
const baseType = resolvePostgresColumnType(column);
|
|
1708
|
+
const isOptional = column.isNullable;
|
|
1709
|
+
const typeWithNullability = column.isNullable ? `${baseType} | null` : baseType;
|
|
1710
|
+
return ` ${propertyName}${isOptional ? "?" : ""}: ${typeWithNullability}`;
|
|
1711
|
+
}).join("\n");
|
|
1712
|
+
const nullableLines = Object.values(descriptor.table.columns).map((column) => ` ${renderObjectKey(column.name)}: ${column.isNullable ? "true" : "false"}`).join(",\n");
|
|
1713
|
+
const relationEntries = Object.entries(descriptor.table.relations);
|
|
1714
|
+
const relationBlock = config.features.emitRelations && relationEntries.length > 0 ? `,
|
|
1715
|
+
relations: {
|
|
1716
|
+
${relationEntries.map(([relationKey2, relationValue]) => ` ${renderObjectKey(relationKey2)}: ${renderRelationLiteral(relationValue)}`).join(",\n")}
|
|
1717
|
+
}` : "";
|
|
1718
|
+
const content = `import { defineModel } from '@xylex-group/athena'
|
|
1719
|
+
|
|
1720
|
+
export interface ${descriptor.rowTypeName} {
|
|
1721
|
+
${columnLines}
|
|
1722
|
+
}
|
|
1723
|
+
|
|
1724
|
+
export type ${descriptor.insertTypeName} = Partial<${descriptor.rowTypeName}>
|
|
1725
|
+
export type ${descriptor.updateTypeName} = Partial<${descriptor.insertTypeName}>
|
|
1726
|
+
|
|
1727
|
+
export const ${descriptor.modelConstName} = defineModel<${descriptor.rowTypeName}, ${descriptor.insertTypeName}, ${descriptor.updateTypeName}>({
|
|
1728
|
+
meta: {
|
|
1729
|
+
database: ${escapeStringLiteral(databaseName)},
|
|
1730
|
+
schema: ${escapeStringLiteral(descriptor.schemaName)},
|
|
1731
|
+
model: ${escapeStringLiteral(descriptor.tableName)},
|
|
1732
|
+
tableName: ${escapeStringLiteral(`${descriptor.schemaName}.${descriptor.tableName}`)},
|
|
1733
|
+
primaryKey: [${descriptor.table.primaryKey.map((value) => escapeStringLiteral(value)).join(", ")}],
|
|
1734
|
+
nullable: {
|
|
1735
|
+
${nullableLines}
|
|
1736
|
+
}${relationBlock}
|
|
1737
|
+
}
|
|
1738
|
+
})
|
|
1739
|
+
`;
|
|
1740
|
+
return {
|
|
1741
|
+
kind: "model",
|
|
1742
|
+
path: descriptor.filePath,
|
|
1743
|
+
content
|
|
1744
|
+
};
|
|
1745
|
+
}
|
|
1409
1746
|
function generateArtifactsFromSnapshot(snapshot, config) {
|
|
1410
|
-
const normalizedConfig = "
|
|
1411
|
-
|
|
1747
|
+
const normalizedConfig = "internal" in config ? config : normalizeGeneratorConfig(config);
|
|
1748
|
+
if (normalizedConfig.output.format === "table-builder") {
|
|
1749
|
+
return generateTableBuilderArtifactsFromSnapshot(snapshot, normalizedConfig);
|
|
1750
|
+
}
|
|
1751
|
+
return composeGeneratorArtifacts({
|
|
1752
|
+
snapshot,
|
|
1753
|
+
config: normalizedConfig,
|
|
1754
|
+
createModelDescriptor({ providerName, databaseName, schemaName, tableName, table }) {
|
|
1755
|
+
const modelConstName = toSafeIdentifier(
|
|
1756
|
+
`${schemaName} ${tableName} model`,
|
|
1757
|
+
normalizedConfig.naming.modelConst,
|
|
1758
|
+
"model"
|
|
1759
|
+
);
|
|
1760
|
+
return {
|
|
1761
|
+
schemaName,
|
|
1762
|
+
tableName,
|
|
1763
|
+
filePath: resolveOutputPath(
|
|
1764
|
+
normalizedConfig.output.targets.model,
|
|
1765
|
+
{
|
|
1766
|
+
provider: providerName,
|
|
1767
|
+
kind: "model",
|
|
1768
|
+
database: databaseName,
|
|
1769
|
+
schema: schemaName,
|
|
1770
|
+
model: tableName
|
|
1771
|
+
},
|
|
1772
|
+
normalizedConfig
|
|
1773
|
+
),
|
|
1774
|
+
rowTypeName: `${toSafeIdentifier(`${schemaName} ${tableName}`, normalizedConfig.naming.modelType, "Model")}Row`,
|
|
1775
|
+
insertTypeName: `${toSafeIdentifier(`${schemaName} ${tableName}`, normalizedConfig.naming.modelType, "Model")}Insert`,
|
|
1776
|
+
updateTypeName: `${toSafeIdentifier(`${schemaName} ${tableName}`, normalizedConfig.naming.modelType, "Model")}Update`,
|
|
1777
|
+
modelConstName,
|
|
1778
|
+
exportConstName: modelConstName,
|
|
1779
|
+
table
|
|
1780
|
+
};
|
|
1781
|
+
},
|
|
1782
|
+
renderModelArtifact: (descriptor) => renderModelArtifact2(snapshot.database, descriptor, normalizedConfig)
|
|
1783
|
+
});
|
|
1412
1784
|
}
|
|
1413
1785
|
|
|
1414
1786
|
// src/gateway/url.ts
|
|
@@ -1497,16 +1869,23 @@ var getSessionCookie = (request, config) => {
|
|
|
1497
1869
|
const { cookieName = "session_token", cookiePrefix = "athena-auth" } = {};
|
|
1498
1870
|
const parsedCookie = parseCookies(cookies);
|
|
1499
1871
|
const getCookie = (name) => parsedCookie.get(name) || parsedCookie.get(`${SECURE_COOKIE_PREFIX}${name}`);
|
|
1500
|
-
const
|
|
1501
|
-
|
|
1502
|
-
|
|
1872
|
+
const candidateCookieNames = Array.from(/* @__PURE__ */ new Set([
|
|
1873
|
+
cookieName,
|
|
1874
|
+
cookieName.replace(/_/g, "-"),
|
|
1875
|
+
cookieName.replace(/-/g, "_")
|
|
1876
|
+
])).filter(Boolean);
|
|
1877
|
+
for (const candidateName of candidateCookieNames) {
|
|
1878
|
+
const sessionToken = getCookie(`${cookiePrefix}.${candidateName}`) || getCookie(`${cookiePrefix}-${candidateName}`);
|
|
1879
|
+
if (sessionToken) {
|
|
1880
|
+
return sessionToken;
|
|
1881
|
+
}
|
|
1503
1882
|
}
|
|
1504
1883
|
return null;
|
|
1505
1884
|
};
|
|
1506
1885
|
|
|
1507
1886
|
// package.json
|
|
1508
1887
|
var package_default = {
|
|
1509
|
-
version: "2.
|
|
1888
|
+
version: "2.8.0"
|
|
1510
1889
|
};
|
|
1511
1890
|
|
|
1512
1891
|
// src/sdk-version.ts
|
|
@@ -3453,11 +3832,12 @@ function createAuthClient(config = {}) {
|
|
|
3453
3832
|
// src/db/module.ts
|
|
3454
3833
|
function createDbModule(input) {
|
|
3455
3834
|
const db = {
|
|
3456
|
-
from
|
|
3457
|
-
|
|
3458
|
-
|
|
3459
|
-
|
|
3460
|
-
|
|
3835
|
+
from: input.from,
|
|
3836
|
+
select(table, first, second) {
|
|
3837
|
+
if (first && typeof first === "object" && !Array.isArray(first)) {
|
|
3838
|
+
return input.from(table).select(void 0, first);
|
|
3839
|
+
}
|
|
3840
|
+
return input.from(table).select(first, second);
|
|
3461
3841
|
},
|
|
3462
3842
|
insert(table, values, options) {
|
|
3463
3843
|
return Array.isArray(values) ? input.from(table).insert(values, options) : input.from(table).insert(values, options);
|
|
@@ -3481,6 +3861,344 @@ function createDbModule(input) {
|
|
|
3481
3861
|
return db;
|
|
3482
3862
|
}
|
|
3483
3863
|
|
|
3864
|
+
// src/storage/file.ts
|
|
3865
|
+
function createStorageFileModule(base, config = {}) {
|
|
3866
|
+
const upload = async (input, options) => {
|
|
3867
|
+
const sources = normalizeUploadSources(input);
|
|
3868
|
+
validateUploadConstraints(sources, input);
|
|
3869
|
+
const uploadRequests = sources.map((source, index) => {
|
|
3870
|
+
const storageKey = resolveUploadStorageKey(input, source, index, options, config);
|
|
3871
|
+
return {
|
|
3872
|
+
source,
|
|
3873
|
+
uploadRequest: {
|
|
3874
|
+
s3_id: input.s3_id,
|
|
3875
|
+
bucket: input.bucket,
|
|
3876
|
+
storage_key: storageKey,
|
|
3877
|
+
name: input.name ?? source.fileName,
|
|
3878
|
+
original_name: input.original_name ?? source.fileName,
|
|
3879
|
+
resource_id: input.resource_id ?? input.resourceId,
|
|
3880
|
+
mime_type: input.mime_type ?? source.contentType,
|
|
3881
|
+
content_type: input.content_type ?? source.contentType,
|
|
3882
|
+
size_bytes: source.sizeBytes,
|
|
3883
|
+
public: input.public,
|
|
3884
|
+
metadata: input.metadata
|
|
3885
|
+
}
|
|
3886
|
+
};
|
|
3887
|
+
});
|
|
3888
|
+
input.onProgress?.(createProgressSnapshot("preparing", sources, 0, 0, 0));
|
|
3889
|
+
const uploadUrls = uploadRequests.length === 1 ? [await base.createStorageUploadUrl(uploadRequests[0].uploadRequest, options)] : (await base.createStorageUploadUrls({ files: uploadRequests.map((request) => request.uploadRequest) }, options)).files;
|
|
3890
|
+
const aggregateLoaded = new Array(uploadRequests.length).fill(0);
|
|
3891
|
+
const uploaded = [];
|
|
3892
|
+
for (let index = 0; index < uploadRequests.length; index += 1) {
|
|
3893
|
+
const request = uploadRequests[index];
|
|
3894
|
+
const uploadUrl = uploadUrls[index];
|
|
3895
|
+
const response = await putUploadBody(uploadUrl.upload.url, request.source, input, options, (progress) => {
|
|
3896
|
+
aggregateLoaded[index] = progress.loaded;
|
|
3897
|
+
input.onProgress?.(createProgressSnapshot("uploading", sources, index, progress.loaded, sum(aggregateLoaded)));
|
|
3898
|
+
});
|
|
3899
|
+
uploaded.push({
|
|
3900
|
+
file: uploadUrl.file,
|
|
3901
|
+
upload: uploadUrl.upload,
|
|
3902
|
+
source: request.source.source,
|
|
3903
|
+
fileName: request.source.fileName,
|
|
3904
|
+
storage_key: request.uploadRequest.storage_key,
|
|
3905
|
+
response
|
|
3906
|
+
});
|
|
3907
|
+
aggregateLoaded[index] = request.source.sizeBytes;
|
|
3908
|
+
input.onProgress?.(createProgressSnapshot("complete", sources, index, request.source.sizeBytes, sum(aggregateLoaded)));
|
|
3909
|
+
}
|
|
3910
|
+
return {
|
|
3911
|
+
files: uploaded,
|
|
3912
|
+
count: uploaded.length
|
|
3913
|
+
};
|
|
3914
|
+
};
|
|
3915
|
+
const download = ((input, queryOrOptions, maybeOptions) => {
|
|
3916
|
+
const { fileIds, query, options } = normalizeDownloadArgs(input, queryOrOptions, maybeOptions);
|
|
3917
|
+
const downloads = fileIds.map((fileId) => base.getStorageFileProxy(fileId, query, options));
|
|
3918
|
+
return Array.isArray(input) || isRecord5(input) && Array.isArray(input.fileIds) ? Promise.all(downloads) : downloads[0];
|
|
3919
|
+
});
|
|
3920
|
+
const deleteFile = ((input, options) => {
|
|
3921
|
+
if (Array.isArray(input)) {
|
|
3922
|
+
return Promise.all(input.map((fileId) => base.deleteStorageFile(fileId, options)));
|
|
3923
|
+
}
|
|
3924
|
+
return base.deleteStorageFile(input, options);
|
|
3925
|
+
});
|
|
3926
|
+
return {
|
|
3927
|
+
upload,
|
|
3928
|
+
download,
|
|
3929
|
+
list(input, options) {
|
|
3930
|
+
const prefix = resolveStoragePath(input.prefix ?? "", input, options, config);
|
|
3931
|
+
return base.listStorageFiles(
|
|
3932
|
+
{
|
|
3933
|
+
s3_id: input.s3_id,
|
|
3934
|
+
prefix
|
|
3935
|
+
},
|
|
3936
|
+
options
|
|
3937
|
+
);
|
|
3938
|
+
},
|
|
3939
|
+
delete: deleteFile
|
|
3940
|
+
};
|
|
3941
|
+
}
|
|
3942
|
+
function resolveStoragePath(path, input, options, config = {}) {
|
|
3943
|
+
const context = createPathContext(input, options, config);
|
|
3944
|
+
const prefixPath = input.prefixPath ?? config.prefixPath;
|
|
3945
|
+
const prefix = typeof prefixPath === "function" ? prefixPath(context) : prefixPath;
|
|
3946
|
+
return joinStoragePath(renderStorageTemplate(prefix ?? "", context), renderStorageTemplate(path, context));
|
|
3947
|
+
}
|
|
3948
|
+
function resolveUploadStorageKey(input, source, index, options, config) {
|
|
3949
|
+
const explicitKey = input.storage_key ?? input.storageKey;
|
|
3950
|
+
const keyTemplate = input.storageKeyTemplate;
|
|
3951
|
+
const fallbackName = source.fileName;
|
|
3952
|
+
const context = createPathContext(input, options, config);
|
|
3953
|
+
const key = keyTemplate ? renderStorageTemplate(keyTemplate, {
|
|
3954
|
+
...context,
|
|
3955
|
+
vars: {
|
|
3956
|
+
...context.vars,
|
|
3957
|
+
index,
|
|
3958
|
+
fileName: source.fileName,
|
|
3959
|
+
name: source.fileName
|
|
3960
|
+
}
|
|
3961
|
+
}) : explicitKey ?? fallbackName;
|
|
3962
|
+
return resolveStoragePath(key, input, options, config);
|
|
3963
|
+
}
|
|
3964
|
+
function normalizeUploadSources(input) {
|
|
3965
|
+
const files = toArray(input.files);
|
|
3966
|
+
if (files.length === 0) {
|
|
3967
|
+
throw new Error("athena.storage.file.upload requires at least one file");
|
|
3968
|
+
}
|
|
3969
|
+
return files.map((source, index) => {
|
|
3970
|
+
const fileName = input.fileName ?? sourceName(source) ?? `file-${index + 1}`;
|
|
3971
|
+
const sizeBytes = sourceSize(source);
|
|
3972
|
+
const contentType = input.content_type ?? input.mime_type ?? sourceContentType(source);
|
|
3973
|
+
return {
|
|
3974
|
+
source,
|
|
3975
|
+
fileName,
|
|
3976
|
+
sizeBytes,
|
|
3977
|
+
contentType
|
|
3978
|
+
};
|
|
3979
|
+
});
|
|
3980
|
+
}
|
|
3981
|
+
function validateUploadConstraints(sources, input) {
|
|
3982
|
+
const maxFiles = input.maxFiles ?? 1;
|
|
3983
|
+
if (sources.length > maxFiles) {
|
|
3984
|
+
throw new Error(`athena.storage.file.upload accepts at most ${maxFiles} file${maxFiles === 1 ? "" : "s"} for this call`);
|
|
3985
|
+
}
|
|
3986
|
+
const maxFileSizeBytes = input.maxFileSizeBytes ?? (input.maxFileSizeMb === void 0 ? void 0 : Math.floor(input.maxFileSizeMb * 1024 * 1024));
|
|
3987
|
+
if (maxFileSizeBytes !== void 0) {
|
|
3988
|
+
const tooLarge = sources.find((source) => source.sizeBytes > maxFileSizeBytes);
|
|
3989
|
+
if (tooLarge) {
|
|
3990
|
+
throw new Error(`athena.storage.file.upload rejected ${tooLarge.fileName}: file exceeds ${maxFileSizeBytes} bytes`);
|
|
3991
|
+
}
|
|
3992
|
+
}
|
|
3993
|
+
const allowedExtensions = normalizeExtensions(input.allowedExtensions ?? input.extensions);
|
|
3994
|
+
if (allowedExtensions.size > 0) {
|
|
3995
|
+
const invalid = sources.find((source) => !allowedExtensions.has(fileExtension(source.fileName)));
|
|
3996
|
+
if (invalid) {
|
|
3997
|
+
throw new Error(`athena.storage.file.upload rejected ${invalid.fileName}: extension is not allowed`);
|
|
3998
|
+
}
|
|
3999
|
+
}
|
|
4000
|
+
}
|
|
4001
|
+
async function putUploadBody(url, source, input, options, onProgress) {
|
|
4002
|
+
const headers = new Headers(input.uploadHeaders);
|
|
4003
|
+
if (source.contentType && !headers.has("Content-Type")) {
|
|
4004
|
+
headers.set("Content-Type", source.contentType);
|
|
4005
|
+
}
|
|
4006
|
+
if (typeof XMLHttpRequest !== "undefined") {
|
|
4007
|
+
return putUploadBodyWithXhr(url, source, headers, options, onProgress);
|
|
4008
|
+
}
|
|
4009
|
+
onProgress({ loaded: 0 });
|
|
4010
|
+
const response = await fetch(url, {
|
|
4011
|
+
method: "PUT",
|
|
4012
|
+
headers,
|
|
4013
|
+
body: source.source,
|
|
4014
|
+
signal: options?.signal
|
|
4015
|
+
});
|
|
4016
|
+
if (!response.ok) {
|
|
4017
|
+
throw new Error(`athena.storage.file.upload failed with status ${response.status}`);
|
|
4018
|
+
}
|
|
4019
|
+
onProgress({ loaded: source.sizeBytes });
|
|
4020
|
+
return response;
|
|
4021
|
+
}
|
|
4022
|
+
function putUploadBodyWithXhr(url, source, headers, options, onProgress) {
|
|
4023
|
+
const Xhr = XMLHttpRequest;
|
|
4024
|
+
if (Xhr === void 0) {
|
|
4025
|
+
return Promise.reject(new Error("athena.storage.file.upload requires XMLHttpRequest in this runtime"));
|
|
4026
|
+
}
|
|
4027
|
+
return new Promise((resolve3, reject) => {
|
|
4028
|
+
const xhr = new Xhr();
|
|
4029
|
+
const abort = () => xhr.abort();
|
|
4030
|
+
xhr.open("PUT", url);
|
|
4031
|
+
headers.forEach((value, key) => xhr.setRequestHeader(key, value));
|
|
4032
|
+
xhr.upload.onprogress = (event) => {
|
|
4033
|
+
onProgress({ loaded: event.loaded });
|
|
4034
|
+
};
|
|
4035
|
+
xhr.onload = () => {
|
|
4036
|
+
if (options?.signal) {
|
|
4037
|
+
options.signal.removeEventListener("abort", abort);
|
|
4038
|
+
}
|
|
4039
|
+
if (xhr.status < 200 || xhr.status >= 300) {
|
|
4040
|
+
reject(new Error(`athena.storage.file.upload failed with status ${xhr.status}`));
|
|
4041
|
+
return;
|
|
4042
|
+
}
|
|
4043
|
+
onProgress({ loaded: source.sizeBytes });
|
|
4044
|
+
resolve3(new Response(xhr.response, {
|
|
4045
|
+
status: xhr.status,
|
|
4046
|
+
statusText: xhr.statusText,
|
|
4047
|
+
headers: parseXhrHeaders(xhr.getAllResponseHeaders())
|
|
4048
|
+
}));
|
|
4049
|
+
};
|
|
4050
|
+
xhr.onerror = () => {
|
|
4051
|
+
if (options?.signal) {
|
|
4052
|
+
options.signal.removeEventListener("abort", abort);
|
|
4053
|
+
}
|
|
4054
|
+
reject(new Error("athena.storage.file.upload failed with a network error"));
|
|
4055
|
+
};
|
|
4056
|
+
xhr.onabort = () => {
|
|
4057
|
+
if (options?.signal) {
|
|
4058
|
+
options.signal.removeEventListener("abort", abort);
|
|
4059
|
+
}
|
|
4060
|
+
reject(new DOMException("Upload aborted", "AbortError"));
|
|
4061
|
+
};
|
|
4062
|
+
if (options?.signal) {
|
|
4063
|
+
if (options.signal.aborted) {
|
|
4064
|
+
abort();
|
|
4065
|
+
return;
|
|
4066
|
+
}
|
|
4067
|
+
options.signal.addEventListener("abort", abort, { once: true });
|
|
4068
|
+
}
|
|
4069
|
+
xhr.send(source.source);
|
|
4070
|
+
});
|
|
4071
|
+
}
|
|
4072
|
+
function normalizeDownloadArgs(input, queryOrOptions, maybeOptions) {
|
|
4073
|
+
if (typeof input === "string") {
|
|
4074
|
+
return { fileIds: [input], query: queryOrOptions, options: maybeOptions };
|
|
4075
|
+
}
|
|
4076
|
+
if (Array.isArray(input)) {
|
|
4077
|
+
return { fileIds: [...input], query: queryOrOptions, options: maybeOptions };
|
|
4078
|
+
}
|
|
4079
|
+
const downloadInput = input;
|
|
4080
|
+
const { fileId, fileIds, ...query } = downloadInput;
|
|
4081
|
+
return {
|
|
4082
|
+
fileIds: fileIds ? [...fileIds] : fileId ? [fileId] : [],
|
|
4083
|
+
query,
|
|
4084
|
+
options: queryOrOptions
|
|
4085
|
+
};
|
|
4086
|
+
}
|
|
4087
|
+
function createPathContext(input, options, config) {
|
|
4088
|
+
const organizationId = input.organizationId ?? input.organization_id ?? options?.organizationId ?? void 0;
|
|
4089
|
+
const userId = input.userId ?? input.user_id ?? options?.userId ?? void 0;
|
|
4090
|
+
const resourceId = input.resourceId ?? input.resource_id ?? void 0;
|
|
4091
|
+
const vars = {
|
|
4092
|
+
...config.vars ?? {},
|
|
4093
|
+
...input.vars ?? {}
|
|
4094
|
+
};
|
|
4095
|
+
if (organizationId !== void 0) {
|
|
4096
|
+
vars.organizationId = organizationId;
|
|
4097
|
+
vars.organization_id = organizationId;
|
|
4098
|
+
}
|
|
4099
|
+
if (userId !== void 0) {
|
|
4100
|
+
vars.userId = userId;
|
|
4101
|
+
vars.user_id = userId;
|
|
4102
|
+
}
|
|
4103
|
+
if (resourceId !== void 0) {
|
|
4104
|
+
vars.resourceId = resourceId;
|
|
4105
|
+
vars.resource_id = resourceId;
|
|
4106
|
+
}
|
|
4107
|
+
return {
|
|
4108
|
+
vars,
|
|
4109
|
+
env: {
|
|
4110
|
+
...readProcessEnv(),
|
|
4111
|
+
...config.env ?? {},
|
|
4112
|
+
...input.env ?? {}
|
|
4113
|
+
},
|
|
4114
|
+
organizationId,
|
|
4115
|
+
organization_id: organizationId,
|
|
4116
|
+
userId,
|
|
4117
|
+
user_id: userId,
|
|
4118
|
+
resourceId,
|
|
4119
|
+
resource_id: resourceId
|
|
4120
|
+
};
|
|
4121
|
+
}
|
|
4122
|
+
function renderStorageTemplate(template, context) {
|
|
4123
|
+
return template.replace(/\$\{([^}]+)\}|\{([^}]+)\}/g, (_match, shellToken, braceToken) => {
|
|
4124
|
+
const token = (shellToken ?? braceToken ?? "").trim();
|
|
4125
|
+
if (!token) return "";
|
|
4126
|
+
const value = resolveTemplateToken(token, context);
|
|
4127
|
+
return value === void 0 || value === null ? "" : String(value);
|
|
4128
|
+
});
|
|
4129
|
+
}
|
|
4130
|
+
function resolveTemplateToken(token, context) {
|
|
4131
|
+
if (token.startsWith("env.")) {
|
|
4132
|
+
return context.env[token.slice(4)];
|
|
4133
|
+
}
|
|
4134
|
+
if (token in context.vars) {
|
|
4135
|
+
return context.vars[token];
|
|
4136
|
+
}
|
|
4137
|
+
return context.env[token];
|
|
4138
|
+
}
|
|
4139
|
+
function joinStoragePath(...parts) {
|
|
4140
|
+
return parts.map((part) => part.trim().replace(/^\/+|\/+$/g, "")).filter(Boolean).join("/");
|
|
4141
|
+
}
|
|
4142
|
+
function toArray(files) {
|
|
4143
|
+
if (isUploadSource(files)) return [files];
|
|
4144
|
+
return Array.from(files);
|
|
4145
|
+
}
|
|
4146
|
+
function isUploadSource(value) {
|
|
4147
|
+
return value instanceof Blob || value instanceof ArrayBuffer || value instanceof Uint8Array;
|
|
4148
|
+
}
|
|
4149
|
+
function sourceName(source) {
|
|
4150
|
+
return isRecord5(source) && typeof source.name === "string" && source.name.trim() ? source.name.trim() : void 0;
|
|
4151
|
+
}
|
|
4152
|
+
function sourceSize(source) {
|
|
4153
|
+
if (source instanceof Blob) return source.size;
|
|
4154
|
+
return source.byteLength;
|
|
4155
|
+
}
|
|
4156
|
+
function sourceContentType(source) {
|
|
4157
|
+
return source instanceof Blob && source.type.trim() ? source.type.trim() : void 0;
|
|
4158
|
+
}
|
|
4159
|
+
function normalizeExtensions(extensions) {
|
|
4160
|
+
return new Set((extensions ?? []).map((extension) => extension.replace(/^\./, "").toLowerCase()).filter(Boolean));
|
|
4161
|
+
}
|
|
4162
|
+
function fileExtension(fileName) {
|
|
4163
|
+
const lastDot = fileName.lastIndexOf(".");
|
|
4164
|
+
return lastDot === -1 ? "" : fileName.slice(lastDot + 1).toLowerCase();
|
|
4165
|
+
}
|
|
4166
|
+
function createProgressSnapshot(phase, sources, fileIndex, loaded, aggregateLoaded) {
|
|
4167
|
+
const total = sources[fileIndex]?.sizeBytes ?? 0;
|
|
4168
|
+
const aggregateTotal = sources.reduce((totalBytes, source) => totalBytes + source.sizeBytes, 0);
|
|
4169
|
+
return {
|
|
4170
|
+
phase,
|
|
4171
|
+
fileIndex,
|
|
4172
|
+
fileCount: sources.length,
|
|
4173
|
+
fileName: sources[fileIndex]?.fileName ?? "",
|
|
4174
|
+
loaded,
|
|
4175
|
+
total,
|
|
4176
|
+
percent: total > 0 ? Math.round(loaded / total * 100) : 100,
|
|
4177
|
+
aggregateLoaded,
|
|
4178
|
+
aggregateTotal,
|
|
4179
|
+
aggregatePercent: aggregateTotal > 0 ? Math.round(aggregateLoaded / aggregateTotal * 100) : 100
|
|
4180
|
+
};
|
|
4181
|
+
}
|
|
4182
|
+
function sum(values) {
|
|
4183
|
+
return values.reduce((total, value) => total + value, 0);
|
|
4184
|
+
}
|
|
4185
|
+
function parseXhrHeaders(raw) {
|
|
4186
|
+
const headers = new Headers();
|
|
4187
|
+
for (const line of raw.trim().split(/[\r\n]+/)) {
|
|
4188
|
+
const index = line.indexOf(":");
|
|
4189
|
+
if (index === -1) continue;
|
|
4190
|
+
headers.set(line.slice(0, index).trim(), line.slice(index + 1).trim());
|
|
4191
|
+
}
|
|
4192
|
+
return headers;
|
|
4193
|
+
}
|
|
4194
|
+
function readProcessEnv() {
|
|
4195
|
+
const processLike = globalThis.process;
|
|
4196
|
+
return processLike?.env ?? {};
|
|
4197
|
+
}
|
|
4198
|
+
function isRecord5(value) {
|
|
4199
|
+
return Boolean(value) && typeof value === "object";
|
|
4200
|
+
}
|
|
4201
|
+
|
|
3484
4202
|
// src/storage/module.ts
|
|
3485
4203
|
var storageSdkManifest = {
|
|
3486
4204
|
methods: [
|
|
@@ -3675,7 +4393,7 @@ var AthenaStorageError = class extends Error {
|
|
|
3675
4393
|
};
|
|
3676
4394
|
}
|
|
3677
4395
|
};
|
|
3678
|
-
function
|
|
4396
|
+
function isRecord6(value) {
|
|
3679
4397
|
return Boolean(value) && typeof value === "object" && !Array.isArray(value);
|
|
3680
4398
|
}
|
|
3681
4399
|
function causeToString(cause) {
|
|
@@ -3786,11 +4504,20 @@ function appendQuery(path, query) {
|
|
|
3786
4504
|
function storagePath(path) {
|
|
3787
4505
|
return path;
|
|
3788
4506
|
}
|
|
4507
|
+
function resolveStorageEndpointPath(endpoint, runtimeOptions) {
|
|
4508
|
+
if (!runtimeOptions?.stripBasePath) {
|
|
4509
|
+
return endpoint;
|
|
4510
|
+
}
|
|
4511
|
+
const [pathname, queryText] = String(endpoint).split("?", 2);
|
|
4512
|
+
const trimmedPathname = pathname.startsWith("/storage/") ? pathname.slice("/storage".length) : pathname === "/storage" ? "/" : pathname;
|
|
4513
|
+
const resolvedPath = trimmedPathname.startsWith("/") ? trimmedPathname : `/${trimmedPathname}`;
|
|
4514
|
+
return storagePath(queryText ? `${resolvedPath}?${queryText}` : resolvedPath);
|
|
4515
|
+
}
|
|
3789
4516
|
function withPathParam(path, name, value) {
|
|
3790
4517
|
return path.replace(`{${name}}`, encodeURIComponent(value));
|
|
3791
4518
|
}
|
|
3792
4519
|
function resolveErrorMessage3(payload, fallback) {
|
|
3793
|
-
if (
|
|
4520
|
+
if (isRecord6(payload)) {
|
|
3794
4521
|
const message = payload.message ?? payload.error ?? payload.details;
|
|
3795
4522
|
if (typeof message === "string" && message.trim()) {
|
|
3796
4523
|
return message.trim();
|
|
@@ -3802,12 +4529,12 @@ function resolveErrorMessage3(payload, fallback) {
|
|
|
3802
4529
|
return fallback;
|
|
3803
4530
|
}
|
|
3804
4531
|
function resolveErrorHint2(payload) {
|
|
3805
|
-
if (!
|
|
4532
|
+
if (!isRecord6(payload)) return void 0;
|
|
3806
4533
|
const hint = payload.hint ?? payload.suggestion;
|
|
3807
4534
|
return typeof hint === "string" && hint.trim() ? hint.trim() : void 0;
|
|
3808
4535
|
}
|
|
3809
4536
|
function resolveErrorCause(payload) {
|
|
3810
|
-
if (!
|
|
4537
|
+
if (!isRecord6(payload)) return void 0;
|
|
3811
4538
|
const cause = payload.cause ?? payload.reason;
|
|
3812
4539
|
return typeof cause === "string" && cause.trim() ? cause.trim() : void 0;
|
|
3813
4540
|
}
|
|
@@ -3824,8 +4551,8 @@ async function callStorageEndpoint(gateway, endpoint, method, envelope, payload,
|
|
|
3824
4551
|
let url;
|
|
3825
4552
|
let headers;
|
|
3826
4553
|
try {
|
|
3827
|
-
const baseUrl = options?.baseUrl ? normalizeAthenaGatewayBaseUrl(options.baseUrl) : gateway.baseUrl;
|
|
3828
|
-
url = buildAthenaGatewayUrl(baseUrl, endpoint);
|
|
4554
|
+
const baseUrl = options?.baseUrl ? normalizeAthenaGatewayBaseUrl(options.baseUrl) : runtimeOptions?.baseUrl ? normalizeAthenaGatewayBaseUrl(runtimeOptions.baseUrl) : gateway.baseUrl;
|
|
4555
|
+
url = buildAthenaGatewayUrl(baseUrl, resolveStorageEndpointPath(endpoint, runtimeOptions));
|
|
3829
4556
|
headers = gateway.buildHeaders(options);
|
|
3830
4557
|
} catch (error) {
|
|
3831
4558
|
return rejectStorageError(
|
|
@@ -3926,7 +4653,7 @@ async function callStorageEndpoint(gateway, endpoint, method, envelope, payload,
|
|
|
3926
4653
|
);
|
|
3927
4654
|
}
|
|
3928
4655
|
if (envelope === "athena") {
|
|
3929
|
-
if (!
|
|
4656
|
+
if (!isRecord6(parsedBody.parsed) || !("data" in parsedBody.parsed)) {
|
|
3930
4657
|
return rejectStorageError(
|
|
3931
4658
|
{
|
|
3932
4659
|
code: "INVALID_ATHENA_ENVELOPE",
|
|
@@ -3949,8 +4676,8 @@ async function callStorageBinaryEndpoint(gateway, endpoint, method, options, run
|
|
|
3949
4676
|
let url;
|
|
3950
4677
|
let headers;
|
|
3951
4678
|
try {
|
|
3952
|
-
const baseUrl = options?.baseUrl ? normalizeAthenaGatewayBaseUrl(options.baseUrl) : gateway.baseUrl;
|
|
3953
|
-
url = buildAthenaGatewayUrl(baseUrl, endpoint);
|
|
4679
|
+
const baseUrl = options?.baseUrl ? normalizeAthenaGatewayBaseUrl(options.baseUrl) : runtimeOptions?.baseUrl ? normalizeAthenaGatewayBaseUrl(runtimeOptions.baseUrl) : gateway.baseUrl;
|
|
4680
|
+
url = buildAthenaGatewayUrl(baseUrl, resolveStorageEndpointPath(endpoint, runtimeOptions));
|
|
3954
4681
|
headers = gateway.buildHeaders(options);
|
|
3955
4682
|
} catch (error) {
|
|
3956
4683
|
return rejectStorageError(
|
|
@@ -4034,129 +4761,515 @@ async function callStorageBinaryEndpoint(gateway, endpoint, method, options, run
|
|
|
4034
4761
|
runtimeOptions
|
|
4035
4762
|
);
|
|
4036
4763
|
}
|
|
4037
|
-
function
|
|
4764
|
+
function isBlobBody(body) {
|
|
4765
|
+
return typeof Blob !== "undefined" && body instanceof Blob;
|
|
4766
|
+
}
|
|
4767
|
+
function isReadableStreamBody(body) {
|
|
4768
|
+
return typeof ReadableStream !== "undefined" && body instanceof ReadableStream;
|
|
4769
|
+
}
|
|
4770
|
+
async function putPresignedUploadBody(uploadUrl, uploadHeaders, body, options) {
|
|
4771
|
+
const headers = new Headers(uploadHeaders);
|
|
4772
|
+
Object.entries(options?.headers ?? {}).forEach(([key, value]) => headers.set(key, value));
|
|
4773
|
+
if (!headers.has("Content-Type") && isBlobBody(body) && body.type) {
|
|
4774
|
+
headers.set("Content-Type", body.type);
|
|
4775
|
+
}
|
|
4776
|
+
const init = {
|
|
4777
|
+
method: "PUT",
|
|
4778
|
+
headers,
|
|
4779
|
+
body,
|
|
4780
|
+
signal: options?.signal
|
|
4781
|
+
};
|
|
4782
|
+
if (isReadableStreamBody(body)) {
|
|
4783
|
+
init.duplex = "half";
|
|
4784
|
+
}
|
|
4785
|
+
return fetch(uploadUrl, init);
|
|
4786
|
+
}
|
|
4787
|
+
function attachManagedUpload(upload) {
|
|
4788
|
+
const headers = {};
|
|
4038
4789
|
return {
|
|
4039
|
-
|
|
4040
|
-
|
|
4041
|
-
|
|
4042
|
-
|
|
4043
|
-
|
|
4044
|
-
|
|
4045
|
-
|
|
4046
|
-
|
|
4047
|
-
|
|
4048
|
-
|
|
4049
|
-
|
|
4050
|
-
|
|
4051
|
-
|
|
4052
|
-
|
|
4053
|
-
|
|
4054
|
-
|
|
4055
|
-
|
|
4056
|
-
|
|
4057
|
-
|
|
4058
|
-
|
|
4059
|
-
|
|
4060
|
-
|
|
4061
|
-
|
|
4062
|
-
|
|
4063
|
-
|
|
4064
|
-
|
|
4065
|
-
|
|
4790
|
+
...upload,
|
|
4791
|
+
method: "PUT",
|
|
4792
|
+
headers,
|
|
4793
|
+
expiresAt: upload.expires_at,
|
|
4794
|
+
put(body, options) {
|
|
4795
|
+
return putPresignedUploadBody(upload.url, headers, body, options);
|
|
4796
|
+
}
|
|
4797
|
+
};
|
|
4798
|
+
}
|
|
4799
|
+
function attachUploadHelper(response) {
|
|
4800
|
+
return {
|
|
4801
|
+
...response,
|
|
4802
|
+
upload: attachManagedUpload(response.upload)
|
|
4803
|
+
};
|
|
4804
|
+
}
|
|
4805
|
+
function attachUploadHelpers(response) {
|
|
4806
|
+
return {
|
|
4807
|
+
files: response.files.map(attachUploadHelper)
|
|
4808
|
+
};
|
|
4809
|
+
}
|
|
4810
|
+
function normalizeUploadUrlRequest(input) {
|
|
4811
|
+
const s3_id = input.s3_id ?? input.s3Id;
|
|
4812
|
+
const storage_key = input.storage_key ?? input.storageKey;
|
|
4813
|
+
if (!s3_id?.trim()) {
|
|
4814
|
+
throw new Error("athena.storage.file.upload requires s3_id or s3Id");
|
|
4815
|
+
}
|
|
4816
|
+
if (!storage_key?.trim()) {
|
|
4817
|
+
throw new Error("athena.storage.file.upload requires storage_key or storageKey");
|
|
4818
|
+
}
|
|
4819
|
+
const fileName = input.fileName?.trim();
|
|
4820
|
+
const originalName = input.originalName?.trim();
|
|
4821
|
+
return {
|
|
4822
|
+
s3_id,
|
|
4823
|
+
bucket: input.bucket,
|
|
4824
|
+
storage_key,
|
|
4825
|
+
name: input.name ?? fileName,
|
|
4826
|
+
original_name: input.original_name ?? originalName ?? fileName,
|
|
4827
|
+
resource_id: input.resource_id ?? input.resourceId,
|
|
4828
|
+
mime_type: input.mime_type ?? input.mimeType,
|
|
4829
|
+
content_type: input.content_type ?? input.contentType,
|
|
4830
|
+
size_bytes: input.size_bytes ?? input.sizeBytes,
|
|
4831
|
+
file_id: input.file_id ?? input.fileId,
|
|
4832
|
+
public: input.public,
|
|
4833
|
+
visibility: input.visibility,
|
|
4834
|
+
metadata: input.metadata
|
|
4835
|
+
};
|
|
4836
|
+
}
|
|
4837
|
+
async function callStorageUploadBinaryEndpoint(gateway, endpoint, body, options, runtimeOptions) {
|
|
4838
|
+
let url;
|
|
4839
|
+
let headers;
|
|
4840
|
+
try {
|
|
4841
|
+
const baseUrl = options?.baseUrl ? normalizeAthenaGatewayBaseUrl(options.baseUrl) : runtimeOptions?.baseUrl ? normalizeAthenaGatewayBaseUrl(runtimeOptions.baseUrl) : gateway.baseUrl;
|
|
4842
|
+
url = buildAthenaGatewayUrl(baseUrl, resolveStorageEndpointPath(endpoint, runtimeOptions));
|
|
4843
|
+
headers = gateway.buildHeaders(options);
|
|
4844
|
+
} catch (error) {
|
|
4845
|
+
return rejectStorageError(
|
|
4846
|
+
{
|
|
4847
|
+
code: storageCodeFromUnknown(error),
|
|
4848
|
+
message: error instanceof Error ? error.message : `Athena storage PUT ${endpoint} failed before sending the request`,
|
|
4849
|
+
status: isAthenaGatewayError(error) ? error.status : 0,
|
|
4850
|
+
endpoint,
|
|
4851
|
+
method: "PUT",
|
|
4852
|
+
raw: error,
|
|
4853
|
+
requestId: isAthenaGatewayError(error) ? error.requestId : void 0,
|
|
4854
|
+
hint: isAthenaGatewayError(error) ? error.hint : void 0,
|
|
4855
|
+
cause: error
|
|
4856
|
+
},
|
|
4857
|
+
options,
|
|
4858
|
+
runtimeOptions
|
|
4859
|
+
);
|
|
4860
|
+
}
|
|
4861
|
+
delete headers["Content-Type"];
|
|
4862
|
+
delete headers["content-type"];
|
|
4863
|
+
if (isBlobBody(body) && body.type) {
|
|
4864
|
+
headers["Content-Type"] = body.type;
|
|
4865
|
+
}
|
|
4866
|
+
const requestInit = {
|
|
4867
|
+
method: "PUT",
|
|
4868
|
+
headers,
|
|
4869
|
+
body,
|
|
4870
|
+
signal: options?.signal
|
|
4871
|
+
};
|
|
4872
|
+
if (isReadableStreamBody(body)) {
|
|
4873
|
+
requestInit.duplex = "half";
|
|
4874
|
+
}
|
|
4875
|
+
let response;
|
|
4876
|
+
try {
|
|
4877
|
+
response = await fetch(url, requestInit);
|
|
4878
|
+
} catch (error) {
|
|
4879
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
4880
|
+
return rejectStorageError(
|
|
4881
|
+
{
|
|
4882
|
+
code: "NETWORK_ERROR",
|
|
4883
|
+
message: `Network error while calling Athena storage PUT ${endpoint}: ${message}`,
|
|
4884
|
+
status: 0,
|
|
4885
|
+
endpoint,
|
|
4886
|
+
method: "PUT",
|
|
4887
|
+
cause: error
|
|
4888
|
+
},
|
|
4889
|
+
options,
|
|
4890
|
+
runtimeOptions
|
|
4891
|
+
);
|
|
4892
|
+
}
|
|
4893
|
+
let rawText;
|
|
4894
|
+
try {
|
|
4895
|
+
rawText = await response.text();
|
|
4896
|
+
} catch (error) {
|
|
4897
|
+
return rejectStorageError(
|
|
4898
|
+
{
|
|
4899
|
+
code: "NETWORK_ERROR",
|
|
4900
|
+
message: `Athena storage PUT ${endpoint} response body could not be read`,
|
|
4901
|
+
status: response.status,
|
|
4902
|
+
endpoint,
|
|
4903
|
+
method: "PUT",
|
|
4904
|
+
requestId: headerValue(response.headers, ["x-athena-request-id", "x-request-id", "request-id"]),
|
|
4905
|
+
cause: error
|
|
4906
|
+
},
|
|
4907
|
+
options,
|
|
4908
|
+
runtimeOptions
|
|
4909
|
+
);
|
|
4910
|
+
}
|
|
4911
|
+
const parsedBody = parseResponseBody3(rawText ?? "", response.headers.get("content-type"));
|
|
4912
|
+
const requestId = headerValue(response.headers, ["x-athena-request-id", "x-request-id", "request-id"]);
|
|
4913
|
+
if (parsedBody.parseFailed) {
|
|
4914
|
+
return rejectStorageError(
|
|
4915
|
+
{
|
|
4916
|
+
code: "INVALID_JSON",
|
|
4917
|
+
message: `Athena storage PUT ${endpoint} returned malformed JSON`,
|
|
4918
|
+
status: response.status,
|
|
4919
|
+
endpoint,
|
|
4920
|
+
method: "PUT",
|
|
4921
|
+
requestId,
|
|
4922
|
+
raw: parsedBody.parsed
|
|
4923
|
+
},
|
|
4924
|
+
options,
|
|
4925
|
+
runtimeOptions
|
|
4926
|
+
);
|
|
4927
|
+
}
|
|
4928
|
+
if (!response.ok) {
|
|
4929
|
+
return rejectStorageError(
|
|
4930
|
+
{
|
|
4931
|
+
code: "HTTP_ERROR",
|
|
4932
|
+
message: resolveErrorMessage3(
|
|
4933
|
+
parsedBody.parsed,
|
|
4934
|
+
`Athena storage PUT ${endpoint} failed with status ${response.status}`
|
|
4935
|
+
),
|
|
4936
|
+
status: response.status,
|
|
4937
|
+
endpoint,
|
|
4938
|
+
method: "PUT",
|
|
4939
|
+
requestId,
|
|
4940
|
+
hint: resolveErrorHint2(parsedBody.parsed),
|
|
4941
|
+
cause: resolveErrorCause(parsedBody.parsed),
|
|
4942
|
+
raw: parsedBody.parsed
|
|
4943
|
+
},
|
|
4944
|
+
options,
|
|
4945
|
+
runtimeOptions
|
|
4946
|
+
);
|
|
4947
|
+
}
|
|
4948
|
+
if (!isRecord6(parsedBody.parsed) || !("data" in parsedBody.parsed)) {
|
|
4949
|
+
return rejectStorageError(
|
|
4950
|
+
{
|
|
4951
|
+
code: "INVALID_ATHENA_ENVELOPE",
|
|
4952
|
+
message: `Athena storage PUT ${endpoint} returned an invalid Athena envelope`,
|
|
4953
|
+
status: response.status,
|
|
4954
|
+
endpoint,
|
|
4955
|
+
method: "PUT",
|
|
4956
|
+
requestId,
|
|
4957
|
+
raw: parsedBody.parsed
|
|
4958
|
+
},
|
|
4959
|
+
options,
|
|
4960
|
+
runtimeOptions
|
|
4961
|
+
);
|
|
4962
|
+
}
|
|
4963
|
+
return parsedBody.parsed.data;
|
|
4964
|
+
}
|
|
4965
|
+
function createStorageModule(gateway, runtimeOptions) {
|
|
4966
|
+
const resolvedRuntimeOptions = runtimeOptions;
|
|
4967
|
+
const callRaw = (path, method, payload, options) => callStorageEndpoint(
|
|
4968
|
+
gateway,
|
|
4969
|
+
storagePath(path),
|
|
4970
|
+
method,
|
|
4971
|
+
"raw",
|
|
4972
|
+
payload,
|
|
4973
|
+
options,
|
|
4974
|
+
resolvedRuntimeOptions
|
|
4975
|
+
);
|
|
4976
|
+
const callAthena2 = (path, method, payload, options) => callStorageEndpoint(
|
|
4977
|
+
gateway,
|
|
4978
|
+
storagePath(path),
|
|
4979
|
+
method,
|
|
4980
|
+
"athena",
|
|
4981
|
+
payload,
|
|
4982
|
+
options,
|
|
4983
|
+
resolvedRuntimeOptions
|
|
4984
|
+
);
|
|
4985
|
+
const base = {
|
|
4986
|
+
listStorageCatalogs(options) {
|
|
4987
|
+
return callRaw("/storage/catalogs", "GET", void 0, options);
|
|
4988
|
+
},
|
|
4989
|
+
createStorageCatalog(input, options) {
|
|
4990
|
+
return callRaw("/storage/catalogs", "POST", input, options);
|
|
4991
|
+
},
|
|
4992
|
+
updateStorageCatalog(id, input, options) {
|
|
4993
|
+
return callRaw(withPathParam("/storage/catalogs/{id}", "id", id), "PATCH", input, options);
|
|
4994
|
+
},
|
|
4995
|
+
deleteStorageCatalog(id, options) {
|
|
4996
|
+
return callRaw(withPathParam("/storage/catalogs/{id}", "id", id), "DELETE", void 0, options);
|
|
4066
4997
|
},
|
|
4067
4998
|
listStorageCredentials(options) {
|
|
4068
|
-
return
|
|
4999
|
+
return callRaw("/storage/credentials", "GET", void 0, options);
|
|
4069
5000
|
},
|
|
4070
5001
|
createStorageUploadUrl(input, options) {
|
|
4071
|
-
return
|
|
4072
|
-
gateway,
|
|
4073
|
-
storagePath("/storage/files/upload-url"),
|
|
4074
|
-
"POST",
|
|
4075
|
-
"athena",
|
|
4076
|
-
input,
|
|
4077
|
-
options,
|
|
4078
|
-
runtimeOptions
|
|
4079
|
-
);
|
|
5002
|
+
return callAthena2("/storage/files/upload-url", "POST", input, options);
|
|
4080
5003
|
},
|
|
4081
5004
|
createStorageUploadUrls(input, options) {
|
|
4082
|
-
return
|
|
4083
|
-
gateway,
|
|
4084
|
-
storagePath("/storage/files/upload-urls"),
|
|
4085
|
-
"POST",
|
|
4086
|
-
"athena",
|
|
4087
|
-
input,
|
|
4088
|
-
options,
|
|
4089
|
-
runtimeOptions
|
|
4090
|
-
);
|
|
5005
|
+
return callAthena2("/storage/files/upload-urls", "POST", input, options);
|
|
4091
5006
|
},
|
|
4092
5007
|
listStorageFiles(input, options) {
|
|
4093
|
-
return
|
|
5008
|
+
return callAthena2("/storage/files/list", "POST", input, options);
|
|
4094
5009
|
},
|
|
4095
5010
|
getStorageFile(fileId, options) {
|
|
4096
|
-
return
|
|
4097
|
-
gateway,
|
|
4098
|
-
storagePath(withPathParam("/storage/files/{file_id}", "file_id", fileId)),
|
|
4099
|
-
"GET",
|
|
4100
|
-
"athena",
|
|
4101
|
-
void 0,
|
|
4102
|
-
options,
|
|
4103
|
-
runtimeOptions
|
|
4104
|
-
);
|
|
5011
|
+
return callAthena2(withPathParam("/storage/files/{file_id}", "file_id", fileId), "GET", void 0, options);
|
|
4105
5012
|
},
|
|
4106
5013
|
getStorageFileUrl(fileId, query, options) {
|
|
4107
5014
|
const path = appendQuery(
|
|
4108
5015
|
withPathParam("/storage/files/{file_id}/url", "file_id", fileId),
|
|
4109
5016
|
query
|
|
4110
5017
|
);
|
|
4111
|
-
return
|
|
5018
|
+
return callAthena2(path, "GET", void 0, options);
|
|
4112
5019
|
},
|
|
4113
5020
|
getStorageFileProxy(fileId, query, options) {
|
|
4114
5021
|
const path = appendQuery(
|
|
4115
5022
|
withPathParam("/storage/files/{file_id}/proxy", "file_id", fileId),
|
|
4116
5023
|
query
|
|
4117
5024
|
);
|
|
4118
|
-
return callStorageBinaryEndpoint(gateway, storagePath(path), "GET", options,
|
|
5025
|
+
return callStorageBinaryEndpoint(gateway, storagePath(path), "GET", options, resolvedRuntimeOptions);
|
|
4119
5026
|
},
|
|
4120
5027
|
updateStorageFile(fileId, input, options) {
|
|
4121
|
-
return
|
|
4122
|
-
gateway,
|
|
4123
|
-
storagePath(withPathParam("/storage/files/{file_id}", "file_id", fileId)),
|
|
4124
|
-
"PATCH",
|
|
4125
|
-
"athena",
|
|
4126
|
-
input,
|
|
4127
|
-
options,
|
|
4128
|
-
runtimeOptions
|
|
4129
|
-
);
|
|
5028
|
+
return callAthena2(withPathParam("/storage/files/{file_id}", "file_id", fileId), "PATCH", input, options);
|
|
4130
5029
|
},
|
|
4131
5030
|
deleteStorageFile(fileId, options) {
|
|
4132
|
-
return
|
|
4133
|
-
gateway,
|
|
4134
|
-
storagePath(withPathParam("/storage/files/{file_id}", "file_id", fileId)),
|
|
4135
|
-
"DELETE",
|
|
4136
|
-
"athena",
|
|
4137
|
-
void 0,
|
|
4138
|
-
options,
|
|
4139
|
-
runtimeOptions
|
|
4140
|
-
);
|
|
5031
|
+
return callAthena2(withPathParam("/storage/files/{file_id}", "file_id", fileId), "DELETE", void 0, options);
|
|
4141
5032
|
},
|
|
4142
5033
|
setStorageFileVisibility(fileId, input, options) {
|
|
4143
|
-
return
|
|
5034
|
+
return callAthena2(withPathParam("/storage/files/{file_id}/visibility", "file_id", fileId), "PATCH", input, options);
|
|
5035
|
+
},
|
|
5036
|
+
deleteStorageFolder(input, options) {
|
|
5037
|
+
return callAthena2("/storage/folders/delete", "POST", input, options);
|
|
5038
|
+
},
|
|
5039
|
+
moveStorageFolder(input, options) {
|
|
5040
|
+
return callAthena2("/storage/folders/move", "POST", input, options);
|
|
5041
|
+
}
|
|
5042
|
+
};
|
|
5043
|
+
const fileFacade = createStorageFileModule(base, runtimeOptions);
|
|
5044
|
+
const fileUpload = ((input, options) => {
|
|
5045
|
+
if (isRecord6(input) && "files" in input) {
|
|
5046
|
+
return fileFacade.upload(input, options);
|
|
5047
|
+
}
|
|
5048
|
+
return base.createStorageUploadUrl(
|
|
5049
|
+
normalizeUploadUrlRequest(input),
|
|
5050
|
+
options
|
|
5051
|
+
).then(attachUploadHelper);
|
|
5052
|
+
});
|
|
5053
|
+
const fileDelete = ((input, options) => fileFacade.delete(input, options));
|
|
5054
|
+
const file = {
|
|
5055
|
+
...fileFacade,
|
|
5056
|
+
upload: fileUpload,
|
|
5057
|
+
uploadMany(input, options) {
|
|
5058
|
+
return base.createStorageUploadUrls(
|
|
5059
|
+
{ files: input.files.map(normalizeUploadUrlRequest) },
|
|
5060
|
+
options
|
|
5061
|
+
).then(attachUploadHelpers);
|
|
5062
|
+
},
|
|
5063
|
+
confirmUpload(fileId, input, options) {
|
|
5064
|
+
return callAthena2(withPathParam("/storage/files/{file_id}/confirm-upload", "file_id", fileId), "POST", input ?? {}, options);
|
|
5065
|
+
},
|
|
5066
|
+
uploadBinary(fileId, body, options) {
|
|
5067
|
+
return callStorageUploadBinaryEndpoint(
|
|
4144
5068
|
gateway,
|
|
4145
|
-
storagePath(withPathParam("/storage/files/{file_id}/
|
|
4146
|
-
|
|
4147
|
-
"athena",
|
|
4148
|
-
input,
|
|
5069
|
+
storagePath(withPathParam("/storage/files/{file_id}/upload", "file_id", fileId)),
|
|
5070
|
+
body,
|
|
4149
5071
|
options,
|
|
4150
|
-
|
|
5072
|
+
resolvedRuntimeOptions
|
|
4151
5073
|
);
|
|
4152
5074
|
},
|
|
4153
|
-
|
|
4154
|
-
return
|
|
5075
|
+
search(input, options) {
|
|
5076
|
+
return callAthena2("/storage/files/search", "POST", input, options);
|
|
4155
5077
|
},
|
|
4156
|
-
|
|
4157
|
-
return
|
|
5078
|
+
get(fileId, options) {
|
|
5079
|
+
return base.getStorageFile(fileId, options);
|
|
5080
|
+
},
|
|
5081
|
+
update(fileId, input, options) {
|
|
5082
|
+
return base.updateStorageFile(fileId, input, options);
|
|
5083
|
+
},
|
|
5084
|
+
delete: fileDelete,
|
|
5085
|
+
deleteMany(input, options) {
|
|
5086
|
+
return callAthena2("/storage/files/delete-many", "POST", input, options);
|
|
5087
|
+
},
|
|
5088
|
+
updateMany(input, options) {
|
|
5089
|
+
return callAthena2("/storage/files/update-many", "POST", input, options);
|
|
5090
|
+
},
|
|
5091
|
+
restore(fileId, options) {
|
|
5092
|
+
return callAthena2(withPathParam("/storage/files/{file_id}/restore", "file_id", fileId), "POST", {}, options);
|
|
5093
|
+
},
|
|
5094
|
+
purge(fileId, options) {
|
|
5095
|
+
return callAthena2(withPathParam("/storage/files/{file_id}/purge", "file_id", fileId), "DELETE", void 0, options);
|
|
5096
|
+
},
|
|
5097
|
+
copy(fileId, input, options) {
|
|
5098
|
+
return callAthena2(withPathParam("/storage/files/{file_id}/copy", "file_id", fileId), "POST", input, options);
|
|
5099
|
+
},
|
|
5100
|
+
url(fileId, query, options) {
|
|
5101
|
+
return base.getStorageFileUrl(fileId, query, options);
|
|
5102
|
+
},
|
|
5103
|
+
publicUrl(fileId, options) {
|
|
5104
|
+
return callAthena2(withPathParam("/storage/files/{file_id}/public-url", "file_id", fileId), "GET", void 0, options);
|
|
5105
|
+
},
|
|
5106
|
+
proxy(fileId, query, options) {
|
|
5107
|
+
return base.getStorageFileProxy(fileId, query, options);
|
|
5108
|
+
},
|
|
5109
|
+
visibility: {
|
|
5110
|
+
set(fileId, input, options) {
|
|
5111
|
+
return base.setStorageFileVisibility(fileId, input, options);
|
|
5112
|
+
},
|
|
5113
|
+
setMany(input, options) {
|
|
5114
|
+
return callAthena2("/storage/files/visibility-many", "POST", input, options);
|
|
5115
|
+
}
|
|
5116
|
+
}
|
|
5117
|
+
};
|
|
5118
|
+
const credentials = {
|
|
5119
|
+
list(options) {
|
|
5120
|
+
return base.listStorageCredentials(options);
|
|
5121
|
+
}
|
|
5122
|
+
};
|
|
5123
|
+
const catalog = {
|
|
5124
|
+
list(options) {
|
|
5125
|
+
return base.listStorageCatalogs(options);
|
|
5126
|
+
},
|
|
5127
|
+
create(input, options) {
|
|
5128
|
+
return base.createStorageCatalog(input, options);
|
|
5129
|
+
},
|
|
5130
|
+
update(id, input, options) {
|
|
5131
|
+
return base.updateStorageCatalog(id, input, options);
|
|
5132
|
+
},
|
|
5133
|
+
delete(id, options) {
|
|
5134
|
+
return base.deleteStorageCatalog(id, options);
|
|
5135
|
+
}
|
|
5136
|
+
};
|
|
5137
|
+
const folder = {
|
|
5138
|
+
list(input, options) {
|
|
5139
|
+
return callAthena2("/storage/folders/list", "POST", input, options);
|
|
5140
|
+
},
|
|
5141
|
+
tree(input, options) {
|
|
5142
|
+
return callAthena2("/storage/folders/tree", "POST", input, options);
|
|
5143
|
+
},
|
|
5144
|
+
delete(input, options) {
|
|
5145
|
+
return base.deleteStorageFolder(input, options);
|
|
5146
|
+
},
|
|
5147
|
+
move(input, options) {
|
|
5148
|
+
return base.moveStorageFolder(input, options);
|
|
5149
|
+
}
|
|
5150
|
+
};
|
|
5151
|
+
const permission = {
|
|
5152
|
+
list(input, options) {
|
|
5153
|
+
return callAthena2("/storage/permissions/list", "POST", input, options);
|
|
5154
|
+
},
|
|
5155
|
+
grant(input, options) {
|
|
5156
|
+
return callAthena2("/storage/permissions/grant", "POST", input, options);
|
|
5157
|
+
},
|
|
5158
|
+
revoke(input, options) {
|
|
5159
|
+
return callAthena2("/storage/permissions/revoke", "POST", input, options);
|
|
5160
|
+
},
|
|
5161
|
+
check(input, options) {
|
|
5162
|
+
return callAthena2("/storage/permissions/check", "POST", input, options);
|
|
5163
|
+
}
|
|
5164
|
+
};
|
|
5165
|
+
const objectFolder = {
|
|
5166
|
+
create(input, options) {
|
|
5167
|
+
return callAthena2("/storage/objects/folder", "POST", input, options);
|
|
5168
|
+
},
|
|
5169
|
+
delete(input, options) {
|
|
5170
|
+
return callAthena2("/storage/objects/folder/delete", "POST", input, options);
|
|
5171
|
+
},
|
|
5172
|
+
rename(input, options) {
|
|
5173
|
+
return callAthena2("/storage/objects/folder/rename", "POST", input, options);
|
|
4158
5174
|
}
|
|
4159
5175
|
};
|
|
5176
|
+
const object = {
|
|
5177
|
+
list(input, options) {
|
|
5178
|
+
return callAthena2("/storage/objects", "POST", input, options);
|
|
5179
|
+
},
|
|
5180
|
+
head(input, options) {
|
|
5181
|
+
return callAthena2("/storage/objects/head", "POST", input, options);
|
|
5182
|
+
},
|
|
5183
|
+
exists(input, options) {
|
|
5184
|
+
return callAthena2("/storage/objects/exists", "POST", input, options);
|
|
5185
|
+
},
|
|
5186
|
+
validate(input, options) {
|
|
5187
|
+
return callAthena2("/storage/objects/validate", "POST", input, options);
|
|
5188
|
+
},
|
|
5189
|
+
update(input, options) {
|
|
5190
|
+
return callAthena2("/storage/objects/update", "POST", input, options);
|
|
5191
|
+
},
|
|
5192
|
+
copy(input, options) {
|
|
5193
|
+
return callAthena2("/storage/objects/copy", "POST", input, options);
|
|
5194
|
+
},
|
|
5195
|
+
url(input, options) {
|
|
5196
|
+
return callAthena2("/storage/objects/url", "POST", input, options);
|
|
5197
|
+
},
|
|
5198
|
+
publicUrl(input, options) {
|
|
5199
|
+
return callAthena2("/storage/objects/public-url", "POST", input, options);
|
|
5200
|
+
},
|
|
5201
|
+
delete(input, options) {
|
|
5202
|
+
return callAthena2("/storage/objects/delete", "POST", input, options);
|
|
5203
|
+
},
|
|
5204
|
+
uploadUrl(input, options) {
|
|
5205
|
+
return callAthena2("/storage/objects/upload-url", "POST", input, options);
|
|
5206
|
+
},
|
|
5207
|
+
folder: objectFolder
|
|
5208
|
+
};
|
|
5209
|
+
const bucket = {
|
|
5210
|
+
list(input, options) {
|
|
5211
|
+
return callAthena2("/storage/buckets/list", "POST", input, options);
|
|
5212
|
+
},
|
|
5213
|
+
create(input, options) {
|
|
5214
|
+
return callAthena2("/storage/buckets/create", "POST", input, options);
|
|
5215
|
+
},
|
|
5216
|
+
delete(input, options) {
|
|
5217
|
+
return callAthena2("/storage/buckets/delete", "POST", input, options);
|
|
5218
|
+
},
|
|
5219
|
+
cors: {
|
|
5220
|
+
get(input, options) {
|
|
5221
|
+
return callAthena2("/storage/buckets/cors", "POST", input, options);
|
|
5222
|
+
},
|
|
5223
|
+
set(input, options) {
|
|
5224
|
+
return callAthena2("/storage/buckets/cors/set", "POST", input, options);
|
|
5225
|
+
},
|
|
5226
|
+
delete(input, options) {
|
|
5227
|
+
return callAthena2("/storage/buckets/cors/delete", "POST", input, options);
|
|
5228
|
+
}
|
|
5229
|
+
}
|
|
5230
|
+
};
|
|
5231
|
+
const multipart = {
|
|
5232
|
+
create(input, options) {
|
|
5233
|
+
return callAthena2("/storage/multipart/create", "POST", input, options);
|
|
5234
|
+
},
|
|
5235
|
+
signPart(input, options) {
|
|
5236
|
+
return callAthena2("/storage/multipart/sign-part", "POST", input, options);
|
|
5237
|
+
},
|
|
5238
|
+
complete(input, options) {
|
|
5239
|
+
return callAthena2("/storage/multipart/complete", "POST", input, options);
|
|
5240
|
+
},
|
|
5241
|
+
abort(input, options) {
|
|
5242
|
+
return callAthena2("/storage/multipart/abort", "POST", input, options);
|
|
5243
|
+
},
|
|
5244
|
+
listParts(input, options) {
|
|
5245
|
+
return callAthena2("/storage/multipart/list-parts", "POST", input, options);
|
|
5246
|
+
}
|
|
5247
|
+
};
|
|
5248
|
+
const audit = {
|
|
5249
|
+
list(input, options) {
|
|
5250
|
+
return callAthena2("/storage/audit/list", "POST", input, options);
|
|
5251
|
+
}
|
|
5252
|
+
};
|
|
5253
|
+
return {
|
|
5254
|
+
...base,
|
|
5255
|
+
credentials,
|
|
5256
|
+
catalog,
|
|
5257
|
+
file,
|
|
5258
|
+
folder,
|
|
5259
|
+
permission,
|
|
5260
|
+
object,
|
|
5261
|
+
bucket,
|
|
5262
|
+
multipart,
|
|
5263
|
+
audit,
|
|
5264
|
+
delete: file.delete
|
|
5265
|
+
};
|
|
5266
|
+
}
|
|
5267
|
+
|
|
5268
|
+
// src/client-builder.ts
|
|
5269
|
+
var DEFAULT_BACKEND = { type: "athena" };
|
|
5270
|
+
function toBackendConfig(value) {
|
|
5271
|
+
if (!value) return DEFAULT_BACKEND;
|
|
5272
|
+
return typeof value === "string" ? { type: value } : value;
|
|
4160
5273
|
}
|
|
4161
5274
|
|
|
4162
5275
|
// src/query-ast.ts
|
|
@@ -4186,7 +5299,7 @@ var BOOLEAN_SAFE_OPERATORS = /* @__PURE__ */ new Set([
|
|
|
4186
5299
|
"ilike",
|
|
4187
5300
|
"is"
|
|
4188
5301
|
]);
|
|
4189
|
-
function
|
|
5302
|
+
function isRecord7(value) {
|
|
4190
5303
|
return Boolean(value) && typeof value === "object" && !Array.isArray(value);
|
|
4191
5304
|
}
|
|
4192
5305
|
function isUuidString(value) {
|
|
@@ -4199,7 +5312,7 @@ function shouldUseUuidTextComparison(column, value) {
|
|
|
4199
5312
|
return typeof value === "string" && isUuidString(value) && isUuidIdentifierColumn(column);
|
|
4200
5313
|
}
|
|
4201
5314
|
function isRelationSelectNode(value) {
|
|
4202
|
-
return
|
|
5315
|
+
return isRecord7(value) && isRecord7(value.select);
|
|
4203
5316
|
}
|
|
4204
5317
|
function normalizeIdentifier(value, label) {
|
|
4205
5318
|
const normalized = value.trim();
|
|
@@ -4255,7 +5368,7 @@ function compileRelationToken(key, node) {
|
|
|
4255
5368
|
return `${prefix}${relationToken}(${nested})`;
|
|
4256
5369
|
}
|
|
4257
5370
|
function compileSelectShape(select) {
|
|
4258
|
-
if (!
|
|
5371
|
+
if (!isRecord7(select)) {
|
|
4259
5372
|
throw new Error("findMany select must be an object");
|
|
4260
5373
|
}
|
|
4261
5374
|
const tokens = [];
|
|
@@ -4279,7 +5392,7 @@ function compileSelectShape(select) {
|
|
|
4279
5392
|
return tokens.join(",");
|
|
4280
5393
|
}
|
|
4281
5394
|
function selectShapeUsesRelationSchema(select) {
|
|
4282
|
-
if (!
|
|
5395
|
+
if (!isRecord7(select)) {
|
|
4283
5396
|
return false;
|
|
4284
5397
|
}
|
|
4285
5398
|
for (const rawValue of Object.values(select)) {
|
|
@@ -4297,7 +5410,7 @@ function selectShapeUsesRelationSchema(select) {
|
|
|
4297
5410
|
}
|
|
4298
5411
|
function compileColumnWhere(column, input) {
|
|
4299
5412
|
const normalizedColumn = normalizeIdentifier(column, "where column");
|
|
4300
|
-
if (!
|
|
5413
|
+
if (!isRecord7(input)) {
|
|
4301
5414
|
return [buildGatewayCondition("eq", normalizedColumn, input)];
|
|
4302
5415
|
}
|
|
4303
5416
|
const conditions = [];
|
|
@@ -4325,7 +5438,7 @@ function compileColumnWhere(column, input) {
|
|
|
4325
5438
|
return conditions;
|
|
4326
5439
|
}
|
|
4327
5440
|
function compileBooleanExpressionTerms(clause, label) {
|
|
4328
|
-
if (!
|
|
5441
|
+
if (!isRecord7(clause)) {
|
|
4329
5442
|
throw new Error(`findMany where.${label} clauses must be objects`);
|
|
4330
5443
|
}
|
|
4331
5444
|
const entries = Object.entries(clause).filter(([, value]) => value !== void 0);
|
|
@@ -4334,7 +5447,7 @@ function compileBooleanExpressionTerms(clause, label) {
|
|
|
4334
5447
|
}
|
|
4335
5448
|
const [rawColumn, rawValue] = entries[0];
|
|
4336
5449
|
const column = normalizeIdentifier(rawColumn, `where.${label} column`);
|
|
4337
|
-
if (!
|
|
5450
|
+
if (!isRecord7(rawValue)) {
|
|
4338
5451
|
return [`${column}.eq.${stringifyFilterValue(rawValue)}`];
|
|
4339
5452
|
}
|
|
4340
5453
|
const operatorEntries = Object.entries(rawValue).filter(([, value]) => value !== void 0);
|
|
@@ -4358,7 +5471,7 @@ function compileWhere(where) {
|
|
|
4358
5471
|
if (where === void 0) {
|
|
4359
5472
|
return void 0;
|
|
4360
5473
|
}
|
|
4361
|
-
if (!
|
|
5474
|
+
if (!isRecord7(where)) {
|
|
4362
5475
|
throw new Error("findMany where must be an object");
|
|
4363
5476
|
}
|
|
4364
5477
|
const conditions = [];
|
|
@@ -4408,7 +5521,7 @@ function compileOrderBy(orderBy) {
|
|
|
4408
5521
|
if (orderBy === void 0) {
|
|
4409
5522
|
return void 0;
|
|
4410
5523
|
}
|
|
4411
|
-
if (!
|
|
5524
|
+
if (!isRecord7(orderBy)) {
|
|
4412
5525
|
throw new Error("findMany orderBy must be an object");
|
|
4413
5526
|
}
|
|
4414
5527
|
if ("column" in orderBy) {
|
|
@@ -4583,11 +5696,11 @@ function toFindManyAstOrder(order) {
|
|
|
4583
5696
|
ascending: order.direction !== "descending"
|
|
4584
5697
|
};
|
|
4585
5698
|
}
|
|
4586
|
-
function
|
|
5699
|
+
function isRecord8(value) {
|
|
4587
5700
|
return Boolean(value) && typeof value === "object" && !Array.isArray(value);
|
|
4588
5701
|
}
|
|
4589
5702
|
function normalizeFindManyAstColumnPredicate(value) {
|
|
4590
|
-
if (!
|
|
5703
|
+
if (!isRecord8(value)) {
|
|
4591
5704
|
return {
|
|
4592
5705
|
eq: value
|
|
4593
5706
|
};
|
|
@@ -4611,7 +5724,7 @@ function normalizeFindManyAstBooleanOperand(clause) {
|
|
|
4611
5724
|
return normalized;
|
|
4612
5725
|
}
|
|
4613
5726
|
function normalizeFindManyAstWhere(where) {
|
|
4614
|
-
if (!where || !
|
|
5727
|
+
if (!where || !isRecord8(where)) {
|
|
4615
5728
|
return where;
|
|
4616
5729
|
}
|
|
4617
5730
|
const normalized = {};
|
|
@@ -4625,7 +5738,7 @@ function normalizeFindManyAstWhere(where) {
|
|
|
4625
5738
|
);
|
|
4626
5739
|
continue;
|
|
4627
5740
|
}
|
|
4628
|
-
if (key === "not" &&
|
|
5741
|
+
if (key === "not" && isRecord8(value)) {
|
|
4629
5742
|
normalized.not = normalizeFindManyAstBooleanOperand(
|
|
4630
5743
|
value
|
|
4631
5744
|
);
|
|
@@ -4636,7 +5749,7 @@ function normalizeFindManyAstWhere(where) {
|
|
|
4636
5749
|
return normalized;
|
|
4637
5750
|
}
|
|
4638
5751
|
function predicateRequiresUuidQueryFallback(column, value) {
|
|
4639
|
-
if (!
|
|
5752
|
+
if (!isRecord8(value)) {
|
|
4640
5753
|
return shouldUseUuidTextComparison(column, value);
|
|
4641
5754
|
}
|
|
4642
5755
|
const eqValue = value.eq;
|
|
@@ -4654,7 +5767,7 @@ function booleanOperandRequiresUuidQueryFallback(clause) {
|
|
|
4654
5767
|
return false;
|
|
4655
5768
|
}
|
|
4656
5769
|
function findManyAstWhereRequiresLegacyTransport(where) {
|
|
4657
|
-
if (!where || !
|
|
5770
|
+
if (!where || !isRecord8(where)) {
|
|
4658
5771
|
return false;
|
|
4659
5772
|
}
|
|
4660
5773
|
for (const [key, value] of Object.entries(where)) {
|
|
@@ -4669,7 +5782,7 @@ function findManyAstWhereRequiresLegacyTransport(where) {
|
|
|
4669
5782
|
}
|
|
4670
5783
|
continue;
|
|
4671
5784
|
}
|
|
4672
|
-
if (key === "not" &&
|
|
5785
|
+
if (key === "not" && isRecord8(value)) {
|
|
4673
5786
|
if (booleanOperandRequiresUuidQueryFallback(value)) {
|
|
4674
5787
|
return true;
|
|
4675
5788
|
}
|
|
@@ -4781,20 +5894,437 @@ function createSelectTransportPlan(input) {
|
|
|
4781
5894
|
};
|
|
4782
5895
|
}
|
|
4783
5896
|
|
|
5897
|
+
// src/query-debug-ast.ts
|
|
5898
|
+
var ATHENA_DEBUG_AST_KEY = "__athenaDebugAst";
|
|
5899
|
+
function cloneConditions(conditions) {
|
|
5900
|
+
return conditions.map((condition) => ({ ...condition }));
|
|
5901
|
+
}
|
|
5902
|
+
function cloneTableBuilderStateAst(state) {
|
|
5903
|
+
return {
|
|
5904
|
+
conditions: cloneConditions(state.conditions),
|
|
5905
|
+
limit: state.limit,
|
|
5906
|
+
offset: state.offset,
|
|
5907
|
+
order: state.order ? { ...state.order } : void 0,
|
|
5908
|
+
currentPage: state.currentPage,
|
|
5909
|
+
pageSize: state.pageSize,
|
|
5910
|
+
totalPages: state.totalPages
|
|
5911
|
+
};
|
|
5912
|
+
}
|
|
5913
|
+
function cloneRpcBuilderStateAst(state) {
|
|
5914
|
+
return {
|
|
5915
|
+
filters: state.filters.map((filter) => ({ ...filter })),
|
|
5916
|
+
limit: state.limit,
|
|
5917
|
+
offset: state.offset,
|
|
5918
|
+
order: state.order ? { ...state.order } : void 0
|
|
5919
|
+
};
|
|
5920
|
+
}
|
|
5921
|
+
function toSelectTransportAst(plan) {
|
|
5922
|
+
if (plan.kind === "query") {
|
|
5923
|
+
return {
|
|
5924
|
+
mode: "typed-query",
|
|
5925
|
+
endpoint: "/gateway/query",
|
|
5926
|
+
payload: plan.payload
|
|
5927
|
+
};
|
|
5928
|
+
}
|
|
5929
|
+
return {
|
|
5930
|
+
mode: plan.payload.select !== void 0 ? "structured-fetch" : "compiled-fetch",
|
|
5931
|
+
endpoint: "/gateway/fetch",
|
|
5932
|
+
payload: plan.payload
|
|
5933
|
+
};
|
|
5934
|
+
}
|
|
5935
|
+
function resolveDebugTableName(tableName) {
|
|
5936
|
+
return tableName ?? "__unknown_table__";
|
|
5937
|
+
}
|
|
5938
|
+
function buildSelectDebugAst(input) {
|
|
5939
|
+
return {
|
|
5940
|
+
version: 1,
|
|
5941
|
+
kind: "select",
|
|
5942
|
+
tableName: input.tableName,
|
|
5943
|
+
input: {
|
|
5944
|
+
columns: input.columns,
|
|
5945
|
+
state: cloneTableBuilderStateAst(input.state)
|
|
5946
|
+
},
|
|
5947
|
+
transport: toSelectTransportAst(input.plan)
|
|
5948
|
+
};
|
|
5949
|
+
}
|
|
5950
|
+
function buildFindManyCompiledDebugAst(input) {
|
|
5951
|
+
return {
|
|
5952
|
+
version: 1,
|
|
5953
|
+
kind: "findMany",
|
|
5954
|
+
tableName: input.tableName,
|
|
5955
|
+
input: {
|
|
5956
|
+
select: input.options.select,
|
|
5957
|
+
where: input.options.where,
|
|
5958
|
+
orderBy: input.options.orderBy,
|
|
5959
|
+
limit: input.options.limit
|
|
5960
|
+
},
|
|
5961
|
+
compiled: {
|
|
5962
|
+
columns: input.compiledColumns,
|
|
5963
|
+
baseState: cloneTableBuilderStateAst(input.baseState),
|
|
5964
|
+
executionState: cloneTableBuilderStateAst(input.executionState)
|
|
5965
|
+
},
|
|
5966
|
+
transport: planToFindManyTransport(input.plan)
|
|
5967
|
+
};
|
|
5968
|
+
}
|
|
5969
|
+
function buildFindManyDirectDebugAst(input) {
|
|
5970
|
+
return {
|
|
5971
|
+
version: 1,
|
|
5972
|
+
kind: "findMany",
|
|
5973
|
+
tableName: input.tableName,
|
|
5974
|
+
input: {
|
|
5975
|
+
select: input.options.select,
|
|
5976
|
+
where: input.options.where,
|
|
5977
|
+
orderBy: input.options.orderBy,
|
|
5978
|
+
limit: input.options.limit
|
|
5979
|
+
},
|
|
5980
|
+
compiled: {
|
|
5981
|
+
columns: input.compiledColumns,
|
|
5982
|
+
baseState: cloneTableBuilderStateAst(input.baseState),
|
|
5983
|
+
executionState: cloneTableBuilderStateAst(input.executionState)
|
|
5984
|
+
},
|
|
5985
|
+
transport: {
|
|
5986
|
+
mode: "direct-ast-fetch",
|
|
5987
|
+
endpoint: "/gateway/fetch",
|
|
5988
|
+
payload: input.payload
|
|
5989
|
+
}
|
|
5990
|
+
};
|
|
5991
|
+
}
|
|
5992
|
+
function planToFindManyTransport(plan) {
|
|
5993
|
+
if (plan.kind === "query") {
|
|
5994
|
+
return {
|
|
5995
|
+
mode: "compiled-query",
|
|
5996
|
+
endpoint: "/gateway/query",
|
|
5997
|
+
payload: plan.payload
|
|
5998
|
+
};
|
|
5999
|
+
}
|
|
6000
|
+
return {
|
|
6001
|
+
mode: plan.payload.select !== void 0 ? "structured-fetch" : "compiled-fetch",
|
|
6002
|
+
endpoint: "/gateway/fetch",
|
|
6003
|
+
payload: plan.payload
|
|
6004
|
+
};
|
|
6005
|
+
}
|
|
6006
|
+
function buildInsertDebugAst(payload) {
|
|
6007
|
+
return {
|
|
6008
|
+
version: 1,
|
|
6009
|
+
kind: "insert",
|
|
6010
|
+
tableName: payload.table_name,
|
|
6011
|
+
input: {
|
|
6012
|
+
values: payload.insert_body,
|
|
6013
|
+
returning: payload.columns,
|
|
6014
|
+
count: payload.count,
|
|
6015
|
+
head: payload.head,
|
|
6016
|
+
defaultToNull: payload.default_to_null
|
|
6017
|
+
},
|
|
6018
|
+
transport: {
|
|
6019
|
+
mode: "insert",
|
|
6020
|
+
endpoint: "/gateway/insert",
|
|
6021
|
+
payload
|
|
6022
|
+
}
|
|
6023
|
+
};
|
|
6024
|
+
}
|
|
6025
|
+
function buildUpsertDebugAst(payload) {
|
|
6026
|
+
return {
|
|
6027
|
+
version: 1,
|
|
6028
|
+
kind: "upsert",
|
|
6029
|
+
tableName: payload.table_name,
|
|
6030
|
+
input: {
|
|
6031
|
+
values: payload.insert_body,
|
|
6032
|
+
updateBody: payload.update_body,
|
|
6033
|
+
onConflict: payload.on_conflict,
|
|
6034
|
+
returning: payload.columns,
|
|
6035
|
+
count: payload.count,
|
|
6036
|
+
head: payload.head,
|
|
6037
|
+
defaultToNull: payload.default_to_null
|
|
6038
|
+
},
|
|
6039
|
+
transport: {
|
|
6040
|
+
mode: "upsert",
|
|
6041
|
+
endpoint: "/gateway/insert",
|
|
6042
|
+
payload
|
|
6043
|
+
}
|
|
6044
|
+
};
|
|
6045
|
+
}
|
|
6046
|
+
function buildUpdateDebugAst(input) {
|
|
6047
|
+
return {
|
|
6048
|
+
version: 1,
|
|
6049
|
+
kind: "update",
|
|
6050
|
+
tableName: resolveDebugTableName(input.payload.table_name),
|
|
6051
|
+
input: {
|
|
6052
|
+
values: input.payload.set,
|
|
6053
|
+
state: cloneTableBuilderStateAst(input.state),
|
|
6054
|
+
returning: input.payload.columns
|
|
6055
|
+
},
|
|
6056
|
+
transport: {
|
|
6057
|
+
mode: "update",
|
|
6058
|
+
endpoint: "/gateway/update",
|
|
6059
|
+
payload: input.payload
|
|
6060
|
+
}
|
|
6061
|
+
};
|
|
6062
|
+
}
|
|
6063
|
+
function buildDeleteDebugAst(input) {
|
|
6064
|
+
return {
|
|
6065
|
+
version: 1,
|
|
6066
|
+
kind: "delete",
|
|
6067
|
+
tableName: input.payload.table_name,
|
|
6068
|
+
input: {
|
|
6069
|
+
resourceId: input.payload.resource_id,
|
|
6070
|
+
state: cloneTableBuilderStateAst(input.state),
|
|
6071
|
+
returning: input.payload.columns
|
|
6072
|
+
},
|
|
6073
|
+
transport: {
|
|
6074
|
+
mode: "delete",
|
|
6075
|
+
endpoint: "/gateway/delete",
|
|
6076
|
+
payload: input.payload
|
|
6077
|
+
}
|
|
6078
|
+
};
|
|
6079
|
+
}
|
|
6080
|
+
function buildRpcDebugAst(input) {
|
|
6081
|
+
return {
|
|
6082
|
+
version: 1,
|
|
6083
|
+
kind: "rpc",
|
|
6084
|
+
functionName: input.functionName,
|
|
6085
|
+
input: {
|
|
6086
|
+
args: input.args,
|
|
6087
|
+
select: input.selectedColumns,
|
|
6088
|
+
state: cloneRpcBuilderStateAst(input.state)
|
|
6089
|
+
},
|
|
6090
|
+
transport: {
|
|
6091
|
+
mode: input.endpoint === "/gateway/rpc" ? "rpc-post" : "rpc-get",
|
|
6092
|
+
endpoint: input.endpoint,
|
|
6093
|
+
payload: input.payload
|
|
6094
|
+
}
|
|
6095
|
+
};
|
|
6096
|
+
}
|
|
6097
|
+
function buildRawQueryDebugAst(query) {
|
|
6098
|
+
return {
|
|
6099
|
+
version: 1,
|
|
6100
|
+
kind: "query",
|
|
6101
|
+
input: {
|
|
6102
|
+
query
|
|
6103
|
+
},
|
|
6104
|
+
transport: {
|
|
6105
|
+
mode: "raw-query",
|
|
6106
|
+
endpoint: "/gateway/query",
|
|
6107
|
+
payload: {
|
|
6108
|
+
query
|
|
6109
|
+
}
|
|
6110
|
+
}
|
|
6111
|
+
};
|
|
6112
|
+
}
|
|
6113
|
+
function attachAthenaDebugAst(target, ast) {
|
|
6114
|
+
if (!ast) {
|
|
6115
|
+
return;
|
|
6116
|
+
}
|
|
6117
|
+
if (!target || typeof target !== "object" && typeof target !== "function") {
|
|
6118
|
+
return;
|
|
6119
|
+
}
|
|
6120
|
+
Object.defineProperty(target, ATHENA_DEBUG_AST_KEY, {
|
|
6121
|
+
value: ast,
|
|
6122
|
+
enumerable: false,
|
|
6123
|
+
configurable: true,
|
|
6124
|
+
writable: false
|
|
6125
|
+
});
|
|
6126
|
+
}
|
|
6127
|
+
|
|
6128
|
+
// src/query-tracing.ts
|
|
6129
|
+
var QUERY_TRACE_STACK_SKIP_PATTERNS = [
|
|
6130
|
+
"src\\client.ts",
|
|
6131
|
+
"src/client.ts",
|
|
6132
|
+
"src\\query-tracing.ts",
|
|
6133
|
+
"src/query-tracing.ts",
|
|
6134
|
+
"dist\\client.",
|
|
6135
|
+
"dist/client.",
|
|
6136
|
+
"dist\\query-tracing.",
|
|
6137
|
+
"dist/query-tracing.",
|
|
6138
|
+
"node_modules\\@xylex-group\\athena",
|
|
6139
|
+
"node_modules/@xylex-group/athena",
|
|
6140
|
+
"node:internal",
|
|
6141
|
+
"internal/process"
|
|
6142
|
+
];
|
|
6143
|
+
function parseQueryTraceCallsiteFrame(frame) {
|
|
6144
|
+
const trimmed = frame.trim();
|
|
6145
|
+
if (!trimmed) {
|
|
6146
|
+
return null;
|
|
6147
|
+
}
|
|
6148
|
+
let body = trimmed.replace(/^at\s+/, "");
|
|
6149
|
+
if (body.startsWith("async ")) {
|
|
6150
|
+
body = body.slice(6);
|
|
6151
|
+
}
|
|
6152
|
+
let functionName;
|
|
6153
|
+
let location = body;
|
|
6154
|
+
const wrappedMatch = body.match(/^(.*?)\s+\((.*)\)$/);
|
|
6155
|
+
if (wrappedMatch) {
|
|
6156
|
+
functionName = wrappedMatch[1].trim() || void 0;
|
|
6157
|
+
location = wrappedMatch[2].trim();
|
|
6158
|
+
}
|
|
6159
|
+
const locationMatch = location.match(/^(.*):(\d+):(\d+)$/);
|
|
6160
|
+
if (!locationMatch) {
|
|
6161
|
+
return null;
|
|
6162
|
+
}
|
|
6163
|
+
const filePath = locationMatch[1].replace(/^file:\/\//, "");
|
|
6164
|
+
const line = Number(locationMatch[2]);
|
|
6165
|
+
const column = Number(locationMatch[3]);
|
|
6166
|
+
if (!Number.isFinite(line) || !Number.isFinite(column)) {
|
|
6167
|
+
return null;
|
|
6168
|
+
}
|
|
6169
|
+
const normalizedPath = filePath.replace(/\\/g, "/");
|
|
6170
|
+
const fileName = normalizedPath.split("/").at(-1) ?? filePath;
|
|
6171
|
+
return {
|
|
6172
|
+
filePath,
|
|
6173
|
+
fileName,
|
|
6174
|
+
line,
|
|
6175
|
+
column,
|
|
6176
|
+
frame: trimmed,
|
|
6177
|
+
functionName
|
|
6178
|
+
};
|
|
6179
|
+
}
|
|
6180
|
+
function captureQueryTraceCallsite() {
|
|
6181
|
+
const stack = new Error().stack;
|
|
6182
|
+
if (!stack) return null;
|
|
6183
|
+
const frames = stack.split("\n").slice(2).map((frame) => frame.trim()).filter(Boolean);
|
|
6184
|
+
for (const frame of frames) {
|
|
6185
|
+
if (QUERY_TRACE_STACK_SKIP_PATTERNS.some((pattern) => frame.includes(pattern))) {
|
|
6186
|
+
continue;
|
|
6187
|
+
}
|
|
6188
|
+
const callsite = parseQueryTraceCallsiteFrame(frame);
|
|
6189
|
+
if (callsite) return callsite;
|
|
6190
|
+
}
|
|
6191
|
+
const fallback = frames.find((frame) => !frame.includes("captureQueryTraceCallsite"));
|
|
6192
|
+
return fallback ? parseQueryTraceCallsiteFrame(fallback) : null;
|
|
6193
|
+
}
|
|
6194
|
+
function defaultQueryTraceLogger(event) {
|
|
6195
|
+
const target = event.table ?? event.functionName ?? "gateway";
|
|
6196
|
+
const outcomeState = event.outcome?.error ? "error" : "ok";
|
|
6197
|
+
const banner = `[athena-js][trace] ${event.operation.toUpperCase()} ${event.endpoint} ${target} ${event.durationMs}ms ${outcomeState}`;
|
|
6198
|
+
console.info(banner, event);
|
|
6199
|
+
}
|
|
6200
|
+
function captureTraceCallsite(tracer) {
|
|
6201
|
+
return tracer?.captureCallsite() ?? null;
|
|
6202
|
+
}
|
|
6203
|
+
function createTraceCallsiteStore(tracer, initialCallsite) {
|
|
6204
|
+
let storedCallsite = initialCallsite ?? void 0;
|
|
6205
|
+
return {
|
|
6206
|
+
resolve(callsite) {
|
|
6207
|
+
if (callsite) {
|
|
6208
|
+
storedCallsite = callsite;
|
|
6209
|
+
return callsite;
|
|
6210
|
+
}
|
|
6211
|
+
if (storedCallsite !== void 0) {
|
|
6212
|
+
return storedCallsite;
|
|
6213
|
+
}
|
|
6214
|
+
const capturedCallsite = captureTraceCallsite(tracer);
|
|
6215
|
+
if (capturedCallsite) {
|
|
6216
|
+
storedCallsite = capturedCallsite;
|
|
6217
|
+
}
|
|
6218
|
+
return capturedCallsite;
|
|
6219
|
+
}
|
|
6220
|
+
};
|
|
6221
|
+
}
|
|
6222
|
+
function createQueryTracer(experimental) {
|
|
6223
|
+
const traceOption = experimental?.traceQueries;
|
|
6224
|
+
if (!traceOption) {
|
|
6225
|
+
return void 0;
|
|
6226
|
+
}
|
|
6227
|
+
const logger = typeof traceOption === "object" && traceOption.logger ? traceOption.logger : defaultQueryTraceLogger;
|
|
6228
|
+
const emit = (event) => {
|
|
6229
|
+
try {
|
|
6230
|
+
logger(event);
|
|
6231
|
+
} catch (error) {
|
|
6232
|
+
console.warn("[athena-js][trace] logger failed", error);
|
|
6233
|
+
}
|
|
6234
|
+
};
|
|
6235
|
+
return {
|
|
6236
|
+
captureCallsite: captureQueryTraceCallsite,
|
|
6237
|
+
publishSuccess(context, result, durationMs, callsite) {
|
|
6238
|
+
emit({
|
|
6239
|
+
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
6240
|
+
durationMs,
|
|
6241
|
+
operation: context.operation,
|
|
6242
|
+
endpoint: context.endpoint,
|
|
6243
|
+
table: context.table,
|
|
6244
|
+
functionName: context.functionName,
|
|
6245
|
+
sql: context.sql,
|
|
6246
|
+
payload: context.payload,
|
|
6247
|
+
ast: context.ast,
|
|
6248
|
+
options: context.options,
|
|
6249
|
+
callsite,
|
|
6250
|
+
outcome: {
|
|
6251
|
+
status: result.status,
|
|
6252
|
+
error: result.error,
|
|
6253
|
+
errorDetails: result.errorDetails ?? null,
|
|
6254
|
+
count: result.count ?? null,
|
|
6255
|
+
data: result.data,
|
|
6256
|
+
raw: result.raw
|
|
6257
|
+
}
|
|
6258
|
+
});
|
|
6259
|
+
},
|
|
6260
|
+
publishFailure(context, error, durationMs, callsite) {
|
|
6261
|
+
emit({
|
|
6262
|
+
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
6263
|
+
durationMs,
|
|
6264
|
+
operation: context.operation,
|
|
6265
|
+
endpoint: context.endpoint,
|
|
6266
|
+
table: context.table,
|
|
6267
|
+
functionName: context.functionName,
|
|
6268
|
+
sql: context.sql,
|
|
6269
|
+
payload: context.payload,
|
|
6270
|
+
ast: context.ast,
|
|
6271
|
+
options: context.options,
|
|
6272
|
+
callsite,
|
|
6273
|
+
thrownError: error
|
|
6274
|
+
});
|
|
6275
|
+
}
|
|
6276
|
+
};
|
|
6277
|
+
}
|
|
6278
|
+
async function executeWithQueryTrace(tracer, context, runner, callsiteOverride) {
|
|
6279
|
+
const callsite = tracer ? callsiteOverride ?? tracer.captureCallsite() : null;
|
|
6280
|
+
const startedAt = tracer ? Date.now() : 0;
|
|
6281
|
+
try {
|
|
6282
|
+
const result = await runner();
|
|
6283
|
+
attachAthenaDebugAst(result, context.ast);
|
|
6284
|
+
if (tracer) {
|
|
6285
|
+
tracer.publishSuccess(context, result, Date.now() - startedAt, callsite);
|
|
6286
|
+
}
|
|
6287
|
+
return result;
|
|
6288
|
+
} catch (error) {
|
|
6289
|
+
attachAthenaDebugAst(error, context.ast);
|
|
6290
|
+
if (tracer) {
|
|
6291
|
+
tracer.publishFailure(context, error, Date.now() - startedAt, callsite);
|
|
6292
|
+
}
|
|
6293
|
+
throw error;
|
|
6294
|
+
}
|
|
6295
|
+
}
|
|
6296
|
+
|
|
6297
|
+
// src/schema/model-target.ts
|
|
6298
|
+
function normalizeOptionalName(value) {
|
|
6299
|
+
const normalized = value?.trim();
|
|
6300
|
+
return normalized ? normalized : void 0;
|
|
6301
|
+
}
|
|
6302
|
+
function isAthenaModelTarget(value) {
|
|
6303
|
+
if (!value || typeof value !== "object") {
|
|
6304
|
+
return false;
|
|
6305
|
+
}
|
|
6306
|
+
const candidate = value;
|
|
6307
|
+
return Boolean(candidate.meta && Array.isArray(candidate.meta.primaryKey));
|
|
6308
|
+
}
|
|
6309
|
+
function resolveAthenaModelTargetTableName(target, options = {}) {
|
|
6310
|
+
const explicitTableName = normalizeOptionalName(target.meta.tableName);
|
|
6311
|
+
if (explicitTableName) {
|
|
6312
|
+
return explicitTableName;
|
|
6313
|
+
}
|
|
6314
|
+
const schemaName = normalizeOptionalName(target.meta.schema ?? options.fallbackSchema);
|
|
6315
|
+
const modelName = normalizeOptionalName(target.meta.model ?? options.fallbackModel);
|
|
6316
|
+
if (!modelName) {
|
|
6317
|
+
throw new Error(
|
|
6318
|
+
"Athena model target is missing meta.model or meta.tableName. Provide one of those before calling from(model)."
|
|
6319
|
+
);
|
|
6320
|
+
}
|
|
6321
|
+
return schemaName ? `${schemaName}.${modelName}` : modelName;
|
|
6322
|
+
}
|
|
6323
|
+
|
|
4784
6324
|
// src/client.ts
|
|
4785
6325
|
var DEFAULT_COLUMNS = "*";
|
|
4786
6326
|
var SAFE_CAST_PATTERN = /^[a-z_][a-z0-9_]*(?:\[\])?$/i;
|
|
4787
6327
|
var ATHENA_NORMALIZED_ERROR_KEY = "__athenaNormalizedError";
|
|
4788
|
-
var QUERY_TRACE_STACK_SKIP_PATTERNS = [
|
|
4789
|
-
"src\\client.ts",
|
|
4790
|
-
"src/client.ts",
|
|
4791
|
-
"dist\\client.",
|
|
4792
|
-
"dist/client.",
|
|
4793
|
-
"node_modules\\@xylex-group\\athena",
|
|
4794
|
-
"node_modules/@xylex-group/athena",
|
|
4795
|
-
"node:internal",
|
|
4796
|
-
"internal/process"
|
|
4797
|
-
];
|
|
4798
6328
|
function formatResult(response) {
|
|
4799
6329
|
const result = {
|
|
4800
6330
|
data: response.data ?? null,
|
|
@@ -4871,7 +6401,7 @@ async function executeExperimentalRead(experimental, runner) {
|
|
|
4871
6401
|
throw error;
|
|
4872
6402
|
}
|
|
4873
6403
|
}
|
|
4874
|
-
function
|
|
6404
|
+
function isRecord9(value) {
|
|
4875
6405
|
return Boolean(value) && typeof value === "object" && !Array.isArray(value);
|
|
4876
6406
|
}
|
|
4877
6407
|
function firstNonEmptyString2(...values) {
|
|
@@ -4883,8 +6413,8 @@ function firstNonEmptyString2(...values) {
|
|
|
4883
6413
|
return void 0;
|
|
4884
6414
|
}
|
|
4885
6415
|
function resolveStructuredErrorPayload2(raw) {
|
|
4886
|
-
if (!
|
|
4887
|
-
return
|
|
6416
|
+
if (!isRecord9(raw)) return null;
|
|
6417
|
+
return isRecord9(raw.error) ? raw.error : raw;
|
|
4888
6418
|
}
|
|
4889
6419
|
function resolveStructuredErrorDetails(payload, message) {
|
|
4890
6420
|
if (!payload || !("details" in payload)) {
|
|
@@ -4900,7 +6430,7 @@ function resolveStructuredErrorDetails(payload, message) {
|
|
|
4900
6430
|
return details;
|
|
4901
6431
|
}
|
|
4902
6432
|
function createResultError(response, result, normalized) {
|
|
4903
|
-
const rawRecord =
|
|
6433
|
+
const rawRecord = isRecord9(response.raw) ? response.raw : null;
|
|
4904
6434
|
const payload = resolveStructuredErrorPayload2(response.raw);
|
|
4905
6435
|
const message = firstNonEmptyString2(
|
|
4906
6436
|
response.error,
|
|
@@ -4936,154 +6466,6 @@ function createResultError(response, result, normalized) {
|
|
|
4936
6466
|
raw: result.raw
|
|
4937
6467
|
};
|
|
4938
6468
|
}
|
|
4939
|
-
function parseQueryTraceCallsiteFrame(frame) {
|
|
4940
|
-
const trimmed = frame.trim();
|
|
4941
|
-
if (!trimmed) {
|
|
4942
|
-
return null;
|
|
4943
|
-
}
|
|
4944
|
-
let body = trimmed.replace(/^at\s+/, "");
|
|
4945
|
-
if (body.startsWith("async ")) {
|
|
4946
|
-
body = body.slice(6);
|
|
4947
|
-
}
|
|
4948
|
-
let functionName;
|
|
4949
|
-
let location = body;
|
|
4950
|
-
const wrappedMatch = body.match(/^(.*?)\s+\((.*)\)$/);
|
|
4951
|
-
if (wrappedMatch) {
|
|
4952
|
-
functionName = wrappedMatch[1].trim() || void 0;
|
|
4953
|
-
location = wrappedMatch[2].trim();
|
|
4954
|
-
}
|
|
4955
|
-
const locationMatch = location.match(/^(.*):(\d+):(\d+)$/);
|
|
4956
|
-
if (!locationMatch) {
|
|
4957
|
-
return null;
|
|
4958
|
-
}
|
|
4959
|
-
const filePath = locationMatch[1].replace(/^file:\/\//, "");
|
|
4960
|
-
const line = Number(locationMatch[2]);
|
|
4961
|
-
const column = Number(locationMatch[3]);
|
|
4962
|
-
if (!Number.isFinite(line) || !Number.isFinite(column)) {
|
|
4963
|
-
return null;
|
|
4964
|
-
}
|
|
4965
|
-
const normalizedPath = filePath.replace(/\\/g, "/");
|
|
4966
|
-
const fileName = normalizedPath.split("/").at(-1) ?? filePath;
|
|
4967
|
-
return {
|
|
4968
|
-
filePath,
|
|
4969
|
-
fileName,
|
|
4970
|
-
line,
|
|
4971
|
-
column,
|
|
4972
|
-
frame: trimmed,
|
|
4973
|
-
functionName
|
|
4974
|
-
};
|
|
4975
|
-
}
|
|
4976
|
-
function captureQueryTraceCallsite() {
|
|
4977
|
-
const stack = new Error().stack;
|
|
4978
|
-
if (!stack) return null;
|
|
4979
|
-
const frames = stack.split("\n").slice(2).map((frame) => frame.trim()).filter(Boolean);
|
|
4980
|
-
for (const frame of frames) {
|
|
4981
|
-
if (QUERY_TRACE_STACK_SKIP_PATTERNS.some((pattern) => frame.includes(pattern))) {
|
|
4982
|
-
continue;
|
|
4983
|
-
}
|
|
4984
|
-
const callsite = parseQueryTraceCallsiteFrame(frame);
|
|
4985
|
-
if (callsite) return callsite;
|
|
4986
|
-
}
|
|
4987
|
-
const fallback = frames.find((frame) => !frame.includes("captureQueryTraceCallsite"));
|
|
4988
|
-
return fallback ? parseQueryTraceCallsiteFrame(fallback) : null;
|
|
4989
|
-
}
|
|
4990
|
-
function defaultQueryTraceLogger(event) {
|
|
4991
|
-
const target = event.table ?? event.functionName ?? "gateway";
|
|
4992
|
-
const outcomeState = event.outcome?.error ? "error" : "ok";
|
|
4993
|
-
const banner = `[athena-js][trace] ${event.operation.toUpperCase()} ${event.endpoint} ${target} ${event.durationMs}ms ${outcomeState}`;
|
|
4994
|
-
console.info(banner, event);
|
|
4995
|
-
}
|
|
4996
|
-
function captureTraceCallsite(tracer) {
|
|
4997
|
-
return tracer?.captureCallsite() ?? null;
|
|
4998
|
-
}
|
|
4999
|
-
function createTraceCallsiteStore(tracer, initialCallsite) {
|
|
5000
|
-
let storedCallsite = initialCallsite ?? void 0;
|
|
5001
|
-
return {
|
|
5002
|
-
resolve(callsite) {
|
|
5003
|
-
if (callsite) {
|
|
5004
|
-
storedCallsite = callsite;
|
|
5005
|
-
return callsite;
|
|
5006
|
-
}
|
|
5007
|
-
if (storedCallsite !== void 0) {
|
|
5008
|
-
return storedCallsite;
|
|
5009
|
-
}
|
|
5010
|
-
const capturedCallsite = captureTraceCallsite(tracer);
|
|
5011
|
-
if (capturedCallsite) {
|
|
5012
|
-
storedCallsite = capturedCallsite;
|
|
5013
|
-
}
|
|
5014
|
-
return capturedCallsite;
|
|
5015
|
-
}
|
|
5016
|
-
};
|
|
5017
|
-
}
|
|
5018
|
-
function createQueryTracer(experimental) {
|
|
5019
|
-
const traceOption = experimental?.traceQueries;
|
|
5020
|
-
if (!traceOption) {
|
|
5021
|
-
return void 0;
|
|
5022
|
-
}
|
|
5023
|
-
const logger = typeof traceOption === "object" && traceOption.logger ? traceOption.logger : defaultQueryTraceLogger;
|
|
5024
|
-
const emit = (event) => {
|
|
5025
|
-
try {
|
|
5026
|
-
logger(event);
|
|
5027
|
-
} catch (error) {
|
|
5028
|
-
console.warn("[athena-js][trace] logger failed", error);
|
|
5029
|
-
}
|
|
5030
|
-
};
|
|
5031
|
-
return {
|
|
5032
|
-
captureCallsite: captureQueryTraceCallsite,
|
|
5033
|
-
publishSuccess(context, result, durationMs, callsite) {
|
|
5034
|
-
emit({
|
|
5035
|
-
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
5036
|
-
durationMs,
|
|
5037
|
-
operation: context.operation,
|
|
5038
|
-
endpoint: context.endpoint,
|
|
5039
|
-
table: context.table,
|
|
5040
|
-
functionName: context.functionName,
|
|
5041
|
-
sql: context.sql,
|
|
5042
|
-
payload: context.payload,
|
|
5043
|
-
options: context.options,
|
|
5044
|
-
callsite,
|
|
5045
|
-
outcome: {
|
|
5046
|
-
status: result.status,
|
|
5047
|
-
error: result.error,
|
|
5048
|
-
errorDetails: result.errorDetails ?? null,
|
|
5049
|
-
count: result.count ?? null,
|
|
5050
|
-
data: result.data,
|
|
5051
|
-
raw: result.raw
|
|
5052
|
-
}
|
|
5053
|
-
});
|
|
5054
|
-
},
|
|
5055
|
-
publishFailure(context, error, durationMs, callsite) {
|
|
5056
|
-
emit({
|
|
5057
|
-
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
5058
|
-
durationMs,
|
|
5059
|
-
operation: context.operation,
|
|
5060
|
-
endpoint: context.endpoint,
|
|
5061
|
-
table: context.table,
|
|
5062
|
-
functionName: context.functionName,
|
|
5063
|
-
sql: context.sql,
|
|
5064
|
-
payload: context.payload,
|
|
5065
|
-
options: context.options,
|
|
5066
|
-
callsite,
|
|
5067
|
-
thrownError: error
|
|
5068
|
-
});
|
|
5069
|
-
}
|
|
5070
|
-
};
|
|
5071
|
-
}
|
|
5072
|
-
async function executeWithQueryTrace(tracer, context, runner, callsiteOverride) {
|
|
5073
|
-
if (!tracer) {
|
|
5074
|
-
return runner();
|
|
5075
|
-
}
|
|
5076
|
-
const callsite = callsiteOverride ?? tracer.captureCallsite();
|
|
5077
|
-
const startedAt = Date.now();
|
|
5078
|
-
try {
|
|
5079
|
-
const result = await runner();
|
|
5080
|
-
tracer.publishSuccess(context, result, Date.now() - startedAt, callsite);
|
|
5081
|
-
return result;
|
|
5082
|
-
} catch (error) {
|
|
5083
|
-
tracer.publishFailure(context, error, Date.now() - startedAt, callsite);
|
|
5084
|
-
throw error;
|
|
5085
|
-
}
|
|
5086
|
-
}
|
|
5087
6469
|
function toSingleResult(response) {
|
|
5088
6470
|
const payload = response.data;
|
|
5089
6471
|
const singleData = Array.isArray(payload) ? payload.length ? payload[0] : null : payload ?? null;
|
|
@@ -5111,6 +6493,15 @@ function asAthenaJsonObject(value) {
|
|
|
5111
6493
|
function asAthenaJsonObjectArray(values) {
|
|
5112
6494
|
return values;
|
|
5113
6495
|
}
|
|
6496
|
+
function normalizeSelectColumnsInput(columns) {
|
|
6497
|
+
if (columns === void 0) {
|
|
6498
|
+
return void 0;
|
|
6499
|
+
}
|
|
6500
|
+
if (typeof columns === "string") {
|
|
6501
|
+
return columns;
|
|
6502
|
+
}
|
|
6503
|
+
return [...columns];
|
|
6504
|
+
}
|
|
5114
6505
|
function createMutationQuery(executor, defaultColumns = DEFAULT_COLUMNS, tracer, initialCallsite) {
|
|
5115
6506
|
let selectedColumns = defaultColumns === null ? void 0 : defaultColumns;
|
|
5116
6507
|
let selectedOptions;
|
|
@@ -5120,25 +6511,29 @@ function createMutationQuery(executor, defaultColumns = DEFAULT_COLUMNS, tracer,
|
|
|
5120
6511
|
const payloadColumns = columns ?? selectedColumns;
|
|
5121
6512
|
const payloadOptions = options ?? selectedOptions;
|
|
5122
6513
|
if (!promise) {
|
|
5123
|
-
promise = executor(
|
|
6514
|
+
promise = executor(
|
|
6515
|
+
normalizeSelectColumnsInput(payloadColumns),
|
|
6516
|
+
payloadOptions,
|
|
6517
|
+
callsiteStore.resolve(callsite)
|
|
6518
|
+
);
|
|
5124
6519
|
}
|
|
5125
6520
|
return promise;
|
|
5126
6521
|
};
|
|
5127
6522
|
const mutationQuery = {
|
|
5128
|
-
select(columns
|
|
6523
|
+
select(columns, options) {
|
|
5129
6524
|
selectedColumns = columns;
|
|
5130
6525
|
selectedOptions = options ?? selectedOptions;
|
|
5131
6526
|
return run(columns, options, captureTraceCallsite(tracer));
|
|
5132
6527
|
},
|
|
5133
|
-
returning(columns
|
|
6528
|
+
returning(columns, options) {
|
|
5134
6529
|
return mutationQuery.select(columns, options);
|
|
5135
6530
|
},
|
|
5136
|
-
single(columns
|
|
6531
|
+
single(columns, options) {
|
|
5137
6532
|
selectedColumns = columns;
|
|
5138
6533
|
selectedOptions = options ?? selectedOptions;
|
|
5139
6534
|
return run(columns, options, captureTraceCallsite(tracer)).then(toSingleResult);
|
|
5140
6535
|
},
|
|
5141
|
-
maybeSingle(columns
|
|
6536
|
+
maybeSingle(columns, options) {
|
|
5142
6537
|
return mutationQuery.single(columns, options);
|
|
5143
6538
|
},
|
|
5144
6539
|
then(onfulfilled, onrejected) {
|
|
@@ -5695,7 +7090,10 @@ function createFilterMethods(state, addCondition, self) {
|
|
|
5695
7090
|
}
|
|
5696
7091
|
function toRpcSelect(columns) {
|
|
5697
7092
|
if (!columns) return void 0;
|
|
5698
|
-
|
|
7093
|
+
if (typeof columns === "string") {
|
|
7094
|
+
return columns;
|
|
7095
|
+
}
|
|
7096
|
+
return columns.join(",");
|
|
5699
7097
|
}
|
|
5700
7098
|
function createRpcFilterMethods(filters, self) {
|
|
5701
7099
|
const addFilter = (operator, column, value) => {
|
|
@@ -5744,7 +7142,7 @@ function createRpcFilterMethods(filters, self) {
|
|
|
5744
7142
|
}
|
|
5745
7143
|
};
|
|
5746
7144
|
}
|
|
5747
|
-
function createRpcBuilder(functionName, args, baseOptions, client, formatGatewayResult, tracer, initialCallsite) {
|
|
7145
|
+
function createRpcBuilder(functionName, args, baseOptions, client, formatGatewayResult, tracer, initialCallsite, debugAstEnabled = false) {
|
|
5748
7146
|
const state = {
|
|
5749
7147
|
filters: []
|
|
5750
7148
|
};
|
|
@@ -5754,6 +7152,7 @@ function createRpcBuilder(functionName, args, baseOptions, client, formatGateway
|
|
|
5754
7152
|
const callsiteStore = createTraceCallsiteStore(tracer, initialCallsite);
|
|
5755
7153
|
const executeRpc = async (columns, options, callsite) => {
|
|
5756
7154
|
const mergedOptions = mergeOptions(baseOptions, options);
|
|
7155
|
+
const normalizedSelectedColumns = normalizeSelectColumnsInput(columns);
|
|
5757
7156
|
const payload = {
|
|
5758
7157
|
function: functionName,
|
|
5759
7158
|
args,
|
|
@@ -5768,6 +7167,14 @@ function createRpcBuilder(functionName, args, baseOptions, client, formatGateway
|
|
|
5768
7167
|
};
|
|
5769
7168
|
const endpoint = mergedOptions?.get ? `/rpc/${functionName}` : "/gateway/rpc";
|
|
5770
7169
|
const sql = buildRpcDebugSql(payload);
|
|
7170
|
+
const debugAst = debugAstEnabled ? buildRpcDebugAst({
|
|
7171
|
+
functionName,
|
|
7172
|
+
args,
|
|
7173
|
+
selectedColumns: normalizedSelectedColumns,
|
|
7174
|
+
state,
|
|
7175
|
+
payload,
|
|
7176
|
+
endpoint
|
|
7177
|
+
}) : void 0;
|
|
5771
7178
|
return executeWithQueryTrace(
|
|
5772
7179
|
tracer,
|
|
5773
7180
|
{
|
|
@@ -5776,6 +7183,7 @@ function createRpcBuilder(functionName, args, baseOptions, client, formatGateway
|
|
|
5776
7183
|
functionName,
|
|
5777
7184
|
sql,
|
|
5778
7185
|
payload,
|
|
7186
|
+
ast: debugAst,
|
|
5779
7187
|
options: mergedOptions
|
|
5780
7188
|
},
|
|
5781
7189
|
async () => {
|
|
@@ -5796,7 +7204,7 @@ function createRpcBuilder(functionName, args, baseOptions, client, formatGateway
|
|
|
5796
7204
|
const builder = {};
|
|
5797
7205
|
const filterMethods = createRpcFilterMethods(state.filters, builder);
|
|
5798
7206
|
Object.assign(builder, filterMethods, {
|
|
5799
|
-
select(columns
|
|
7207
|
+
select(columns, options) {
|
|
5800
7208
|
selectedColumns = columns;
|
|
5801
7209
|
selectedOptions = options ?? selectedOptions;
|
|
5802
7210
|
return run(columns, options, captureTraceCallsite(tracer));
|
|
@@ -5841,6 +7249,7 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
5841
7249
|
const state = {
|
|
5842
7250
|
conditions: []
|
|
5843
7251
|
};
|
|
7252
|
+
const debugAstEnabled = Boolean(experimental?.debugAst);
|
|
5844
7253
|
const addCondition = (operator, column, value, hints) => {
|
|
5845
7254
|
const condition = { operator };
|
|
5846
7255
|
if (column) {
|
|
@@ -5884,15 +7293,27 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
5884
7293
|
addCondition,
|
|
5885
7294
|
builder
|
|
5886
7295
|
);
|
|
5887
|
-
const runSelect = async (columns = DEFAULT_COLUMNS, options, executionState = snapshotState(), callsite) => {
|
|
7296
|
+
const runSelect = async (columns = DEFAULT_COLUMNS, options, executionState = snapshotState(), callsite, debugAstFactory) => {
|
|
7297
|
+
const runtimeColumns = normalizeSelectColumnsInput(columns) ?? DEFAULT_COLUMNS;
|
|
5888
7298
|
const resolvedTableName = resolveTableNameForCall(tableName, options?.schema);
|
|
5889
7299
|
const plan = createSelectTransportPlan({
|
|
5890
7300
|
tableName: resolvedTableName,
|
|
5891
|
-
columns,
|
|
7301
|
+
columns: runtimeColumns,
|
|
5892
7302
|
state: executionState,
|
|
5893
7303
|
options,
|
|
5894
7304
|
buildTypedSelectQuery
|
|
5895
7305
|
});
|
|
7306
|
+
const debugAst = debugAstEnabled ? debugAstFactory?.({
|
|
7307
|
+
tableName: resolvedTableName,
|
|
7308
|
+
columns: runtimeColumns,
|
|
7309
|
+
executionState,
|
|
7310
|
+
plan
|
|
7311
|
+
}) ?? buildSelectDebugAst({
|
|
7312
|
+
tableName: resolvedTableName,
|
|
7313
|
+
columns: runtimeColumns,
|
|
7314
|
+
state: executionState,
|
|
7315
|
+
plan
|
|
7316
|
+
}) : void 0;
|
|
5896
7317
|
if (plan.kind === "query") {
|
|
5897
7318
|
return executeExperimentalRead(
|
|
5898
7319
|
experimental,
|
|
@@ -5904,6 +7325,7 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
5904
7325
|
table: resolvedTableName,
|
|
5905
7326
|
sql: plan.query,
|
|
5906
7327
|
payload: plan.payload,
|
|
7328
|
+
ast: debugAst,
|
|
5907
7329
|
options
|
|
5908
7330
|
},
|
|
5909
7331
|
async () => {
|
|
@@ -5928,6 +7350,7 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
5928
7350
|
table: resolvedTableName,
|
|
5929
7351
|
sql,
|
|
5930
7352
|
payload: plan.payload,
|
|
7353
|
+
ast: debugAst,
|
|
5931
7354
|
options
|
|
5932
7355
|
},
|
|
5933
7356
|
async () => {
|
|
@@ -5941,7 +7364,11 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
5941
7364
|
const createSelectChain = (columns, options, initialCallsite) => {
|
|
5942
7365
|
const chain = {};
|
|
5943
7366
|
const callsiteStore = createTraceCallsiteStore(tracer, initialCallsite);
|
|
5944
|
-
const filterMethods2 = createFilterMethods(
|
|
7367
|
+
const filterMethods2 = createFilterMethods(
|
|
7368
|
+
state,
|
|
7369
|
+
addCondition,
|
|
7370
|
+
chain
|
|
7371
|
+
);
|
|
5945
7372
|
Object.assign(chain, filterMethods2, {
|
|
5946
7373
|
async single(cols, opts) {
|
|
5947
7374
|
const r = await runSelect(
|
|
@@ -6028,6 +7455,14 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6028
7455
|
limit: executionState.limit,
|
|
6029
7456
|
order: executionState.order
|
|
6030
7457
|
});
|
|
7458
|
+
const debugAst = debugAstEnabled ? buildFindManyDirectDebugAst({
|
|
7459
|
+
tableName: resolvedTableName,
|
|
7460
|
+
options,
|
|
7461
|
+
compiledColumns: columns,
|
|
7462
|
+
baseState,
|
|
7463
|
+
executionState,
|
|
7464
|
+
payload
|
|
7465
|
+
}) : void 0;
|
|
6031
7466
|
return executeExperimentalRead(
|
|
6032
7467
|
experimental,
|
|
6033
7468
|
() => executeWithQueryTrace(
|
|
@@ -6037,7 +7472,8 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6037
7472
|
endpoint: "/gateway/fetch",
|
|
6038
7473
|
table: resolvedTableName,
|
|
6039
7474
|
sql,
|
|
6040
|
-
payload
|
|
7475
|
+
payload,
|
|
7476
|
+
ast: debugAst
|
|
6041
7477
|
},
|
|
6042
7478
|
async () => {
|
|
6043
7479
|
const response = await client.fetchGateway(
|
|
@@ -6053,7 +7489,15 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6053
7489
|
columns,
|
|
6054
7490
|
void 0,
|
|
6055
7491
|
executionState,
|
|
6056
|
-
callsite
|
|
7492
|
+
callsite,
|
|
7493
|
+
debugAstEnabled ? ({ tableName: resolvedTableName, executionState: tracedState, plan }) => buildFindManyCompiledDebugAst({
|
|
7494
|
+
tableName: resolvedTableName,
|
|
7495
|
+
options,
|
|
7496
|
+
compiledColumns: columns,
|
|
7497
|
+
baseState,
|
|
7498
|
+
executionState: tracedState,
|
|
7499
|
+
plan
|
|
7500
|
+
}) : void 0
|
|
6057
7501
|
);
|
|
6058
7502
|
},
|
|
6059
7503
|
insert(values, options) {
|
|
@@ -6073,6 +7517,7 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6073
7517
|
payload.default_to_null = mergedOptions.defaultToNull;
|
|
6074
7518
|
}
|
|
6075
7519
|
const sql = buildInsertDebugSql(payload);
|
|
7520
|
+
const debugAst = debugAstEnabled ? buildInsertDebugAst(payload) : void 0;
|
|
6076
7521
|
return executeWithQueryTrace(
|
|
6077
7522
|
tracer,
|
|
6078
7523
|
{
|
|
@@ -6081,6 +7526,7 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6081
7526
|
table: resolvedTableName,
|
|
6082
7527
|
sql,
|
|
6083
7528
|
payload,
|
|
7529
|
+
ast: debugAst,
|
|
6084
7530
|
options: mergedOptions
|
|
6085
7531
|
},
|
|
6086
7532
|
async () => {
|
|
@@ -6106,6 +7552,7 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6106
7552
|
payload.default_to_null = mergedOptions.defaultToNull;
|
|
6107
7553
|
}
|
|
6108
7554
|
const sql = buildInsertDebugSql(payload);
|
|
7555
|
+
const debugAst = debugAstEnabled ? buildInsertDebugAst(payload) : void 0;
|
|
6109
7556
|
return executeWithQueryTrace(
|
|
6110
7557
|
tracer,
|
|
6111
7558
|
{
|
|
@@ -6114,6 +7561,7 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6114
7561
|
table: resolvedTableName,
|
|
6115
7562
|
sql,
|
|
6116
7563
|
payload,
|
|
7564
|
+
ast: debugAst,
|
|
6117
7565
|
options: mergedOptions
|
|
6118
7566
|
},
|
|
6119
7567
|
async () => {
|
|
@@ -6144,6 +7592,7 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6144
7592
|
payload.default_to_null = mergedOptions.defaultToNull;
|
|
6145
7593
|
}
|
|
6146
7594
|
const sql = buildInsertDebugSql(payload);
|
|
7595
|
+
const debugAst = debugAstEnabled ? buildUpsertDebugAst(payload) : void 0;
|
|
6147
7596
|
return executeWithQueryTrace(
|
|
6148
7597
|
tracer,
|
|
6149
7598
|
{
|
|
@@ -6152,6 +7601,7 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6152
7601
|
table: resolvedTableName,
|
|
6153
7602
|
sql,
|
|
6154
7603
|
payload,
|
|
7604
|
+
ast: debugAst,
|
|
6155
7605
|
options: mergedOptions
|
|
6156
7606
|
},
|
|
6157
7607
|
async () => {
|
|
@@ -6179,6 +7629,7 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6179
7629
|
payload.default_to_null = mergedOptions.defaultToNull;
|
|
6180
7630
|
}
|
|
6181
7631
|
const sql = buildInsertDebugSql(payload);
|
|
7632
|
+
const debugAst = debugAstEnabled ? buildUpsertDebugAst(payload) : void 0;
|
|
6182
7633
|
return executeWithQueryTrace(
|
|
6183
7634
|
tracer,
|
|
6184
7635
|
{
|
|
@@ -6187,6 +7638,7 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6187
7638
|
table: resolvedTableName,
|
|
6188
7639
|
sql,
|
|
6189
7640
|
payload,
|
|
7641
|
+
ast: debugAst,
|
|
6190
7642
|
options: mergedOptions
|
|
6191
7643
|
},
|
|
6192
7644
|
async () => {
|
|
@@ -6201,7 +7653,8 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6201
7653
|
update(values, options) {
|
|
6202
7654
|
const mutationCallsite = captureTraceCallsite(tracer);
|
|
6203
7655
|
const executeUpdate = async (columns, selectOptions, callsite) => {
|
|
6204
|
-
const
|
|
7656
|
+
const executionState = snapshotState();
|
|
7657
|
+
const filters = executionState.conditions.length ? [...executionState.conditions] : void 0;
|
|
6205
7658
|
const mergedOptions = mergeOptions(options, selectOptions);
|
|
6206
7659
|
const resolvedTableName = resolveTableNameForCall(tableName, mergedOptions?.schema);
|
|
6207
7660
|
const payload = {
|
|
@@ -6210,12 +7663,16 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6210
7663
|
conditions: filters,
|
|
6211
7664
|
strip_nulls: mergedOptions?.stripNulls ?? true
|
|
6212
7665
|
};
|
|
6213
|
-
if (
|
|
6214
|
-
if (
|
|
6215
|
-
if (
|
|
6216
|
-
if (
|
|
7666
|
+
if (executionState.order) payload.sort_by = executionState.order;
|
|
7667
|
+
if (executionState.currentPage !== void 0) payload.current_page = executionState.currentPage;
|
|
7668
|
+
if (executionState.pageSize !== void 0) payload.page_size = executionState.pageSize;
|
|
7669
|
+
if (executionState.totalPages !== void 0) payload.total_pages = executionState.totalPages;
|
|
6217
7670
|
if (columns) payload.columns = columns;
|
|
6218
7671
|
const sql = buildUpdateDebugSql(payload);
|
|
7672
|
+
const debugAst = debugAstEnabled ? buildUpdateDebugAst({
|
|
7673
|
+
state: executionState,
|
|
7674
|
+
payload
|
|
7675
|
+
}) : void 0;
|
|
6219
7676
|
return executeWithQueryTrace(
|
|
6220
7677
|
tracer,
|
|
6221
7678
|
{
|
|
@@ -6224,6 +7681,7 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6224
7681
|
table: resolvedTableName,
|
|
6225
7682
|
sql,
|
|
6226
7683
|
payload,
|
|
7684
|
+
ast: debugAst,
|
|
6227
7685
|
options: mergedOptions
|
|
6228
7686
|
},
|
|
6229
7687
|
async () => {
|
|
@@ -6247,6 +7705,11 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6247
7705
|
}
|
|
6248
7706
|
const mutationCallsite = captureTraceCallsite(tracer);
|
|
6249
7707
|
const executeDelete = async (columns, selectOptions, callsite) => {
|
|
7708
|
+
const executionState = snapshotState();
|
|
7709
|
+
const debugState = {
|
|
7710
|
+
...executionState,
|
|
7711
|
+
conditions: filters ? filters.map((condition) => ({ ...condition })) : []
|
|
7712
|
+
};
|
|
6250
7713
|
const mergedOptions = mergeOptions(options, selectOptions);
|
|
6251
7714
|
const resolvedTableName = resolveTableNameForCall(tableName, mergedOptions?.schema);
|
|
6252
7715
|
const payload = {
|
|
@@ -6254,12 +7717,16 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6254
7717
|
resource_id: resourceId,
|
|
6255
7718
|
conditions: filters
|
|
6256
7719
|
};
|
|
6257
|
-
if (
|
|
6258
|
-
if (
|
|
6259
|
-
if (
|
|
6260
|
-
if (
|
|
7720
|
+
if (executionState.order) payload.sort_by = executionState.order;
|
|
7721
|
+
if (executionState.currentPage !== void 0) payload.current_page = executionState.currentPage;
|
|
7722
|
+
if (executionState.pageSize !== void 0) payload.page_size = executionState.pageSize;
|
|
7723
|
+
if (executionState.totalPages !== void 0) payload.total_pages = executionState.totalPages;
|
|
6261
7724
|
if (columns) payload.columns = columns;
|
|
6262
7725
|
const sql = buildDeleteDebugSql(payload);
|
|
7726
|
+
const debugAst = debugAstEnabled ? buildDeleteDebugAst({
|
|
7727
|
+
state: debugState,
|
|
7728
|
+
payload
|
|
7729
|
+
}) : void 0;
|
|
6263
7730
|
return executeWithQueryTrace(
|
|
6264
7731
|
tracer,
|
|
6265
7732
|
{
|
|
@@ -6268,6 +7735,7 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6268
7735
|
table: resolvedTableName,
|
|
6269
7736
|
sql,
|
|
6270
7737
|
payload,
|
|
7738
|
+
ast: debugAst,
|
|
6271
7739
|
options: mergedOptions
|
|
6272
7740
|
},
|
|
6273
7741
|
async () => {
|
|
@@ -6295,6 +7763,7 @@ function createTableBuilder(tableName, client, formatGatewayResult, tracer, expe
|
|
|
6295
7763
|
return builder;
|
|
6296
7764
|
}
|
|
6297
7765
|
function createQueryBuilder(client, formatGatewayResult, experimental, tracer) {
|
|
7766
|
+
const debugAstEnabled = Boolean(experimental?.debugAst);
|
|
6298
7767
|
return async function query(query, options) {
|
|
6299
7768
|
const normalizedQuery = query.trim();
|
|
6300
7769
|
if (!normalizedQuery) {
|
|
@@ -6311,6 +7780,7 @@ function createQueryBuilder(client, formatGatewayResult, experimental, tracer) {
|
|
|
6311
7780
|
endpoint: "/gateway/query",
|
|
6312
7781
|
sql: normalizedQuery,
|
|
6313
7782
|
payload,
|
|
7783
|
+
ast: debugAstEnabled ? buildRawQueryDebugAst(normalizedQuery) : void 0,
|
|
6314
7784
|
options
|
|
6315
7785
|
},
|
|
6316
7786
|
async () => {
|
|
@@ -6322,6 +7792,63 @@ function createQueryBuilder(client, formatGatewayResult, experimental, tracer) {
|
|
|
6322
7792
|
);
|
|
6323
7793
|
};
|
|
6324
7794
|
}
|
|
7795
|
+
function resolveClientServiceBaseUrl(value, label) {
|
|
7796
|
+
if (value === void 0 || value === null) {
|
|
7797
|
+
return void 0;
|
|
7798
|
+
}
|
|
7799
|
+
return normalizeAthenaGatewayBaseUrl(value, { label });
|
|
7800
|
+
}
|
|
7801
|
+
function appendServicePath(baseUrl, segment) {
|
|
7802
|
+
const normalizedBaseUrl = normalizeAthenaGatewayBaseUrl(baseUrl, { label: "Athena public base URL" });
|
|
7803
|
+
return `${normalizedBaseUrl}/${segment.replace(/^\/+/, "")}`;
|
|
7804
|
+
}
|
|
7805
|
+
function resolveServiceUrlOverride(value, label) {
|
|
7806
|
+
return resolveClientServiceBaseUrl(value, label);
|
|
7807
|
+
}
|
|
7808
|
+
function resolveServiceUrls(config) {
|
|
7809
|
+
const baseUrl = resolveClientServiceBaseUrl(config.url, "Athena public base URL");
|
|
7810
|
+
return {
|
|
7811
|
+
dbUrl: resolveServiceUrlOverride(config.db?.url, "Athena DB base URL") ?? resolveServiceUrlOverride(config.gateway?.url, "Athena gateway base URL") ?? resolveServiceUrlOverride(config.dbUrl, "Athena DB base URL") ?? resolveServiceUrlOverride(config.gatewayUrl, "Athena gateway base URL") ?? (baseUrl ? appendServicePath(baseUrl, "db") : void 0),
|
|
7812
|
+
authUrl: resolveServiceUrlOverride(config.auth?.url, "Athena auth base URL") ?? resolveServiceUrlOverride(config.auth?.baseUrl, "Athena auth base URL") ?? resolveServiceUrlOverride(config.authUrl, "Athena auth base URL") ?? (baseUrl ? appendServicePath(baseUrl, "auth") : void 0),
|
|
7813
|
+
storageUrl: resolveServiceUrlOverride(config.storage?.url, "Athena storage base URL") ?? resolveServiceUrlOverride(config.storageUrl, "Athena storage base URL") ?? (baseUrl ? appendServicePath(baseUrl, "storage") : void 0)
|
|
7814
|
+
};
|
|
7815
|
+
}
|
|
7816
|
+
function normalizeAuthClientConfig(auth, defaultBaseUrl) {
|
|
7817
|
+
if (!auth && defaultBaseUrl === void 0) {
|
|
7818
|
+
return void 0;
|
|
7819
|
+
}
|
|
7820
|
+
const { url, ...rest } = auth ?? {};
|
|
7821
|
+
const normalized = {
|
|
7822
|
+
...rest
|
|
7823
|
+
};
|
|
7824
|
+
const resolvedBaseUrl = resolveClientServiceBaseUrl(
|
|
7825
|
+
url ?? rest.baseUrl ?? defaultBaseUrl,
|
|
7826
|
+
"Athena auth base URL"
|
|
7827
|
+
);
|
|
7828
|
+
if (resolvedBaseUrl !== void 0) {
|
|
7829
|
+
normalized.baseUrl = resolvedBaseUrl;
|
|
7830
|
+
}
|
|
7831
|
+
return normalized;
|
|
7832
|
+
}
|
|
7833
|
+
function resolveCreateClientConfig(config) {
|
|
7834
|
+
const resolvedUrls = resolveServiceUrls(config);
|
|
7835
|
+
if (!resolvedUrls.dbUrl) {
|
|
7836
|
+
throw new Error(
|
|
7837
|
+
"Athena DB base URL is required. Pass createClient(url, key) for a unified root, or set db.url / gateway.url / gatewayUrl explicitly."
|
|
7838
|
+
);
|
|
7839
|
+
}
|
|
7840
|
+
return {
|
|
7841
|
+
baseUrl: resolvedUrls.dbUrl,
|
|
7842
|
+
apiKey: config.key,
|
|
7843
|
+
client: config.client,
|
|
7844
|
+
backend: toBackendConfig(config.backend),
|
|
7845
|
+
headers: config.headers,
|
|
7846
|
+
auth: config.auth,
|
|
7847
|
+
authUrl: resolvedUrls.authUrl,
|
|
7848
|
+
storageUrl: resolvedUrls.storageUrl,
|
|
7849
|
+
experimental: config.experimental
|
|
7850
|
+
};
|
|
7851
|
+
}
|
|
6325
7852
|
function createClientFromConfig(config) {
|
|
6326
7853
|
const gatewayHeaders = {
|
|
6327
7854
|
...config.headers ?? {}
|
|
@@ -6336,16 +7863,33 @@ function createClientFromConfig(config) {
|
|
|
6336
7863
|
backend: config.backend,
|
|
6337
7864
|
headers: gatewayHeaders
|
|
6338
7865
|
});
|
|
6339
|
-
const formatGatewayResult = createResultFormatter();
|
|
7866
|
+
const formatGatewayResult = createResultFormatter(config.experimental);
|
|
6340
7867
|
const queryTracer = createQueryTracer(config.experimental);
|
|
6341
|
-
const auth = createAuthClient(config.auth);
|
|
6342
|
-
|
|
6343
|
-
|
|
6344
|
-
|
|
6345
|
-
|
|
6346
|
-
|
|
6347
|
-
|
|
6348
|
-
|
|
7868
|
+
const auth = createAuthClient(normalizeAuthClientConfig(config.auth, config.authUrl));
|
|
7869
|
+
function from(tableOrModel, options) {
|
|
7870
|
+
if (isAthenaModelTarget(tableOrModel)) {
|
|
7871
|
+
if (options?.schema !== void 0) {
|
|
7872
|
+
throw new Error(
|
|
7873
|
+
"from(model) does not accept a schema override because the model already defines its target."
|
|
7874
|
+
);
|
|
7875
|
+
}
|
|
7876
|
+
return createTableBuilder(
|
|
7877
|
+
resolveAthenaModelTargetTableName(tableOrModel),
|
|
7878
|
+
gateway,
|
|
7879
|
+
formatGatewayResult,
|
|
7880
|
+
queryTracer,
|
|
7881
|
+
config.experimental
|
|
7882
|
+
);
|
|
7883
|
+
}
|
|
7884
|
+
const resolvedTableName = resolveTableNameForCall(tableOrModel, options?.schema);
|
|
7885
|
+
return createTableBuilder(
|
|
7886
|
+
resolvedTableName,
|
|
7887
|
+
gateway,
|
|
7888
|
+
formatGatewayResult,
|
|
7889
|
+
queryTracer,
|
|
7890
|
+
config.experimental
|
|
7891
|
+
);
|
|
7892
|
+
}
|
|
6349
7893
|
const rpc = (fn, args, options) => {
|
|
6350
7894
|
const normalizedFn = fn.trim();
|
|
6351
7895
|
if (!normalizedFn) {
|
|
@@ -6358,10 +7902,16 @@ function createClientFromConfig(config) {
|
|
|
6358
7902
|
gateway,
|
|
6359
7903
|
formatGatewayResult,
|
|
6360
7904
|
queryTracer,
|
|
6361
|
-
captureTraceCallsite(queryTracer)
|
|
7905
|
+
captureTraceCallsite(queryTracer),
|
|
7906
|
+
Boolean(config.experimental?.debugAst)
|
|
6362
7907
|
);
|
|
6363
7908
|
};
|
|
6364
|
-
const query = createQueryBuilder(
|
|
7909
|
+
const query = createQueryBuilder(
|
|
7910
|
+
gateway,
|
|
7911
|
+
formatGatewayResult,
|
|
7912
|
+
config.experimental,
|
|
7913
|
+
queryTracer
|
|
7914
|
+
);
|
|
6365
7915
|
const db = createDbModule({ from, rpc, query });
|
|
6366
7916
|
const sdkClient = {
|
|
6367
7917
|
from,
|
|
@@ -6374,27 +7924,27 @@ function createClientFromConfig(config) {
|
|
|
6374
7924
|
if (config.experimental?.athenaStorageBackend) {
|
|
6375
7925
|
const storageClient = {
|
|
6376
7926
|
...sdkClient,
|
|
6377
|
-
storage: createStorageModule(gateway,
|
|
7927
|
+
storage: createStorageModule(gateway, {
|
|
7928
|
+
...config.experimental.storage,
|
|
7929
|
+
...config.storageUrl ? {
|
|
7930
|
+
baseUrl: config.storageUrl,
|
|
7931
|
+
stripBasePath: true
|
|
7932
|
+
} : {}
|
|
7933
|
+
})
|
|
6378
7934
|
};
|
|
6379
7935
|
return storageClient;
|
|
6380
7936
|
}
|
|
6381
7937
|
return sdkClient;
|
|
6382
7938
|
}
|
|
6383
|
-
|
|
6384
|
-
|
|
6385
|
-
|
|
6386
|
-
|
|
6387
|
-
|
|
6388
|
-
|
|
6389
|
-
|
|
6390
|
-
|
|
6391
|
-
|
|
6392
|
-
client: options?.client,
|
|
6393
|
-
backend: toBackendConfig(options?.backend),
|
|
6394
|
-
headers: options?.headers,
|
|
6395
|
-
auth: options?.auth,
|
|
6396
|
-
experimental: options?.experimental
|
|
6397
|
-
});
|
|
7939
|
+
function createClient(configOrUrl, apiKey, options) {
|
|
7940
|
+
if (typeof configOrUrl === "string") {
|
|
7941
|
+
return createClientFromConfig(resolveCreateClientConfig({
|
|
7942
|
+
url: configOrUrl,
|
|
7943
|
+
key: apiKey ?? "",
|
|
7944
|
+
...options
|
|
7945
|
+
}));
|
|
7946
|
+
}
|
|
7947
|
+
return createClientFromConfig(resolveCreateClientConfig(configOrUrl));
|
|
6398
7948
|
}
|
|
6399
7949
|
|
|
6400
7950
|
// src/schema/postgres-introspection-core.ts
|
|
@@ -6991,6 +8541,7 @@ function rootUsage() {
|
|
|
6991
8541
|
"",
|
|
6992
8542
|
"Examples:",
|
|
6993
8543
|
" athena-js generate",
|
|
8544
|
+
" DATABASE_URL=postgres://postgres:postgres@127.0.0.1:5432/app_db athena-js generate --dry-run",
|
|
6994
8545
|
" athena-js generate --config ./athena.config.ts --dry-run",
|
|
6995
8546
|
" athena-js generate --help"
|
|
6996
8547
|
].join("\n");
|
|
@@ -7007,8 +8558,14 @@ function generateUsage() {
|
|
|
7007
8558
|
" --dry-run Build generated files in memory without writing them to disk",
|
|
7008
8559
|
" -h, --help Show help for generate",
|
|
7009
8560
|
"",
|
|
8561
|
+
"Config resolution:",
|
|
8562
|
+
" - uses athena.config.* discovery first",
|
|
8563
|
+
" - falls back to env-only direct mode when DATABASE_URL/PG_URL is present",
|
|
8564
|
+
" - falls back to env-only gateway mode when ATHENA_URL + ATHENA_API_KEY are present",
|
|
8565
|
+
"",
|
|
7010
8566
|
"Examples:",
|
|
7011
8567
|
" athena-js generate",
|
|
8568
|
+
" DATABASE_URL=postgres://postgres:postgres@127.0.0.1:5432/app_db athena-js generate --dry-run",
|
|
7012
8569
|
" athena-js generate --config ./athena.config.ts --dry-run"
|
|
7013
8570
|
].join("\n");
|
|
7014
8571
|
}
|