@marko/run 0.11.0-rc.1 → 0.11.0-rc.3
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/.tsbuildinfo +1 -1
- package/dist/adapter/index.cjs +3 -3
- package/dist/adapter/index.js +3 -3
- package/dist/cli/index.mjs +20 -8
- package/dist/runtime/internal.cjs +104 -69
- package/dist/runtime/internal.d.ts +3 -2
- package/dist/runtime/internal.js +103 -69
- package/dist/runtime/thenable.d.ts +11 -0
- package/dist/runtime/types.d.ts +99 -57
- package/dist/vite/constants.d.ts +1 -1
- package/dist/vite/index.cjs +20 -8
- package/dist/vite/index.js +20 -8
- package/package.json +19 -7
|
@@ -22,6 +22,7 @@ var internal_exports = {};
|
|
|
22
22
|
__export(internal_exports, {
|
|
23
23
|
NotHandled: () => NotHandled,
|
|
24
24
|
NotMatched: () => NotMatched,
|
|
25
|
+
assertHandlerVerb: () => assertHandlerVerb,
|
|
25
26
|
call: () => call,
|
|
26
27
|
compose: () => compose,
|
|
27
28
|
createContext: () => createContext,
|
|
@@ -58,6 +59,28 @@ var httpVerbs = [
|
|
|
58
59
|
"options"
|
|
59
60
|
];
|
|
60
61
|
|
|
62
|
+
// src/runtime/thenable.ts
|
|
63
|
+
var kPromise = /* @__PURE__ */ Symbol("promise");
|
|
64
|
+
var kReadFn = /* @__PURE__ */ Symbol("read fn");
|
|
65
|
+
function thenFn(resolve, reject) {
|
|
66
|
+
return (this[kPromise] || (this[kPromise] = this[kReadFn]())).then(resolve, reject);
|
|
67
|
+
}
|
|
68
|
+
function catchFn(reject) {
|
|
69
|
+
return (this[kPromise] || (this[kPromise] = this[kReadFn]())).catch(reject);
|
|
70
|
+
}
|
|
71
|
+
function finallyFn(resolve) {
|
|
72
|
+
return (this[kPromise] || (this[kPromise] = this[kReadFn]())).finally(resolve);
|
|
73
|
+
}
|
|
74
|
+
function thenable(fn) {
|
|
75
|
+
return {
|
|
76
|
+
[kPromise]: null,
|
|
77
|
+
[kReadFn]: fn,
|
|
78
|
+
then: thenFn,
|
|
79
|
+
catch: catchFn,
|
|
80
|
+
finally: finallyFn
|
|
81
|
+
};
|
|
82
|
+
}
|
|
83
|
+
|
|
61
84
|
// src/runtime/url-builder.ts
|
|
62
85
|
var encode = encodeURIComponent;
|
|
63
86
|
var pathParts = /* @__PURE__ */ new Map();
|
|
@@ -162,18 +185,16 @@ globalThis.MarkoRun ?? (globalThis.MarkoRun = {
|
|
|
162
185
|
NotHandled,
|
|
163
186
|
NotMatched
|
|
164
187
|
});
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
globalThis.Run = namespace;
|
|
176
|
-
}
|
|
188
|
+
globalThis.Run ?? (globalThis.Run = {
|
|
189
|
+
href,
|
|
190
|
+
ALL: createDefineHandler("ALL"),
|
|
191
|
+
...Object.fromEntries(
|
|
192
|
+
httpVerbs.map((v) => {
|
|
193
|
+
const verb = v.toUpperCase();
|
|
194
|
+
return [v.toUpperCase(), createDefineHandler(verb)];
|
|
195
|
+
})
|
|
196
|
+
)
|
|
197
|
+
});
|
|
177
198
|
var toReadable = (rendered) => {
|
|
178
199
|
toReadable = rendered.toReadable ? (rendered2) => rendered2.toReadable() : (rendered2) => {
|
|
179
200
|
let cancelled = false;
|
|
@@ -241,6 +262,29 @@ async function readBodyWithLimit(request, maxBytes) {
|
|
|
241
262
|
bytes.subarray(0, receivedBytes)
|
|
242
263
|
);
|
|
243
264
|
}
|
|
265
|
+
async function readBody(route, context) {
|
|
266
|
+
const { request } = context;
|
|
267
|
+
const contentType = request.headers.get("Content-Type");
|
|
268
|
+
if (contentType == null ? void 0 : contentType.includes("application/json")) {
|
|
269
|
+
const { maxBytes: maxBytes2, validator: validator2 } = route.options.json;
|
|
270
|
+
const json = maxBytes2 < 0 ? await request.json() : JSON.parse(await readBodyWithLimit(request, maxBytes2));
|
|
271
|
+
return validator2 ? validator2(json) : json;
|
|
272
|
+
}
|
|
273
|
+
const { maxBytes, maxParts, maxFiles, maxFileBytes, onFile, validator } = route.options.form;
|
|
274
|
+
const data = searchParamsToObject(
|
|
275
|
+
(contentType == null ? void 0 : contentType.includes("multipart/form-data")) ? await (0, import_form_data_parser.parseFormData)(
|
|
276
|
+
request,
|
|
277
|
+
{
|
|
278
|
+
maxParts,
|
|
279
|
+
maxFiles,
|
|
280
|
+
maxFileSize: maxFileBytes,
|
|
281
|
+
maxTotalSize: maxBytes
|
|
282
|
+
},
|
|
283
|
+
onFile ? (file) => onFile(context, file) : void 0
|
|
284
|
+
) : new import_node_url.URLSearchParams(await readBodyWithLimit(request, maxBytes))
|
|
285
|
+
);
|
|
286
|
+
return validator && validator(data);
|
|
287
|
+
}
|
|
244
288
|
function createContext(route, request, platform, url = new URL(request.url)) {
|
|
245
289
|
const context = {
|
|
246
290
|
route: (route == null ? void 0 : route.path) || "",
|
|
@@ -265,45 +309,7 @@ function createContext(route, request, platform, url = new URL(request.url)) {
|
|
|
265
309
|
});
|
|
266
310
|
return value;
|
|
267
311
|
},
|
|
268
|
-
body: route && request.body ?
|
|
269
|
-
const contentType = request.headers.get("Content-Type");
|
|
270
|
-
let value;
|
|
271
|
-
if (contentType == null ? void 0 : contentType.includes("application/json")) {
|
|
272
|
-
const { maxBytes, validator } = route.options.json;
|
|
273
|
-
const json = maxBytes < 0 ? await request.json() : JSON.parse(await readBodyWithLimit(request, maxBytes));
|
|
274
|
-
value = validator ? validator(json) : json;
|
|
275
|
-
} else {
|
|
276
|
-
const {
|
|
277
|
-
maxBytes,
|
|
278
|
-
maxParts,
|
|
279
|
-
maxFiles,
|
|
280
|
-
maxFileBytes,
|
|
281
|
-
onFile,
|
|
282
|
-
validator
|
|
283
|
-
} = route.options.form;
|
|
284
|
-
const data = searchParamsToObject(
|
|
285
|
-
(contentType == null ? void 0 : contentType.includes("multipart/form-data")) ? await (0, import_form_data_parser.parseFormData)(
|
|
286
|
-
request,
|
|
287
|
-
{
|
|
288
|
-
maxParts,
|
|
289
|
-
maxFiles,
|
|
290
|
-
maxFileSize: maxFileBytes,
|
|
291
|
-
maxTotalSize: maxBytes
|
|
292
|
-
},
|
|
293
|
-
onFile ? (file) => onFile(context, file) : void 0
|
|
294
|
-
) : new import_node_url.URLSearchParams(
|
|
295
|
-
await readBodyWithLimit(request, maxBytes)
|
|
296
|
-
)
|
|
297
|
-
);
|
|
298
|
-
value = validator ? validator(data) : validator;
|
|
299
|
-
}
|
|
300
|
-
Object.defineProperty(context, "body", {
|
|
301
|
-
configurable: true,
|
|
302
|
-
enumerable: true,
|
|
303
|
-
value
|
|
304
|
-
});
|
|
305
|
-
return value;
|
|
306
|
-
} : void 0,
|
|
312
|
+
body: route && request.body ? thenable(() => readBody(route, context)) : void 0,
|
|
307
313
|
data: {},
|
|
308
314
|
url,
|
|
309
315
|
request,
|
|
@@ -357,11 +363,22 @@ function render(context, template, input, data) {
|
|
|
357
363
|
}
|
|
358
364
|
return context.render(template, input);
|
|
359
365
|
}
|
|
366
|
+
var handlerMethod = /* @__PURE__ */ new WeakMap();
|
|
360
367
|
async function call(handler, next, context, data) {
|
|
361
368
|
let response;
|
|
362
369
|
if (data) {
|
|
363
370
|
Object.assign(context.data, data);
|
|
364
371
|
}
|
|
372
|
+
let method = handlerMethod.get(handler);
|
|
373
|
+
if (method === void 0) {
|
|
374
|
+
handlerMethod.set(
|
|
375
|
+
handler,
|
|
376
|
+
method = "verb" in handler && handler.verb !== "ALL" ? handler.verb : false
|
|
377
|
+
);
|
|
378
|
+
}
|
|
379
|
+
if (method && method !== context.method) {
|
|
380
|
+
return next(data);
|
|
381
|
+
}
|
|
365
382
|
if (!process.env.NODE_ENV || process.env.NODE_ENV === "development") {
|
|
366
383
|
let nextCallCount = 0;
|
|
367
384
|
let didThrow = false;
|
|
@@ -402,7 +419,7 @@ async function call(handler, next, context, data) {
|
|
|
402
419
|
if (response === null || response === NotMatched || response === NotHandled) {
|
|
403
420
|
throw response || NotMatched;
|
|
404
421
|
}
|
|
405
|
-
return response || next();
|
|
422
|
+
return response || next(data);
|
|
406
423
|
}
|
|
407
424
|
function compose(handlers) {
|
|
408
425
|
const len = handlers.length;
|
|
@@ -435,25 +452,37 @@ function normalizeHandler(obj) {
|
|
|
435
452
|
}
|
|
436
453
|
return passthrough;
|
|
437
454
|
}
|
|
438
|
-
function
|
|
455
|
+
function assertHandlerVerb(verb, handler) {
|
|
456
|
+
if ("verb" in handler && handler.verb !== verb) {
|
|
457
|
+
throw new Error(
|
|
458
|
+
`Expected verb ${verb} but handler was defined with Run.${handler.verb}`
|
|
459
|
+
);
|
|
460
|
+
}
|
|
461
|
+
}
|
|
462
|
+
function createDefineHandler(verb) {
|
|
439
463
|
return (optionsOrHandlers, handlers) => {
|
|
440
464
|
let handler;
|
|
441
465
|
if (typeof optionsOrHandlers === "function") {
|
|
466
|
+
assertHandlerVerb(verb, optionsOrHandlers);
|
|
442
467
|
handler = optionsOrHandlers;
|
|
443
|
-
handler.options = {};
|
|
468
|
+
handler.options ?? (handler.options = {});
|
|
444
469
|
} else if (Array.isArray(optionsOrHandlers)) {
|
|
470
|
+
for (const h of optionsOrHandlers) assertHandlerVerb(verb, h);
|
|
445
471
|
handler = compose(optionsOrHandlers);
|
|
446
|
-
handler.options =
|
|
472
|
+
handler.options = mergeOptions(...optionsOrHandlers);
|
|
447
473
|
} else if (typeof handlers === "function") {
|
|
474
|
+
assertHandlerVerb(verb, handlers);
|
|
448
475
|
handler = handlers;
|
|
449
|
-
handler.options = optionsOrHandlers;
|
|
476
|
+
handler.options = mergeOptions(handlers, optionsOrHandlers);
|
|
450
477
|
} else if (Array.isArray(handlers)) {
|
|
478
|
+
for (const h of handlers) assertHandlerVerb(verb, h);
|
|
451
479
|
handler = compose(handlers);
|
|
452
|
-
handler.options = optionsOrHandlers;
|
|
480
|
+
handler.options = mergeOptions(...handlers, optionsOrHandlers);
|
|
453
481
|
} else {
|
|
454
482
|
handler = passthroughHandler;
|
|
455
483
|
handler.options = optionsOrHandlers;
|
|
456
484
|
}
|
|
485
|
+
handler.verb = verb;
|
|
457
486
|
return handler;
|
|
458
487
|
};
|
|
459
488
|
}
|
|
@@ -469,19 +498,24 @@ function normalizeValidator(validator) {
|
|
|
469
498
|
var defaultMaxBytes = 1024 * 1024;
|
|
470
499
|
var defaultMaxParts = 1e3;
|
|
471
500
|
var defaultMaxFiles = 20;
|
|
472
|
-
function mergeOptions(...
|
|
501
|
+
function mergeOptions(...arr) {
|
|
473
502
|
const merged = {};
|
|
474
|
-
for (const
|
|
475
|
-
|
|
476
|
-
|
|
477
|
-
|
|
478
|
-
|
|
479
|
-
|
|
480
|
-
|
|
481
|
-
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
|
|
503
|
+
for (const item of arr) {
|
|
504
|
+
let options;
|
|
505
|
+
if (typeof item === "object") {
|
|
506
|
+
options = item;
|
|
507
|
+
} else if ("options" in item) {
|
|
508
|
+
options = item.options;
|
|
509
|
+
} else {
|
|
510
|
+
continue;
|
|
511
|
+
}
|
|
512
|
+
for (const k in options) {
|
|
513
|
+
const key = k;
|
|
514
|
+
const option = options[key];
|
|
515
|
+
if (typeof option === "object" && typeof merged[key] === "object") {
|
|
516
|
+
Object.assign(merged[key], option);
|
|
517
|
+
} else if (option) {
|
|
518
|
+
merged[key] = option;
|
|
485
519
|
}
|
|
486
520
|
}
|
|
487
521
|
}
|
|
@@ -540,6 +574,7 @@ function notMatched() {
|
|
|
540
574
|
0 && (module.exports = {
|
|
541
575
|
NotHandled,
|
|
542
576
|
NotMatched,
|
|
577
|
+
assertHandlerVerb,
|
|
543
578
|
call,
|
|
544
579
|
compose,
|
|
545
580
|
createContext,
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import type { Awaitable, RouteHandler } from "./legacy-types";
|
|
2
|
-
import type { Context, HandlerFunction, HandlerOptions, NextFunction, NormalizedHandler, NormalizedHandlerOptions, Platform, RouteData, RouteMatch, Validator } from "./types";
|
|
2
|
+
import type { Context, HandlerFunction, HandlerOptions, HttpVerbOrAll, NextFunction, NormalizedHandler, NormalizedHandlerOptions, Platform, RouteData, RouteMatch, Validator } from "./types";
|
|
3
3
|
export { getMetaDataLookup as normalizeMeta } from "../vite/utils/meta-data";
|
|
4
4
|
export declare const NotHandled: typeof MarkoRun.NotHandled;
|
|
5
5
|
export declare const NotMatched: typeof MarkoRun.NotMatched;
|
|
@@ -8,8 +8,9 @@ export declare function render<T>(context: Context, template: Marko.Template<T>,
|
|
|
8
8
|
export declare function call(handler: HandlerFunction, next: NextFunction, context: Context, data?: RouteData): Promise<Response>;
|
|
9
9
|
export declare function compose(handlers: HandlerFunction[]): HandlerFunction;
|
|
10
10
|
export declare function normalizeHandler(obj: RouteHandler | RouteHandler[] | Promise<RouteHandler | RouteHandler[]>): RouteHandler;
|
|
11
|
+
export declare function assertHandlerVerb(verb: HttpVerbOrAll, handler: HandlerFunction): void;
|
|
11
12
|
export declare function normalizeValidator<T>(validator: Validator<T> | undefined): import("./types").ValidatorFn<T> | undefined;
|
|
12
|
-
export declare function mergeOptions(...
|
|
13
|
+
export declare function mergeOptions(...arr: (NormalizedHandler<Context, "ALL", any, HandlerOptions> | HandlerFunction | HandlerOptions)[]): NormalizedHandlerOptions;
|
|
13
14
|
export declare function stripResponseBodySync(response: Response): Response;
|
|
14
15
|
export declare function stripResponseBody(response: Awaitable<Response>): Awaitable<Response>;
|
|
15
16
|
export declare function passthrough(): void;
|
package/dist/runtime/internal.js
CHANGED
|
@@ -13,6 +13,28 @@ var httpVerbs = [
|
|
|
13
13
|
"options"
|
|
14
14
|
];
|
|
15
15
|
|
|
16
|
+
// src/runtime/thenable.ts
|
|
17
|
+
var kPromise = /* @__PURE__ */ Symbol("promise");
|
|
18
|
+
var kReadFn = /* @__PURE__ */ Symbol("read fn");
|
|
19
|
+
function thenFn(resolve, reject) {
|
|
20
|
+
return (this[kPromise] || (this[kPromise] = this[kReadFn]())).then(resolve, reject);
|
|
21
|
+
}
|
|
22
|
+
function catchFn(reject) {
|
|
23
|
+
return (this[kPromise] || (this[kPromise] = this[kReadFn]())).catch(reject);
|
|
24
|
+
}
|
|
25
|
+
function finallyFn(resolve) {
|
|
26
|
+
return (this[kPromise] || (this[kPromise] = this[kReadFn]())).finally(resolve);
|
|
27
|
+
}
|
|
28
|
+
function thenable(fn) {
|
|
29
|
+
return {
|
|
30
|
+
[kPromise]: null,
|
|
31
|
+
[kReadFn]: fn,
|
|
32
|
+
then: thenFn,
|
|
33
|
+
catch: catchFn,
|
|
34
|
+
finally: finallyFn
|
|
35
|
+
};
|
|
36
|
+
}
|
|
37
|
+
|
|
16
38
|
// src/runtime/url-builder.ts
|
|
17
39
|
var encode = encodeURIComponent;
|
|
18
40
|
var pathParts = /* @__PURE__ */ new Map();
|
|
@@ -117,18 +139,16 @@ globalThis.MarkoRun ?? (globalThis.MarkoRun = {
|
|
|
117
139
|
NotHandled,
|
|
118
140
|
NotMatched
|
|
119
141
|
});
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
globalThis.Run = namespace;
|
|
131
|
-
}
|
|
142
|
+
globalThis.Run ?? (globalThis.Run = {
|
|
143
|
+
href,
|
|
144
|
+
ALL: createDefineHandler("ALL"),
|
|
145
|
+
...Object.fromEntries(
|
|
146
|
+
httpVerbs.map((v) => {
|
|
147
|
+
const verb = v.toUpperCase();
|
|
148
|
+
return [v.toUpperCase(), createDefineHandler(verb)];
|
|
149
|
+
})
|
|
150
|
+
)
|
|
151
|
+
});
|
|
132
152
|
var toReadable = (rendered) => {
|
|
133
153
|
toReadable = rendered.toReadable ? (rendered2) => rendered2.toReadable() : (rendered2) => {
|
|
134
154
|
let cancelled = false;
|
|
@@ -196,6 +216,29 @@ async function readBodyWithLimit(request, maxBytes) {
|
|
|
196
216
|
bytes.subarray(0, receivedBytes)
|
|
197
217
|
);
|
|
198
218
|
}
|
|
219
|
+
async function readBody(route, context) {
|
|
220
|
+
const { request } = context;
|
|
221
|
+
const contentType = request.headers.get("Content-Type");
|
|
222
|
+
if (contentType == null ? void 0 : contentType.includes("application/json")) {
|
|
223
|
+
const { maxBytes: maxBytes2, validator: validator2 } = route.options.json;
|
|
224
|
+
const json = maxBytes2 < 0 ? await request.json() : JSON.parse(await readBodyWithLimit(request, maxBytes2));
|
|
225
|
+
return validator2 ? validator2(json) : json;
|
|
226
|
+
}
|
|
227
|
+
const { maxBytes, maxParts, maxFiles, maxFileBytes, onFile, validator } = route.options.form;
|
|
228
|
+
const data = searchParamsToObject(
|
|
229
|
+
(contentType == null ? void 0 : contentType.includes("multipart/form-data")) ? await parseFormData(
|
|
230
|
+
request,
|
|
231
|
+
{
|
|
232
|
+
maxParts,
|
|
233
|
+
maxFiles,
|
|
234
|
+
maxFileSize: maxFileBytes,
|
|
235
|
+
maxTotalSize: maxBytes
|
|
236
|
+
},
|
|
237
|
+
onFile ? (file) => onFile(context, file) : void 0
|
|
238
|
+
) : new URLSearchParams2(await readBodyWithLimit(request, maxBytes))
|
|
239
|
+
);
|
|
240
|
+
return validator && validator(data);
|
|
241
|
+
}
|
|
199
242
|
function createContext(route, request, platform, url = new URL(request.url)) {
|
|
200
243
|
const context = {
|
|
201
244
|
route: (route == null ? void 0 : route.path) || "",
|
|
@@ -220,45 +263,7 @@ function createContext(route, request, platform, url = new URL(request.url)) {
|
|
|
220
263
|
});
|
|
221
264
|
return value;
|
|
222
265
|
},
|
|
223
|
-
body: route && request.body ?
|
|
224
|
-
const contentType = request.headers.get("Content-Type");
|
|
225
|
-
let value;
|
|
226
|
-
if (contentType == null ? void 0 : contentType.includes("application/json")) {
|
|
227
|
-
const { maxBytes, validator } = route.options.json;
|
|
228
|
-
const json = maxBytes < 0 ? await request.json() : JSON.parse(await readBodyWithLimit(request, maxBytes));
|
|
229
|
-
value = validator ? validator(json) : json;
|
|
230
|
-
} else {
|
|
231
|
-
const {
|
|
232
|
-
maxBytes,
|
|
233
|
-
maxParts,
|
|
234
|
-
maxFiles,
|
|
235
|
-
maxFileBytes,
|
|
236
|
-
onFile,
|
|
237
|
-
validator
|
|
238
|
-
} = route.options.form;
|
|
239
|
-
const data = searchParamsToObject(
|
|
240
|
-
(contentType == null ? void 0 : contentType.includes("multipart/form-data")) ? await parseFormData(
|
|
241
|
-
request,
|
|
242
|
-
{
|
|
243
|
-
maxParts,
|
|
244
|
-
maxFiles,
|
|
245
|
-
maxFileSize: maxFileBytes,
|
|
246
|
-
maxTotalSize: maxBytes
|
|
247
|
-
},
|
|
248
|
-
onFile ? (file) => onFile(context, file) : void 0
|
|
249
|
-
) : new URLSearchParams2(
|
|
250
|
-
await readBodyWithLimit(request, maxBytes)
|
|
251
|
-
)
|
|
252
|
-
);
|
|
253
|
-
value = validator ? validator(data) : validator;
|
|
254
|
-
}
|
|
255
|
-
Object.defineProperty(context, "body", {
|
|
256
|
-
configurable: true,
|
|
257
|
-
enumerable: true,
|
|
258
|
-
value
|
|
259
|
-
});
|
|
260
|
-
return value;
|
|
261
|
-
} : void 0,
|
|
266
|
+
body: route && request.body ? thenable(() => readBody(route, context)) : void 0,
|
|
262
267
|
data: {},
|
|
263
268
|
url,
|
|
264
269
|
request,
|
|
@@ -312,11 +317,22 @@ function render(context, template, input, data) {
|
|
|
312
317
|
}
|
|
313
318
|
return context.render(template, input);
|
|
314
319
|
}
|
|
320
|
+
var handlerMethod = /* @__PURE__ */ new WeakMap();
|
|
315
321
|
async function call(handler, next, context, data) {
|
|
316
322
|
let response;
|
|
317
323
|
if (data) {
|
|
318
324
|
Object.assign(context.data, data);
|
|
319
325
|
}
|
|
326
|
+
let method = handlerMethod.get(handler);
|
|
327
|
+
if (method === void 0) {
|
|
328
|
+
handlerMethod.set(
|
|
329
|
+
handler,
|
|
330
|
+
method = "verb" in handler && handler.verb !== "ALL" ? handler.verb : false
|
|
331
|
+
);
|
|
332
|
+
}
|
|
333
|
+
if (method && method !== context.method) {
|
|
334
|
+
return next(data);
|
|
335
|
+
}
|
|
320
336
|
if (!process.env.NODE_ENV || process.env.NODE_ENV === "development") {
|
|
321
337
|
let nextCallCount = 0;
|
|
322
338
|
let didThrow = false;
|
|
@@ -357,7 +373,7 @@ async function call(handler, next, context, data) {
|
|
|
357
373
|
if (response === null || response === NotMatched || response === NotHandled) {
|
|
358
374
|
throw response || NotMatched;
|
|
359
375
|
}
|
|
360
|
-
return response || next();
|
|
376
|
+
return response || next(data);
|
|
361
377
|
}
|
|
362
378
|
function compose(handlers) {
|
|
363
379
|
const len = handlers.length;
|
|
@@ -390,25 +406,37 @@ function normalizeHandler(obj) {
|
|
|
390
406
|
}
|
|
391
407
|
return passthrough;
|
|
392
408
|
}
|
|
393
|
-
function
|
|
409
|
+
function assertHandlerVerb(verb, handler) {
|
|
410
|
+
if ("verb" in handler && handler.verb !== verb) {
|
|
411
|
+
throw new Error(
|
|
412
|
+
`Expected verb ${verb} but handler was defined with Run.${handler.verb}`
|
|
413
|
+
);
|
|
414
|
+
}
|
|
415
|
+
}
|
|
416
|
+
function createDefineHandler(verb) {
|
|
394
417
|
return (optionsOrHandlers, handlers) => {
|
|
395
418
|
let handler;
|
|
396
419
|
if (typeof optionsOrHandlers === "function") {
|
|
420
|
+
assertHandlerVerb(verb, optionsOrHandlers);
|
|
397
421
|
handler = optionsOrHandlers;
|
|
398
|
-
handler.options = {};
|
|
422
|
+
handler.options ?? (handler.options = {});
|
|
399
423
|
} else if (Array.isArray(optionsOrHandlers)) {
|
|
424
|
+
for (const h of optionsOrHandlers) assertHandlerVerb(verb, h);
|
|
400
425
|
handler = compose(optionsOrHandlers);
|
|
401
|
-
handler.options =
|
|
426
|
+
handler.options = mergeOptions(...optionsOrHandlers);
|
|
402
427
|
} else if (typeof handlers === "function") {
|
|
428
|
+
assertHandlerVerb(verb, handlers);
|
|
403
429
|
handler = handlers;
|
|
404
|
-
handler.options = optionsOrHandlers;
|
|
430
|
+
handler.options = mergeOptions(handlers, optionsOrHandlers);
|
|
405
431
|
} else if (Array.isArray(handlers)) {
|
|
432
|
+
for (const h of handlers) assertHandlerVerb(verb, h);
|
|
406
433
|
handler = compose(handlers);
|
|
407
|
-
handler.options = optionsOrHandlers;
|
|
434
|
+
handler.options = mergeOptions(...handlers, optionsOrHandlers);
|
|
408
435
|
} else {
|
|
409
436
|
handler = passthroughHandler;
|
|
410
437
|
handler.options = optionsOrHandlers;
|
|
411
438
|
}
|
|
439
|
+
handler.verb = verb;
|
|
412
440
|
return handler;
|
|
413
441
|
};
|
|
414
442
|
}
|
|
@@ -424,19 +452,24 @@ function normalizeValidator(validator) {
|
|
|
424
452
|
var defaultMaxBytes = 1024 * 1024;
|
|
425
453
|
var defaultMaxParts = 1e3;
|
|
426
454
|
var defaultMaxFiles = 20;
|
|
427
|
-
function mergeOptions(...
|
|
455
|
+
function mergeOptions(...arr) {
|
|
428
456
|
const merged = {};
|
|
429
|
-
for (const
|
|
430
|
-
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
|
|
436
|
-
|
|
437
|
-
|
|
438
|
-
|
|
439
|
-
|
|
457
|
+
for (const item of arr) {
|
|
458
|
+
let options;
|
|
459
|
+
if (typeof item === "object") {
|
|
460
|
+
options = item;
|
|
461
|
+
} else if ("options" in item) {
|
|
462
|
+
options = item.options;
|
|
463
|
+
} else {
|
|
464
|
+
continue;
|
|
465
|
+
}
|
|
466
|
+
for (const k in options) {
|
|
467
|
+
const key = k;
|
|
468
|
+
const option = options[key];
|
|
469
|
+
if (typeof option === "object" && typeof merged[key] === "object") {
|
|
470
|
+
Object.assign(merged[key], option);
|
|
471
|
+
} else if (option) {
|
|
472
|
+
merged[key] = option;
|
|
440
473
|
}
|
|
441
474
|
}
|
|
442
475
|
}
|
|
@@ -494,6 +527,7 @@ function notMatched() {
|
|
|
494
527
|
export {
|
|
495
528
|
NotHandled,
|
|
496
529
|
NotMatched,
|
|
530
|
+
assertHandlerVerb,
|
|
497
531
|
call,
|
|
498
532
|
compose,
|
|
499
533
|
createContext,
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
declare const kPromise: unique symbol;
|
|
2
|
+
declare const kReadFn: unique symbol;
|
|
3
|
+
export interface Thenable<T = any> extends Promise<T> {
|
|
4
|
+
[kPromise]: null | Promise<T>;
|
|
5
|
+
[kReadFn]: () => Promise<T>;
|
|
6
|
+
then: Promise<T>["then"];
|
|
7
|
+
catch: Promise<T>["catch"];
|
|
8
|
+
finally: Promise<T>["finally"];
|
|
9
|
+
}
|
|
10
|
+
export default function thenable<T>(fn: () => Promise<T>): Thenable<T>;
|
|
11
|
+
export {};
|