@holo-js/adapter-shared 0.3.19 → 0.3.20
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/build.d.ts +3 -1
- package/dist/build.mjs +3 -1
- package/dist/{chunk-4DGYQBYZ.mjs → chunk-6FHRFQPC.mjs} +128 -30
- package/dist/index.d.ts +1 -1
- package/dist/index.mjs +3 -1
- package/dist/server-errors.d.ts +15 -0
- package/dist/server-errors.mjs +24 -0
- package/package.json +7 -2
package/dist/build.d.ts
CHANGED
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
declare function compileBrowserValidation(source: string, fileName?: string): string | undefined;
|
|
2
2
|
|
|
3
|
+
declare function compileNextRoute(source: string, filename: string): string;
|
|
4
|
+
|
|
3
5
|
type RealtimeDefinitionSourceMap = {
|
|
4
6
|
readonly version: 3;
|
|
5
7
|
readonly file: string;
|
|
@@ -19,4 +21,4 @@ declare function stripRealtimeServerHandlers(source: string): string;
|
|
|
19
21
|
declare function createRealtimeClientDefinitionModule(source: string, importTarget: string): string;
|
|
20
22
|
declare function createRealtimeClientDefinitionTransform(source: string, importTarget: string, options?: RealtimeDefinitionTransformOptions): RealtimeDefinitionTransformResult;
|
|
21
23
|
|
|
22
|
-
export { type RealtimeDefinitionSourceMap, type RealtimeDefinitionTransformOptions, type RealtimeDefinitionTransformResult, compileBrowserValidation, createRealtimeClientDefinitionModule, createRealtimeClientDefinitionTransform, stripRealtimeServerHandlers };
|
|
24
|
+
export { type RealtimeDefinitionSourceMap, type RealtimeDefinitionTransformOptions, type RealtimeDefinitionTransformResult, compileBrowserValidation, compileNextRoute, createRealtimeClientDefinitionModule, createRealtimeClientDefinitionTransform, stripRealtimeServerHandlers };
|
package/dist/build.mjs
CHANGED
|
@@ -1,11 +1,13 @@
|
|
|
1
1
|
import {
|
|
2
2
|
compileBrowserValidation,
|
|
3
|
+
compileNextRoute,
|
|
3
4
|
createRealtimeClientDefinitionModule,
|
|
4
5
|
createRealtimeClientDefinitionTransform,
|
|
5
6
|
stripRealtimeServerHandlers
|
|
6
|
-
} from "./chunk-
|
|
7
|
+
} from "./chunk-6FHRFQPC.mjs";
|
|
7
8
|
export {
|
|
8
9
|
compileBrowserValidation,
|
|
10
|
+
compileNextRoute,
|
|
9
11
|
createRealtimeClientDefinitionModule,
|
|
10
12
|
createRealtimeClientDefinitionTransform,
|
|
11
13
|
stripRealtimeServerHandlers
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
// src/build.ts
|
|
2
|
-
import
|
|
2
|
+
import ts3 from "typescript";
|
|
3
3
|
|
|
4
4
|
// src/validation-transform.ts
|
|
5
5
|
import ts from "typescript";
|
|
@@ -143,10 +143,107 @@ import * as ${runtime} from '@holo-js/validation/internal/compiled'
|
|
|
143
143
|
`;
|
|
144
144
|
}
|
|
145
145
|
|
|
146
|
+
// src/next-route-transform.ts
|
|
147
|
+
import ts2 from "typescript";
|
|
148
|
+
var METHODS = /* @__PURE__ */ new Set(["GET", "HEAD", "OPTIONS", "POST", "PUT", "PATCH", "DELETE"]);
|
|
149
|
+
var runtimeName = "__holoRouteRuntime";
|
|
150
|
+
function wrap(handler) {
|
|
151
|
+
return ts2.factory.createCallExpression(
|
|
152
|
+
ts2.factory.createPropertyAccessExpression(ts2.factory.createIdentifier(runtimeName), "routeHandler"),
|
|
153
|
+
void 0,
|
|
154
|
+
[handler]
|
|
155
|
+
);
|
|
156
|
+
}
|
|
157
|
+
function exportHandler(name, handler) {
|
|
158
|
+
return ts2.factory.createVariableStatement(
|
|
159
|
+
[ts2.factory.createModifier(ts2.SyntaxKind.ExportKeyword)],
|
|
160
|
+
ts2.factory.createVariableDeclarationList([
|
|
161
|
+
ts2.factory.createVariableDeclaration(name, void 0, void 0, wrap(handler))
|
|
162
|
+
], ts2.NodeFlags.Const)
|
|
163
|
+
);
|
|
164
|
+
}
|
|
165
|
+
function compileNextRoute(source, filename) {
|
|
166
|
+
const file = ts2.createSourceFile(filename, source, ts2.ScriptTarget.Latest, true, ts2.ScriptKind.TS);
|
|
167
|
+
let changed = false;
|
|
168
|
+
const statements = file.statements.flatMap((statement) => {
|
|
169
|
+
if (ts2.isFunctionDeclaration(statement) && statement.name && METHODS.has(statement.name.text) && statement.modifiers?.some((modifier) => modifier.kind === ts2.SyntaxKind.ExportKeyword)) {
|
|
170
|
+
changed = true;
|
|
171
|
+
const name = statement.name.text;
|
|
172
|
+
const localName = ts2.factory.createIdentifier(`__holoOriginal${name}`);
|
|
173
|
+
return [ts2.factory.updateFunctionDeclaration(
|
|
174
|
+
statement,
|
|
175
|
+
statement.modifiers.filter((modifier) => modifier.kind !== ts2.SyntaxKind.ExportKeyword),
|
|
176
|
+
statement.asteriskToken,
|
|
177
|
+
localName,
|
|
178
|
+
statement.typeParameters,
|
|
179
|
+
statement.parameters,
|
|
180
|
+
statement.type,
|
|
181
|
+
statement.body
|
|
182
|
+
), exportHandler(name, localName)];
|
|
183
|
+
}
|
|
184
|
+
if (ts2.isVariableStatement(statement) && statement.modifiers?.some((modifier) => modifier.kind === ts2.SyntaxKind.ExportKeyword)) {
|
|
185
|
+
const declarations = statement.declarationList.declarations.map((declaration) => {
|
|
186
|
+
if (!ts2.isIdentifier(declaration.name) || !METHODS.has(declaration.name.text) || !declaration.initializer) return declaration;
|
|
187
|
+
changed = true;
|
|
188
|
+
return ts2.factory.updateVariableDeclaration(
|
|
189
|
+
declaration,
|
|
190
|
+
declaration.name,
|
|
191
|
+
declaration.exclamationToken,
|
|
192
|
+
declaration.type,
|
|
193
|
+
wrap(declaration.initializer)
|
|
194
|
+
);
|
|
195
|
+
});
|
|
196
|
+
return [ts2.factory.updateVariableStatement(
|
|
197
|
+
statement,
|
|
198
|
+
statement.modifiers,
|
|
199
|
+
ts2.factory.updateVariableDeclarationList(statement.declarationList, declarations)
|
|
200
|
+
)];
|
|
201
|
+
}
|
|
202
|
+
if (ts2.isExportDeclaration(statement) && statement.exportClause && ts2.isNamedExports(statement.exportClause)) {
|
|
203
|
+
const handlers = statement.exportClause.elements.filter((element) => METHODS.has(element.name.text));
|
|
204
|
+
if (handlers.length === 0) return [statement];
|
|
205
|
+
changed = true;
|
|
206
|
+
const result = [];
|
|
207
|
+
const remaining = statement.exportClause.elements.filter((element) => !METHODS.has(element.name.text));
|
|
208
|
+
if (remaining.length) result.push(ts2.factory.updateExportDeclaration(
|
|
209
|
+
statement,
|
|
210
|
+
statement.modifiers,
|
|
211
|
+
statement.isTypeOnly,
|
|
212
|
+
ts2.factory.updateNamedExports(statement.exportClause, remaining),
|
|
213
|
+
statement.moduleSpecifier,
|
|
214
|
+
statement.attributes
|
|
215
|
+
));
|
|
216
|
+
for (const handler of handlers) {
|
|
217
|
+
const imported = handler.propertyName ?? handler.name;
|
|
218
|
+
const local = ts2.factory.createIdentifier(statement.moduleSpecifier ? `__holoOriginal${handler.name.text}` : imported.text);
|
|
219
|
+
if (statement.moduleSpecifier) result.push(ts2.factory.createImportDeclaration(
|
|
220
|
+
void 0,
|
|
221
|
+
ts2.factory.createImportClause(false, void 0, ts2.factory.createNamedImports([
|
|
222
|
+
ts2.factory.createImportSpecifier(false, imported, local)
|
|
223
|
+
])),
|
|
224
|
+
statement.moduleSpecifier
|
|
225
|
+
));
|
|
226
|
+
result.push(exportHandler(handler.name.text, local));
|
|
227
|
+
}
|
|
228
|
+
return result;
|
|
229
|
+
}
|
|
230
|
+
return [statement];
|
|
231
|
+
});
|
|
232
|
+
if (!changed) return source;
|
|
233
|
+
const runtimeImport = ts2.factory.createImportDeclaration(
|
|
234
|
+
void 0,
|
|
235
|
+
ts2.factory.createImportClause(false, void 0, ts2.factory.createNamedImports([
|
|
236
|
+
ts2.factory.createImportSpecifier(false, ts2.factory.createIdentifier("adapterNextRuntimeInternals"), ts2.factory.createIdentifier(runtimeName))
|
|
237
|
+
])),
|
|
238
|
+
ts2.factory.createStringLiteral("@holo-js/adapter-next/runtime")
|
|
239
|
+
);
|
|
240
|
+
return ts2.createPrinter().printFile(ts2.factory.updateSourceFile(file, [runtimeImport, ...statements]));
|
|
241
|
+
}
|
|
242
|
+
|
|
146
243
|
// src/build.ts
|
|
147
244
|
function propertyName(property) {
|
|
148
245
|
if (!("name" in property) || !property.name) return void 0;
|
|
149
|
-
return
|
|
246
|
+
return ts3.isIdentifier(property.name) || ts3.isStringLiteral(property.name) ? property.name.text : void 0;
|
|
150
247
|
}
|
|
151
248
|
function collectRealtimeFactories(sourceFile) {
|
|
152
249
|
const factories = /* @__PURE__ */ new Map([
|
|
@@ -154,9 +251,9 @@ function collectRealtimeFactories(sourceFile) {
|
|
|
154
251
|
["mutation", "mutation"]
|
|
155
252
|
]);
|
|
156
253
|
for (const statement of sourceFile.statements) {
|
|
157
|
-
if (!
|
|
158
|
-
if (!
|
|
159
|
-
if (!
|
|
254
|
+
if (!ts3.isImportDeclaration(statement) || !statement.importClause?.namedBindings) continue;
|
|
255
|
+
if (!ts3.isStringLiteral(statement.moduleSpecifier) || statement.moduleSpecifier.text !== "@holo-js/realtime") continue;
|
|
256
|
+
if (!ts3.isNamedImports(statement.importClause.namedBindings)) continue;
|
|
160
257
|
for (const element of statement.importClause.namedBindings.elements) {
|
|
161
258
|
const importedName = element.propertyName?.text ?? element.name.text;
|
|
162
259
|
if (importedName === "query" || importedName === "mutation") {
|
|
@@ -170,17 +267,17 @@ function collectDefinitions(sourceFile) {
|
|
|
170
267
|
const definitions = [];
|
|
171
268
|
const factories = collectRealtimeFactories(sourceFile);
|
|
172
269
|
for (const statement of sourceFile.statements) {
|
|
173
|
-
if (!
|
|
270
|
+
if (!ts3.isVariableStatement(statement) || !statement.modifiers?.some((modifier) => modifier.kind === ts3.SyntaxKind.ExportKeyword)) continue;
|
|
174
271
|
for (const declaration of statement.declarationList.declarations) {
|
|
175
|
-
if (!
|
|
272
|
+
if (!ts3.isIdentifier(declaration.name) || !declaration.initializer || !ts3.isCallExpression(declaration.initializer)) continue;
|
|
176
273
|
const factoryNode = declaration.initializer.expression;
|
|
177
|
-
if (!
|
|
274
|
+
if (!ts3.isIdentifier(factoryNode)) continue;
|
|
178
275
|
const factory = factories.get(factoryNode.text);
|
|
179
276
|
if (!factory) continue;
|
|
180
277
|
const definitionNode = declaration.initializer.arguments[0];
|
|
181
|
-
if (!definitionNode || !
|
|
278
|
+
if (!definitionNode || !ts3.isObjectLiteralExpression(definitionNode)) continue;
|
|
182
279
|
const nameProperty = definitionNode.properties.find((property) => propertyName(property) === "name");
|
|
183
|
-
const name = nameProperty &&
|
|
280
|
+
const name = nameProperty && ts3.isPropertyAssignment(nameProperty) ? nameProperty.initializer.getText(sourceFile) : void 0;
|
|
184
281
|
const sourceLine = sourceFile.getLineAndCharacterOfPosition(declaration.getStart(sourceFile)).line;
|
|
185
282
|
definitions.push({ exportedName: declaration.name.text, factory, sourceLine, ...name ? { name } : {} });
|
|
186
283
|
}
|
|
@@ -217,36 +314,36 @@ function createSourceMap(source, sourceLines) {
|
|
|
217
314
|
};
|
|
218
315
|
}
|
|
219
316
|
function parseRealtimeSource(source) {
|
|
220
|
-
const result =
|
|
221
|
-
compilerOptions: { module:
|
|
317
|
+
const result = ts3.transpileModule(source, {
|
|
318
|
+
compilerOptions: { module: ts3.ModuleKind.ESNext, target: ts3.ScriptTarget.ESNext },
|
|
222
319
|
reportDiagnostics: true
|
|
223
320
|
});
|
|
224
|
-
const diagnostic = result.diagnostics?.find((entry) => entry.category ===
|
|
321
|
+
const diagnostic = result.diagnostics?.find((entry) => entry.category === ts3.DiagnosticCategory.Error);
|
|
225
322
|
if (diagnostic) {
|
|
226
|
-
throw new SyntaxError(
|
|
323
|
+
throw new SyntaxError(ts3.flattenDiagnosticMessageText(diagnostic.messageText, "\n"));
|
|
227
324
|
}
|
|
228
|
-
return
|
|
325
|
+
return ts3.createSourceFile("realtime.ts", source, ts3.ScriptTarget.Latest, true, ts3.ScriptKind.TS);
|
|
229
326
|
}
|
|
230
327
|
function retargetRealtimeImports(source, importTarget) {
|
|
231
328
|
const sourceFile = parseRealtimeSource(source);
|
|
232
329
|
const transformer = (context) => (root) => {
|
|
233
330
|
const visit = (node) => {
|
|
234
|
-
if (
|
|
235
|
-
return
|
|
331
|
+
if (ts3.isImportDeclaration(node) && ts3.isStringLiteral(node.moduleSpecifier) && node.moduleSpecifier.text === "@holo-js/realtime") {
|
|
332
|
+
return ts3.factory.updateImportDeclaration(
|
|
236
333
|
node,
|
|
237
334
|
node.modifiers,
|
|
238
335
|
node.importClause,
|
|
239
|
-
|
|
336
|
+
ts3.factory.createStringLiteral(importTarget),
|
|
240
337
|
node.attributes
|
|
241
338
|
);
|
|
242
339
|
}
|
|
243
|
-
return
|
|
340
|
+
return ts3.visitEachChild(node, visit, context);
|
|
244
341
|
};
|
|
245
|
-
return
|
|
342
|
+
return ts3.visitNode(root, visit);
|
|
246
343
|
};
|
|
247
|
-
const result =
|
|
344
|
+
const result = ts3.transform(sourceFile, [transformer]);
|
|
248
345
|
try {
|
|
249
|
-
return
|
|
346
|
+
return ts3.createPrinter({ newLine: ts3.NewLineKind.LineFeed }).printFile(result.transformed[0]);
|
|
250
347
|
} finally {
|
|
251
348
|
result.dispose();
|
|
252
349
|
}
|
|
@@ -255,19 +352,19 @@ function stripRealtimeServerHandlers(source) {
|
|
|
255
352
|
const sourceFile = parseRealtimeSource(source);
|
|
256
353
|
const transformer = (context) => (root) => {
|
|
257
354
|
const visit = (node) => {
|
|
258
|
-
if (
|
|
259
|
-
return
|
|
355
|
+
if (ts3.isPropertyAssignment(node) && (propertyName(node) === "handler" || propertyName(node) === "authorize")) {
|
|
356
|
+
return ts3.factory.updatePropertyAssignment(node, node.name, ts3.factory.createIdentifier("undefined"));
|
|
260
357
|
}
|
|
261
|
-
if (
|
|
262
|
-
return
|
|
358
|
+
if (ts3.isMethodDeclaration(node) && (propertyName(node) === "handler" || propertyName(node) === "authorize")) {
|
|
359
|
+
return ts3.factory.createPropertyAssignment(node.name, ts3.factory.createIdentifier("undefined"));
|
|
263
360
|
}
|
|
264
|
-
return
|
|
361
|
+
return ts3.visitEachChild(node, visit, context);
|
|
265
362
|
};
|
|
266
|
-
return
|
|
363
|
+
return ts3.visitNode(root, visit);
|
|
267
364
|
};
|
|
268
|
-
const result =
|
|
365
|
+
const result = ts3.transform(sourceFile, [transformer]);
|
|
269
366
|
try {
|
|
270
|
-
return
|
|
367
|
+
return ts3.createPrinter({ newLine: ts3.NewLineKind.LineFeed }).printFile(result.transformed[0]);
|
|
271
368
|
} finally {
|
|
272
369
|
result.dispose();
|
|
273
370
|
}
|
|
@@ -318,6 +415,7 @@ function createRealtimeClientDefinitionTransform(source, importTarget, options =
|
|
|
318
415
|
|
|
319
416
|
export {
|
|
320
417
|
compileBrowserValidation,
|
|
418
|
+
compileNextRoute,
|
|
321
419
|
stripRealtimeServerHandlers,
|
|
322
420
|
createRealtimeClientDefinitionModule,
|
|
323
421
|
createRealtimeClientDefinitionTransform
|
package/dist/index.d.ts
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
export { HoloHttpErrorStatus, NormalizedHoloHttpError, isHoloHttpErrorStatus, normalizeHoloHttpError } from '@holo-js/kernel/http-errors';
|
|
2
2
|
export { ClientErrorPageOptions, renderClientHttpErrorPage } from './client.js';
|
|
3
|
-
export { RealtimeDefinitionSourceMap, RealtimeDefinitionTransformOptions, RealtimeDefinitionTransformResult, compileBrowserValidation, createRealtimeClientDefinitionModule, createRealtimeClientDefinitionTransform, stripRealtimeServerHandlers } from './build.js';
|
|
3
|
+
export { RealtimeDefinitionSourceMap, RealtimeDefinitionTransformOptions, RealtimeDefinitionTransformResult, compileBrowserValidation, compileNextRoute, createRealtimeClientDefinitionModule, createRealtimeClientDefinitionTransform, stripRealtimeServerHandlers } from './build.js';
|
package/dist/index.mjs
CHANGED
|
@@ -5,12 +5,14 @@ import {
|
|
|
5
5
|
} from "./chunk-3GNER7MY.mjs";
|
|
6
6
|
import {
|
|
7
7
|
compileBrowserValidation,
|
|
8
|
+
compileNextRoute,
|
|
8
9
|
createRealtimeClientDefinitionModule,
|
|
9
10
|
createRealtimeClientDefinitionTransform,
|
|
10
11
|
stripRealtimeServerHandlers
|
|
11
|
-
} from "./chunk-
|
|
12
|
+
} from "./chunk-6FHRFQPC.mjs";
|
|
12
13
|
export {
|
|
13
14
|
compileBrowserValidation,
|
|
15
|
+
compileNextRoute,
|
|
14
16
|
createRealtimeClientDefinitionModule,
|
|
15
17
|
createRealtimeClientDefinitionTransform,
|
|
16
18
|
isHoloHttpErrorStatus,
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
type RateLimitFailure = {
|
|
2
|
+
readonly ok: false;
|
|
3
|
+
readonly valid: false;
|
|
4
|
+
readonly status: 429;
|
|
5
|
+
readonly bag: 'default';
|
|
6
|
+
readonly message: string;
|
|
7
|
+
readonly errors: {
|
|
8
|
+
readonly _root: readonly string[];
|
|
9
|
+
};
|
|
10
|
+
readonly values: Readonly<Record<string, never>>;
|
|
11
|
+
readonly retryAfterSeconds?: number;
|
|
12
|
+
};
|
|
13
|
+
declare function serializeRateLimitError(error: unknown): RateLimitFailure | undefined;
|
|
14
|
+
|
|
15
|
+
export { serializeRateLimitError };
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
// src/server-errors.ts
|
|
2
|
+
import { normalizeHoloHttpError } from "@holo-js/kernel/http-errors";
|
|
3
|
+
function serializeRateLimitError(error) {
|
|
4
|
+
const normalized = normalizeHoloHttpError(error);
|
|
5
|
+
if (!normalized || normalized.status !== 429) return void 0;
|
|
6
|
+
const retryAfterSeconds = error && typeof error === "object" && "retryAfterSeconds" in error && typeof error.retryAfterSeconds === "number" && Number.isFinite(error.retryAfterSeconds) ? error.retryAfterSeconds : void 0;
|
|
7
|
+
if (retryAfterSeconds === void 0 && error && typeof error === "object" && "cause" in error) {
|
|
8
|
+
const cause = serializeRateLimitError(error.cause);
|
|
9
|
+
if (cause) return cause;
|
|
10
|
+
}
|
|
11
|
+
return {
|
|
12
|
+
ok: false,
|
|
13
|
+
valid: false,
|
|
14
|
+
status: 429,
|
|
15
|
+
bag: "default",
|
|
16
|
+
message: normalized.message,
|
|
17
|
+
errors: { _root: [normalized.message] },
|
|
18
|
+
values: {},
|
|
19
|
+
...retryAfterSeconds === void 0 ? {} : { retryAfterSeconds }
|
|
20
|
+
};
|
|
21
|
+
}
|
|
22
|
+
export {
|
|
23
|
+
serializeRateLimitError
|
|
24
|
+
};
|
package/package.json
CHANGED
|
@@ -1,10 +1,15 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@holo-js/adapter-shared",
|
|
3
|
-
"version": "0.3.
|
|
3
|
+
"version": "0.3.20",
|
|
4
4
|
"description": "Holo-JS Framework - shared framework adapter infrastructure",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "MIT",
|
|
7
7
|
"exports": {
|
|
8
|
+
"./server-errors": {
|
|
9
|
+
"types": "./dist/server-errors.d.ts",
|
|
10
|
+
"import": "./dist/server-errors.mjs",
|
|
11
|
+
"default": "./dist/server-errors.mjs"
|
|
12
|
+
},
|
|
8
13
|
".": {
|
|
9
14
|
"types": "./dist/index.d.ts",
|
|
10
15
|
"import": "./dist/index.mjs",
|
|
@@ -46,7 +51,7 @@
|
|
|
46
51
|
"test": "vitest --run"
|
|
47
52
|
},
|
|
48
53
|
"dependencies": {
|
|
49
|
-
"@holo-js/kernel": "^0.3.
|
|
54
|
+
"@holo-js/kernel": "^0.3.20",
|
|
50
55
|
"typescript": "^5.7.2"
|
|
51
56
|
},
|
|
52
57
|
"devDependencies": {
|