@sourceregistry/node-webserver 1.3.0 → 1.4.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/dist/index.es.js CHANGED
@@ -1,1072 +1,1170 @@
1
- import { createServer as M } from "http";
2
- import { createServer as $ } from "https";
3
- import { TLSSocket as I } from "tls";
4
- import { Readable as F, Transform as D, Writable as U } from "stream";
5
- import { WebSocketServer as z, WebSocket as P } from "ws";
6
- import { parse as b, serialize as B } from "cookie";
7
- import { createReadStream as X } from "node:fs";
8
- import { stat as W, realpath as v, lstat as J } from "node:fs/promises";
9
- import { sep as G, resolve as O, relative as V, isAbsolute as K, extname as Y } from "node:path";
10
- import { Readable as Q } from "node:stream";
11
- function _(a) {
12
- return S(a) && a.status >= 400 && a.status < 600;
13
- }
14
- function N(a) {
15
- return S(a) && a.status >= 300 && a.status < 400;
1
+ import { randomUUID as e } from "node:crypto";
2
+ import { createServer as t } from "http";
3
+ import { createServer as n } from "https";
4
+ import { TLSSocket as r } from "tls";
5
+ import { Readable as i, Transform as a, Writable as o } from "stream";
6
+ import { WebSocket as s, WebSocketServer as c } from "ws";
7
+ import { parse as l, serialize as u } from "cookie";
8
+ import { createReadStream as d } from "node:fs";
9
+ import { lstat as f, realpath as p, stat as m } from "node:fs/promises";
10
+ import { extname as h, isAbsolute as g, relative as _, resolve as v, sep as y } from "node:path";
11
+ import { Readable as b } from "node:stream";
12
+ //#region \0rolldown/runtime.js
13
+ var x = Object.defineProperty, S = (e, t) => {
14
+ let n = {};
15
+ for (var r in e) x(n, r, {
16
+ get: e[r],
17
+ enumerable: !0
18
+ });
19
+ return t || x(n, Symbol.toStringTag, { value: "Module" }), n;
20
+ };
21
+ //#endregion
22
+ //#region src/utils.ts
23
+ function C(e) {
24
+ return T(e) && e.status >= 400 && e.status < 600;
16
25
  }
17
- function S(a) {
18
- return a instanceof Response;
26
+ function w(e) {
27
+ return T(e) && e.status >= 300 && e.status < 400;
19
28
  }
20
- class Z {
21
- constructor(e) {
22
- this.data = /* @__PURE__ */ new Map(), this.windowMs = e.windowMs, this.startCleanup();
23
- }
24
- async incr(e) {
25
- const t = Date.now();
26
- let s = this.data.get(e);
27
- return !s || t >= s.reset ? (s = { count: 1, reset: t + this.windowMs }, this.data.set(e, s)) : s.count++, { current: s.count, reset: s.reset };
28
- }
29
- startCleanup() {
30
- this.cleanupInterval = setInterval(() => {
31
- const e = Date.now();
32
- for (const [t, { reset: s }] of this.data)
33
- e >= s && this.data.delete(t);
34
- }, Math.min(this.windowMs, 3e5));
35
- }
36
- stop() {
37
- this.cleanupInterval && clearInterval(this.cleanupInterval);
38
- }
39
- async resetAll() {
40
- this.data.clear();
41
- }
29
+ function T(e) {
30
+ return e instanceof Response;
42
31
  }
43
- function ee(a) {
44
- const {
45
- windowMs: e = 6e4,
46
- max: t,
47
- key: s = (c) => c.getClientAddress(),
48
- message: r = "Too many requests, please try again later.",
49
- statusCode: n = 429,
50
- headers: o = "include",
51
- onRateLimit: i,
52
- store: u = new Z({ windowMs: e })
53
- } = a;
54
- return async (c, l) => {
55
- const d = `rl:${s(c)}`, { current: h, reset: p } = await u.incr(d), m = Math.ceil((p - Date.now()) / 1e3);
56
- if (h > t) {
57
- i && i(c, { current: h, max: t, key: d });
58
- const y = {
59
- status: n,
60
- headers: new Headers()
61
- }, f = y.headers;
62
- o === "include" && (f.set("X-RateLimit-Limit", String(t)), f.set("X-RateLimit-Remaining", "0"), f.set("X-RateLimit-Reset", String(Math.floor(p / 1e3))), f.set("Retry-After", String(m)));
63
- let w;
64
- return typeof r == "string" ? (w = r, f.set("Content-Type", "text/plain")) : (w = JSON.stringify(r), f.set("Content-Type", "application/json")), new Response(w, y);
65
- }
66
- if (c.rateLimit = {
67
- current: h,
68
- limit: t,
69
- reset: new Date(p),
70
- remaining: t - h
71
- }, o === "include") {
72
- const y = {
73
- "X-RateLimit-Limit": String(t),
74
- "X-RateLimit-Remaining": String(t - h),
75
- "X-RateLimit-Reset": String(Math.floor(p / 1e3))
76
- }, f = c.setHeaders;
77
- c.setHeaders = (w) => {
78
- f({
79
- ...y,
80
- ...w
81
- });
82
- }, f(y);
83
- }
84
- return l();
85
- };
32
+ //#endregion
33
+ //#region src/middlewares/ratelimiter/InMemory.ts
34
+ var E = class {
35
+ constructor(e) {
36
+ this.data = /* @__PURE__ */ new Map(), this.windowMs = e.windowMs, this.startCleanup();
37
+ }
38
+ async incr(e) {
39
+ let t = Date.now(), n = this.data.get(e);
40
+ return !n || t >= n.reset ? (n = {
41
+ count: 1,
42
+ reset: t + this.windowMs
43
+ }, this.data.set(e, n)) : n.count++, {
44
+ current: n.count,
45
+ reset: n.reset
46
+ };
47
+ }
48
+ startCleanup() {
49
+ this.cleanupInterval = setInterval(() => {
50
+ let e = Date.now();
51
+ for (let [t, { reset: n }] of this.data) e >= n && this.data.delete(t);
52
+ }, Math.min(this.windowMs, 3e5));
53
+ }
54
+ stop() {
55
+ this.cleanupInterval && clearInterval(this.cleanupInterval);
56
+ }
57
+ async resetAll() {
58
+ this.data.clear();
59
+ }
60
+ }, D = /* @__PURE__ */ S({ fixedWindowLimit: () => O });
61
+ function O(e) {
62
+ let { windowMs: t = 6e4, max: n, key: r = (e) => e.getClientAddress(), message: i = "Too many requests, please try again later.", statusCode: a = 429, headers: o = "include", onRateLimit: s, store: c = new E({ windowMs: t }) } = e;
63
+ return async (e, t) => {
64
+ let l = `rl:${r(e)}`, { current: u, reset: d } = await c.incr(l), f = Math.ceil((d - Date.now()) / 1e3);
65
+ if (u > n) {
66
+ s && s(e, {
67
+ current: u,
68
+ max: n,
69
+ key: l
70
+ });
71
+ let t = {
72
+ status: a,
73
+ headers: new Headers()
74
+ }, r = t.headers;
75
+ o === "include" && (r.set("X-RateLimit-Limit", String(n)), r.set("X-RateLimit-Remaining", "0"), r.set("X-RateLimit-Reset", String(Math.floor(d / 1e3))), r.set("Retry-After", String(f)));
76
+ let c;
77
+ return typeof i == "string" ? (c = i, r.set("Content-Type", "text/plain")) : (c = JSON.stringify(i), r.set("Content-Type", "application/json")), new Response(c, t);
78
+ }
79
+ if (e.rateLimit = {
80
+ current: u,
81
+ limit: n,
82
+ reset: new Date(d),
83
+ remaining: n - u
84
+ }, o === "include") {
85
+ let t = {
86
+ "X-RateLimit-Limit": String(n),
87
+ "X-RateLimit-Remaining": String(n - u),
88
+ "X-RateLimit-Reset": String(Math.floor(d / 1e3))
89
+ }, r = e.setHeaders;
90
+ e.setHeaders = (e) => {
91
+ r({
92
+ ...t,
93
+ ...e
94
+ });
95
+ }, r(t);
96
+ }
97
+ return t();
98
+ };
86
99
  }
87
- const Te = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
88
- __proto__: null,
89
- fixedWindowLimit: ee
90
- }, Symbol.toStringTag, { value: "Module" })), te = [
91
- "GET",
92
- "POST",
93
- "PUT",
94
- "DELETE",
95
- "PATCH",
96
- "HEAD",
97
- "OPTIONS"
98
- ], se = [
99
- "Accept",
100
- "Accept-Language",
101
- "Content-Language",
102
- "Content-Type",
103
- "Range"
104
- ], re = [
105
- "Authorization",
106
- "X-Auth-Token",
107
- "X-Requested-With",
108
- "X-CSRF-Token",
109
- "X-HTTP-Method-Override",
110
- "X-Forwarded-For",
111
- "X-Real-IP",
112
- "X-Custom-Header"
100
+ //#endregion
101
+ //#region src/middlewares/cros/index.ts
102
+ var ee = /* @__PURE__ */ S({ policy: () => M }), te = [
103
+ "GET",
104
+ "POST",
105
+ "PUT",
106
+ "DELETE",
107
+ "PATCH",
108
+ "HEAD",
109
+ "OPTIONS"
110
+ ], ne = [
111
+ "Accept",
112
+ "Accept-Language",
113
+ "Content-Language",
114
+ "Content-Type",
115
+ "Range"
116
+ ], k = [
117
+ "Authorization",
118
+ "X-Auth-Token",
119
+ "X-Requested-With",
120
+ "X-CSRF-Token",
121
+ "X-HTTP-Method-Override",
122
+ "X-Forwarded-For",
123
+ "X-Real-IP",
124
+ "X-Custom-Header"
113
125
  ];
114
- function j(a, e) {
115
- return !a || !e ? !1 : e === "*" ? !0 : e === "null" ? a === "null" : Array.isArray(e) ? e.some((t) => j(a, t)) : typeof e == "function" ? e(a) : e instanceof RegExp ? e.test(a) : a === e;
116
- }
117
- function ne(a, e) {
118
- const { origin: t = "*" } = e;
119
- return a ? t === "*" ? e.credentials ? a : "*" : j(a, t) ? a : null : t === "*" ? "*" : null;
120
- }
121
- function oe(a = {}) {
122
- const {
123
- methods: e = te,
124
- allowedHeaders: t = re,
125
- exposedHeaders: s,
126
- credentials: r = !1,
127
- maxAge: n = 86400,
128
- onResponse: o
129
- } = a, i = "Origin,Access-Control-Request-Method,Access-Control-Request-Headers", u = e.join(","), c = [...se, ...t].join(","), l = [
130
- ["Vary", i],
131
- ["Access-Control-Allow-Methods", u],
132
- ["Access-Control-Allow-Headers", c]
133
- ];
134
- return s && l.push(["Access-Control-Expose-Headers", s.join(",")]), r && l.push(["Access-Control-Allow-Credentials", "true"]), n && l.push(["Access-Control-Max-Age", n.toString()]), async (d, h) => {
135
- const p = d.request, m = p.headers.get("Origin"), y = p.method === "OPTIONS" && m !== null && p.headers.has("Access-Control-Request-Method"), f = ne(m, a);
136
- if (y) {
137
- if (!f)
138
- return new Response(null, { status: 403 });
139
- const g = new Response(null, { status: 204 });
140
- for (const [x, q] of l)
141
- g.headers.set(x, q);
142
- return g.headers.set("Access-Control-Allow-Origin", f), g;
143
- }
144
- const w = await h();
145
- if (!w) return;
146
- if (!f) return w;
147
- const H = new Response(w.body, w);
148
- for (const [g, x] of l)
149
- H.headers.set(g, x);
150
- H.headers.set("Access-Control-Allow-Origin", f);
151
- let A = H;
152
- if (o) {
153
- const g = o(A);
154
- g && (A = g);
155
- }
156
- return A;
157
- };
126
+ function A(e, t) {
127
+ return !e || !t ? !1 : t === "*" ? !0 : t === "null" ? e === "null" : Array.isArray(t) ? t.some((t) => A(e, t)) : typeof t == "function" ? t(e) : t instanceof RegExp ? t.test(e) : e === t;
158
128
  }
159
- const Ce = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
160
- __proto__: null,
161
- policy: oe
162
- }, Symbol.toStringTag, { value: "Module" })), ae = ["GET", "PUT", "POST", "DELETE", "PATCH", "HEAD", "OPTIONS"];
163
- class T {
164
- static {
165
- this.cache = /* @__PURE__ */ new Map();
166
- }
167
- static get(e) {
168
- return this.cache.get(e);
169
- }
170
- static set(e, t) {
171
- this.cache.set(e, t);
172
- }
129
+ function j(e, t) {
130
+ let { origin: n = "*" } = t;
131
+ return e ? n === "*" ? t.credentials ? e : "*" : A(e, n) ? e : null : n === "*" ? "*" : null;
173
132
  }
174
- class E {
175
- constructor() {
176
- this._routes = [], this._wsRoutes = [], this._nestedRouters = [], this._middlewares = [], this._preHandlers = [], this._postHandlers = [], this.routesSorted = !1, this.wsRoutesSorted = !1;
177
- }
178
- get routes() {
179
- return this._routes;
180
- }
181
- get nestedRouters() {
182
- return this._nestedRouters;
183
- }
184
- // HTTP method handlers
185
- GET(e, t, ...s) {
186
- return this.addHandler("GET", e, t, s);
187
- }
188
- POST(e, t, ...s) {
189
- return this.addHandler("POST", e, t, s);
190
- }
191
- PUT(e, t, ...s) {
192
- return this.addHandler("PUT", e, t, s);
193
- }
194
- PATCH(e, t, ...s) {
195
- return this.addHandler("PATCH", e, t, s);
196
- }
197
- DELETE(e, t, ...s) {
198
- return this.addHandler("DELETE", e, t, s);
199
- }
200
- HEAD(e, t, ...s) {
201
- return this.addHandler("HEAD", e, t, s);
202
- }
203
- OPTIONS(e, t, ...s) {
204
- return this.addHandler("OPTIONS", e, t, s);
205
- }
206
- // Universal method
207
- USE(e, t, ...s) {
208
- return ae.forEach((r) => this.addHandler(r, e, t, s)), this;
209
- }
210
- // Action handler (POST only)
211
- action(e, t, ...s) {
212
- const r = async (n) => {
213
- try {
214
- const o = await t(n);
215
- return this.formatActionResult(o);
216
- } catch (o) {
217
- return this.handleActionError(o);
218
- }
219
- };
220
- return this.addHandler("POST", e, r, s);
221
- }
222
- use(e, t, ...s) {
223
- let r, n, o = s;
224
- Array.isArray(e) ? ([r, n] = e, o = e.length > 2 ? e.slice(2) : []) : (r = e, n = t);
225
- const i = this.normalizePrefix(r), { regex: u, paramNames: c, isCatchAll: l, priority: d } = this.createPrefixRegex(i);
226
- return this._nestedRouters.push({
227
- prefix: i,
228
- router: n,
229
- regex: u,
230
- paramNames: c,
231
- isCatchAll: l,
232
- priority: d,
233
- middlewares: o
234
- }), this;
235
- }
236
- // Global middleware
237
- useMiddleware(...e) {
238
- return this._middlewares.push(...e), this;
239
- }
240
- pre(...e) {
241
- return this._preHandlers.push(...e), this;
242
- }
243
- post(...e) {
244
- return this._postHandlers.push(...e), this;
245
- }
246
- // Discard routes or nested routers
247
- discard(e, t) {
248
- return this._nestedRouters = this._nestedRouters.filter((s) => s.prefix !== e), this._routes = this._routes.filter(
249
- (s) => s.path !== e || t && s.method !== t
250
- ), this;
251
- }
252
- // WebSocket route
253
- WS(e, t, ...s) {
254
- const { regex: r, paramNames: n, isCatchAll: o, priority: i } = this.createPathRegex(e);
255
- return this._wsRoutes.push({
256
- path: e,
257
- regex: r,
258
- paramNames: n,
259
- isCatchAll: o,
260
- priority: i,
261
- handler: t,
262
- middlewares: s
263
- }), this.wsRoutesSorted = !1, this;
264
- }
265
- // Add this method to your Router class
266
- /**
267
- * Check if the router can handle a WebSocket connection for the given path
268
- * This is used during the upgrade process to validate routes before attempting connection
269
- */
270
- async canHandleWebSocket(e) {
271
- return this.canHandleWebSocketAtPath(e, e.url.pathname);
272
- }
273
- async canHandleWebSocketAtPath(e, t) {
274
- this.wsRoutesSorted || this.sortWsRoutes();
275
- for (const s of [...this._nestedRouters].sort((r, n) => n.priority - r.priority)) {
276
- const r = t.match(s.regex);
277
- if (!r || r.index !== 0) continue;
278
- const n = r[0], o = t.slice(n.length) || "/", i = {
279
- ...e,
280
- params: { ...e.params, ...this.extractPrefixParams(s, n) }
281
- };
282
- if (await s.router.canHandleWebSocketAtPath(i, o))
283
- return !0;
284
- }
285
- for (const s of this._wsRoutes)
286
- if (s.regex.test(t))
287
- return !0;
288
- return !1;
289
- }
290
- // Handle WebSocket upgrade
291
- async handleWebSocket(e, t) {
292
- return this.handleWebSocketAtPath(e, t, e.url.pathname);
293
- }
294
- async handleWebSocketAtPath(e, t, s) {
295
- this.wsRoutesSorted || this.sortWsRoutes();
296
- for (const r of [...this._nestedRouters].sort((n, o) => o.priority - n.priority)) {
297
- const n = s.match(r.regex);
298
- if (!n || n.index !== 0) continue;
299
- const o = n[0], i = s.slice(o.length) || "/", u = this.extractPrefixParams(r, o), c = {
300
- ...e,
301
- params: { ...e.params, ...u }
302
- }, l = [...this._middlewares, ...r.middlewares], d = () => r.router.handleWebSocketAtPath(c, t, i);
303
- if (await this.applyMiddlewaresWithList(c, l, d)) return !0;
304
- }
305
- for (const r of this._wsRoutes) {
306
- if (!r.regex.test(s)) continue;
307
- const n = s.match(r.regex);
308
- if (!n) continue;
309
- const o = Object.fromEntries(
310
- r.paramNames.map((l, d) => [l, n[d + 1] || ""])
311
- ), i = {
312
- ...e,
313
- params: { ...e.params, ...o },
314
- route: { ...e.route, id: r.path },
315
- websocket: t
316
- }, u = [...this._middlewares, ...r.middlewares];
317
- if (await this.applyMiddlewaresWithList(i, u, () => r.handler(i)) === void 0)
318
- return !0;
319
- }
320
- return !1;
321
- }
322
- // Handle HTTP request - FIXED: Single middleware application
323
- async handle(e) {
324
- return this.handleAtPath(e, e.url.pathname);
325
- }
326
- async handleAtPath(e, t) {
327
- try {
328
- const s = e.request.method;
329
- let r = await this.runPreHandlers(e);
330
- if (!r) {
331
- const o = async () => {
332
- const i = await this.handleNestedRouters(e, t);
333
- return i || (this.routesSorted || this.sortRoutes(), this.handleLocalRoutes(e, s, t));
334
- };
335
- r = await this.applyMiddlewaresWithList(e, this._middlewares, o);
336
- }
337
- const n = r || new Response("No Content", { status: 204 });
338
- return await this.runPostHandlers(e, n);
339
- } catch (s) {
340
- if (S(s)) return s;
341
- throw s;
342
- }
343
- }
344
- // Apply middlewares utility
345
- async applyMiddlewaresWithList(e, t, s) {
346
- const r = [...t], n = async (o) => o >= r.length ? s() : r[o](e, () => n(o + 1));
347
- return n(0);
348
- }
349
- async runPreHandlers(e) {
350
- for (const t of this._preHandlers) {
351
- const s = await t(e);
352
- if (s instanceof Response)
353
- return s;
354
- }
355
- }
356
- async runPostHandlers(e, t) {
357
- let s = t;
358
- for (const r of this._postHandlers) {
359
- const n = await r(e, s);
360
- n instanceof Response && (s = n);
361
- }
362
- return s;
363
- }
364
- // Add route handler
365
- addHandler(e, t, s, r = []) {
366
- const { regex: n, paramNames: o, isCatchAll: i, priority: u } = this.createPathRegex(t);
367
- return this._routes.push({
368
- method: e,
369
- path: t,
370
- regex: n,
371
- paramNames: o,
372
- isCatchAll: i,
373
- priority: u,
374
- handler: s,
375
- middlewares: r
376
- }), this.routesSorted = !1, this;
377
- }
378
- // Create regex for route path
379
- createPathRegex(e) {
380
- const t = T.get(e);
381
- if (t) return t;
382
- const s = [];
383
- let r = !1, n;
384
- const o = e.split("/").filter(Boolean);
385
- n = o.reduce((c, l) => l.startsWith("[...") ? c - 10 : l.startsWith("[[") ? c - 5 : l.startsWith("[") ? c - 1 : c + 1, 0);
386
- let i = "^";
387
- for (const c of o)
388
- if (c.startsWith("[...") && c.endsWith("]")) {
389
- r = !0;
390
- const l = c.slice(4, -1);
391
- s.push(l), i += "/(.+)";
392
- } else if (c.startsWith("[[") && c.endsWith("]]")) {
393
- const l = c.slice(2, -2);
394
- s.push(l), i += "(?:/([^/]+))?";
395
- } else if (c.startsWith("[") && c.endsWith("]")) {
396
- const l = c.slice(1, -1);
397
- s.push(l), i += "/([^/]+)";
398
- } else
399
- i += "/" + c.replace(/[-/\\^$*+?.()|[\]{}]/g, "\\$&");
400
- i += "/?$";
401
- const u = { regex: new RegExp(i), paramNames: s, isCatchAll: r, priority: n };
402
- return T.set(e, u), u;
403
- }
404
- // Create regex for prefix
405
- createPrefixRegex(e) {
406
- const t = [];
407
- let s = !1, r;
408
- const n = e.split("/").filter(Boolean);
409
- r = n.reduce((i, u) => u.startsWith("[...") ? i - 10 : u.startsWith("[[") ? i - 5 : u.startsWith("[") ? i - 1 : i + 1, 0);
410
- let o = "^";
411
- for (const i of n)
412
- if (i.startsWith("[...") && i.endsWith("]")) {
413
- s = !0;
414
- const u = i.slice(4, -1);
415
- t.push(u), o += "/(.+)";
416
- } else if (i.startsWith("[[") && i.endsWith("]]")) {
417
- const u = i.slice(2, -2);
418
- t.push(u), o += "(?:/([^/]+))?";
419
- } else if (i.startsWith("[") && i.endsWith("]")) {
420
- const u = i.slice(1, -1);
421
- t.push(u), o += "/([^/]+)";
422
- } else
423
- o += "/" + i.replace(/[-/\\^$*+?.()|[\]{}]/g, "\\$&");
424
- return o += "(?=/|$)", { regex: new RegExp(o), paramNames: t, isCatchAll: s, priority: r };
425
- }
426
- normalizePrefix(e) {
427
- return e.startsWith("/") ? e.replace(/\/$/, "") : `/${e.replace(/\/$/, "")}`;
428
- }
429
- extractPrefixParams(e, t) {
430
- const s = t.match(e.regex);
431
- if (!s) return {};
432
- const r = {};
433
- return e.isCatchAll && e.paramNames.length === 1 ? r[e.paramNames[0]] = s[1]?.replace(/^\//, "") || "" : e.paramNames.forEach((n, o) => {
434
- r[n] = s[o + 1] || "";
435
- }), r;
436
- }
437
- // FIXED: Nested router handling without duplicate middleware application
438
- async handleNestedRouters(e, t) {
439
- const s = [...this._nestedRouters].sort((r, n) => n.priority - r.priority);
440
- for (const r of s) {
441
- const n = t.match(r.regex);
442
- if (!n || n.index !== 0) continue;
443
- const o = n[0], i = t.slice(o.length) || "/", u = this.extractPrefixParams(r, o), c = {
444
- ...e,
445
- params: { ...e.params, ...u }
446
- }, l = async () => await r.router.handleAtPath(c, i), d = await this.applyMiddlewaresWithList(c, r.middlewares, l);
447
- if (d) return d;
448
- }
449
- return null;
450
- }
451
- // FIXED: Local route handling without duplicate middleware application
452
- async handleLocalRoutes(e, t, s) {
453
- const r = /* @__PURE__ */ new Set();
454
- let n = !1;
455
- for (const o of this._routes) {
456
- if (!o.regex.test(s) || (r.add(o.method), o.method === "GET" && (n = !0, r.add("HEAD")), !(o.method === t || t === "HEAD" && o.method === "GET"))) continue;
457
- const u = s.match(o.regex);
458
- if (!u) continue;
459
- const c = Object.fromEntries(
460
- o.paramNames.map((d, h) => [d, u[h + 1] || ""])
461
- );
462
- e.params = { ...e.params, ...c }, e.route = { ...e.route, id: o.path };
463
- const l = () => o.handler(e);
464
- return await this.applyMiddlewaresWithList(e, o.middlewares, l);
465
- }
466
- if (r.size > 0 || t === "HEAD" && n) {
467
- const o = [...r].join(", ");
468
- return t === "OPTIONS" ? new Response(null, {
469
- status: 200,
470
- headers: { Allow: o }
471
- }) : new Response("Method Not Allowed", {
472
- status: 405,
473
- headers: { Allow: o }
474
- });
475
- }
476
- return new Response("Not Found", { status: 404 });
477
- }
478
- sortRoutes() {
479
- this._routes.sort((e, t) => t.priority - e.priority), this.routesSorted = !0;
480
- }
481
- sortWsRoutes() {
482
- this._wsRoutes.sort((e, t) => t.priority - e.priority), this.wsRoutesSorted = !0;
483
- }
484
- formatActionResult(e) {
485
- return e instanceof Response ? e : e?.type === "failure" && "status" in e ? R.fail(e.status, e.data) : R.success(200, e ?? void 0);
486
- }
487
- handleActionError(e) {
488
- if (_(e))
489
- return R.error(e.status, { message: e.statusText || "Error" });
490
- if (N(e)) {
491
- const t = e.headers.get("Location") || "/";
492
- return R.redirect(e.status, t);
493
- }
494
- return console.error(e), R.error(500, { message: "Internal Server Error" });
495
- }
496
- static New() {
497
- return new E();
498
- }
133
+ function M(e = {}) {
134
+ let { methods: t = te, allowedHeaders: n = k, exposedHeaders: r, credentials: i = !1, maxAge: a = 86400, onResponse: o } = e, s = t.join(","), c = [...ne, ...n].join(","), l = [
135
+ ["Vary", "Origin,Access-Control-Request-Method,Access-Control-Request-Headers"],
136
+ ["Access-Control-Allow-Methods", s],
137
+ ["Access-Control-Allow-Headers", c]
138
+ ];
139
+ return r && l.push(["Access-Control-Expose-Headers", r.join(",")]), i && l.push(["Access-Control-Allow-Credentials", "true"]), a && l.push(["Access-Control-Max-Age", a.toString()]), async (t, n) => {
140
+ let r = t.request, i = r.headers.get("Origin"), a = r.method === "OPTIONS" && i !== null && r.headers.has("Access-Control-Request-Method"), s = j(i, e);
141
+ if (a) {
142
+ if (!s) return new Response(null, { status: 403 });
143
+ let e = new Response(null, { status: 204 });
144
+ for (let [t, n] of l) e.headers.set(t, n);
145
+ return e.headers.set("Access-Control-Allow-Origin", s), e;
146
+ }
147
+ let c = await n();
148
+ if (!c) return;
149
+ if (!s) return c;
150
+ let u = new Response(c.body, c);
151
+ for (let [e, t] of l) u.headers.set(e, t);
152
+ u.headers.set("Access-Control-Allow-Origin", s);
153
+ let d = u;
154
+ if (o) {
155
+ let e = o(d);
156
+ e && (d = e);
157
+ }
158
+ return d;
159
+ };
499
160
  }
500
- const R = {
501
- success: (a = 200, e) => new Response(JSON.stringify({ data: e, type: "success", status: a }), {
502
- status: a,
503
- headers: { "Content-Type": "application/json" }
504
- }),
505
- redirect: (a = 302, e) => new Response(JSON.stringify({ location: e, type: "redirect", status: a }), {
506
- status: a,
507
- headers: { "Content-Type": "application/json" }
508
- }),
509
- error: (a = 500, e) => new Response(JSON.stringify({ error: e, type: "error", status: a }), {
510
- status: a,
511
- headers: { "Content-Type": "application/json" }
512
- }),
513
- fail: (a = 400, e) => new Response(JSON.stringify({ data: e, type: "failure", status: a }), {
514
- status: a,
515
- headers: { "Content-Type": "application/json" }
516
- })
161
+ //#endregion
162
+ //#region src/middlewares/security/index.ts
163
+ var N = /* @__PURE__ */ S({ headers: () => F }), P = {
164
+ contentSecurityPolicy: "default-src 'self'; base-uri 'self'; frame-ancestors 'none'; object-src 'none'",
165
+ frameOptions: "DENY",
166
+ referrerPolicy: "no-referrer",
167
+ permissionsPolicy: "geolocation=(), microphone=(), camera=()",
168
+ crossOriginOpenerPolicy: "same-origin",
169
+ crossOriginResourcePolicy: "same-origin",
170
+ strictTransportSecurity: !1
517
171
  };
518
- class ie {
519
- constructor(e, t) {
520
- this.raw = e.headers.get("cookie") ?? "", this.setCookieHeader = t;
521
- }
522
- get(e, t) {
523
- return b(this.raw, t)[e];
524
- }
525
- getAll(e) {
526
- return Object.entries(b(this.raw, e)).filter(([, t]) => t !== void 0).map(([t, s]) => ({ name: t, value: s }));
527
- }
528
- set(e, t, s) {
529
- this.setCookieHeader(B(e, t, s));
530
- }
531
- delete(e, t) {
532
- this.set(e, "", { ...t, maxAge: 0 });
533
- }
172
+ function F(e = {}) {
173
+ let t = {
174
+ ...P,
175
+ ...e
176
+ };
177
+ return async (e, n) => {
178
+ let r = await n();
179
+ if (!r) return;
180
+ let i = new Headers(r.headers);
181
+ return I(i, "content-security-policy", t.contentSecurityPolicy), I(i, "x-frame-options", t.frameOptions), I(i, "referrer-policy", t.referrerPolicy), I(i, "permissions-policy", t.permissionsPolicy), I(i, "cross-origin-opener-policy", t.crossOriginOpenerPolicy), I(i, "cross-origin-resource-policy", t.crossOriginResourcePolicy), I(i, "strict-transport-security", t.strictTransportSecurity), new Response(r.body, {
182
+ status: r.status,
183
+ statusText: r.statusText,
184
+ headers: i
185
+ });
186
+ };
534
187
  }
535
- class C extends Error {
536
- constructor(e = "Payload Too Large") {
537
- super(e), this.status = 413, this.name = "PayloadTooLargeError";
538
- }
188
+ function I(e, t, n) {
189
+ !n || e.has(t) || e.set(t, n);
539
190
  }
540
- class Le extends E {
541
- constructor(e) {
542
- super(), this.upgradeHandlerInstalled = !1, this.config = e ?? { type: "http", options: {} }, this.wss = new z({
543
- noServer: !0,
544
- maxPayload: this.config.security?.maxWebSocketPayload ?? 1024 * 1024
545
- });
546
- }
547
- get server() {
548
- if (!this._server) {
549
- const e = (t, s) => {
550
- this.handleRequest(t, s).catch((r) => {
551
- console.error("Unhandled request error:", r), s.statusCode = 500, s.end("Internal Server Error");
552
- });
553
- };
554
- this._server = this.config.type === "https" ? $(this.config.options, e) : M(this.config.options, e);
555
- }
556
- return this._server;
557
- }
558
- listen(...e) {
559
- return this.upgradeHandlerInstalled || (this.installUpgradeHandler(), this.upgradeHandlerInstalled = !0), this.server.listen(...e), this;
560
- }
561
- installUpgradeHandler() {
562
- this.server.on("upgrade", (e, t, s) => {
563
- if (e.headers.upgrade?.toLowerCase() !== "websocket") {
564
- t.destroy();
565
- return;
566
- }
567
- let r, n;
568
- try {
569
- r = this.toURL(e, !0), n = this.toRequest(e, r, !0);
570
- } catch {
571
- t.destroy();
572
- return;
573
- }
574
- const o = this.toRequestEvent(n, r, {
575
- getClientAddress: () => e.socket.remoteAddress ?? "127.0.0.1",
576
- setHeader: () => {
577
- },
578
- pushSetCookie: () => {
579
- }
580
- });
581
- this.canHandleWebSocket(o).then((i) => {
582
- if (!i || !this.isAllowedWebSocketOrigin(e)) {
583
- t.destroy();
584
- return;
585
- }
586
- this.wss.handleUpgrade(e, t, s, (u) => {
587
- this.handleWebSocket(o, u).then((c) => {
588
- !c && u.readyState === P.OPEN && u.close(1008, "Route not found");
589
- }).catch((c) => {
590
- console.error("WebSocket routing error:", c), u.readyState === P.OPEN && u.close(1011, "Internal error");
591
- });
592
- });
593
- }).catch(() => t.destroy());
594
- });
595
- }
596
- close(e) {
597
- this.wss.close(() => {
598
- this.server.close(e);
599
- });
600
- }
601
- address() {
602
- return this.server.address();
603
- }
604
- get listening() {
605
- return this.server.listening;
606
- }
607
- async handleRequest(e, t) {
608
- if (!this.isRequestBodyAllowed(e)) {
609
- t.statusCode = 413, t.end("Payload Too Large");
610
- return;
611
- }
612
- const s = this.toWebRequest(e), r = new URL(s.url), n = {}, o = [], i = this.toRequestEvent(s, r, {
613
- getClientAddress: () => e.socket.remoteAddress ?? "127.0.0.1",
614
- setHeader: (c, l) => {
615
- n[c.toLowerCase()] = l;
616
- },
617
- pushSetCookie: (c) => {
618
- o.push(c);
619
- }
620
- });
621
- let u;
622
- try {
623
- u = await this.handle(i);
624
- } catch (c) {
625
- u = this.handleError(c);
626
- }
627
- for (const [c, l] of Object.entries(n))
628
- t.setHeader(c, l);
629
- o.length > 0 && t.setHeader("Set-Cookie", o), await this.sendWebResponse(t, u);
630
- }
631
- toWebRequest(e) {
632
- const t = this.toURL(e, !1);
633
- return this.toRequest(e, t, !1);
634
- }
635
- toRequest(e, t, s) {
636
- const r = {
637
- method: s ? "GET" : e.method,
638
- headers: this.toHeaders(e.headers),
639
- // @ts-ignore
640
- duplex: "half"
641
- };
642
- return !s && e.method !== "GET" && e.method !== "HEAD" && (r.body = F.toWeb(this.wrapRequestBody(e))), new Request(t, r);
643
- }
644
- wrapRequestBody(e) {
645
- const t = this.config.security?.maxRequestBodySize;
646
- if (!t)
647
- return e;
648
- let s = 0;
649
- const r = new D({
650
- transform(n, o, i) {
651
- if (s += Buffer.byteLength(n), s > t) {
652
- i(new C());
653
- return;
654
- }
655
- i(null, n);
656
- }
657
- });
658
- return e.on("aborted", () => r.destroy(new Error("Request aborted"))), e.on("error", (n) => r.destroy(n)), e.pipe(r), r;
659
- }
660
- toURL(e, t) {
661
- const s = e.socket instanceof I ? t ? "wss" : "https" : t ? "ws" : "http", r = this.resolveAuthority(e);
662
- return new URL(e.url ?? "/", `${s}://${r}`);
663
- }
664
- resolveAuthority(e) {
665
- const t = this.config.security?.trustHostHeader ? this.normalizeTrustedHost(e.headers.host) : null;
666
- if (t)
667
- return t;
668
- const s = this.server.address();
669
- return s && typeof s == "object" ? `${s.address.includes(":") ? `[${s.address}]` : s.address}:${s.port}` : e.socket.localPort ? `127.0.0.1:${e.socket.localPort}` : "localhost";
670
- }
671
- normalizeTrustedHost(e) {
672
- if (!e) return null;
673
- let t;
674
- try {
675
- t = new URL(`http://${e}`);
676
- } catch {
677
- return null;
678
- }
679
- if (t.username || t.password || t.pathname !== "/" || t.search || t.hash)
680
- return null;
681
- const s = t.port ? `${t.hostname}:${t.port}` : t.hostname, r = this.config.security?.allowedHosts;
682
- return !r || this.matchesValue(s, r) ? s : null;
683
- }
684
- matchesValue(e, t) {
685
- return (Array.isArray(t) ? t : [t]).some((r) => typeof r == "string" ? r === e : r instanceof RegExp ? r.test(e) : r(e));
686
- }
687
- toHeaders(e) {
688
- const t = new Headers();
689
- for (const [s, r] of Object.entries(e))
690
- if (r !== void 0) {
691
- if (Array.isArray(r)) {
692
- const n = s.toLowerCase() === "cookie" ? r.join("; ") : r.join(", ");
693
- t.set(s, n);
694
- continue;
695
- }
696
- t.set(s, r);
697
- }
698
- return t;
699
- }
700
- isRequestBodyAllowed(e) {
701
- const t = this.config.security?.maxRequestBodySize;
702
- if (!t) return !0;
703
- const s = e.headers["content-length"];
704
- if (!s) return !0;
705
- const r = Number.parseInt(Array.isArray(s) ? s[0] : s, 10);
706
- return Number.isFinite(r) && r <= t;
707
- }
708
- handleError(e) {
709
- if (e instanceof C)
710
- return new Response(e.message, { status: e.status });
711
- if (_(e))
712
- return new Response(JSON.stringify({
713
- error: e.statusText || "Error",
714
- status: e.status
715
- }), {
716
- status: e.status,
717
- headers: { "Content-Type": "application/json" }
718
- });
719
- if (N(e)) {
720
- const t = e.headers.get("Location") || "/";
721
- return new Response(null, {
722
- status: e.status,
723
- headers: { Location: t }
724
- });
725
- }
726
- return console.error("Unhandled error:", e), new Response("Internal Server Error", { status: 500 });
727
- }
728
- async sendWebResponse(e, t) {
729
- if (e.statusCode = t.status, t.headers.forEach((n, o) => {
730
- e.setHeader(o, n);
731
- }), e.hasHeader("Server") || e.setHeader("Server", "WebHTTPServer"), !t.body || this.shouldOmitResponseBody(t, e.req?.method)) {
732
- e.end();
733
- return;
734
- }
735
- const s = t.body.getReader(), r = U.toWeb(e).getWriter();
736
- try {
737
- for (; ; ) {
738
- const { done: n, value: o } = await s.read();
739
- if (n) break;
740
- await r.write(o);
741
- }
742
- } finally {
743
- await r.close().catch(() => {
744
- });
745
- }
746
- }
747
- shouldOmitResponseBody(e, t) {
748
- return t === "HEAD" ? !0 : e.status === 204 || e.status === 205 || e.status === 304;
749
- }
750
- isAllowedWebSocketOrigin(e) {
751
- const t = e.headers.origin;
752
- if (!t) return !0;
753
- const s = this.config.security?.allowedWebSocketOrigins;
754
- return s ? this.matchesValue(t, s) : !0;
755
- }
756
- createEventFetch(e, t) {
757
- return async (s, r) => {
758
- const n = this.toEventFetchRequest(e, s, r);
759
- if (n.url.startsWith(`${e.url.origin}/`)) {
760
- const o = this.toRequestEvent(n, new URL(n.url), t);
761
- try {
762
- return await this.handle(o);
763
- } catch (i) {
764
- return this.handleError(i);
765
- }
766
- }
767
- return fetch(n);
768
- };
769
- }
770
- toEventFetchRequest(e, t, s) {
771
- const r = t instanceof URL ? t.toString() : t, n = r instanceof Request ? r : new Request(new URL(String(r), e.url), s);
772
- if (r instanceof Request && !s)
773
- return this.withInheritedRequestHeaders(e, r);
774
- const o = new Headers(r instanceof Request ? r.headers : s?.headers), i = s?.method ?? (r instanceof Request ? r.method : void 0), u = s?.body ?? (r instanceof Request ? r.body : void 0), c = u ? "half" : void 0;
775
- return this.inheritRequestHeader(e.request.headers, o, "cookie"), this.inheritRequestHeader(e.request.headers, o, "authorization"), new Request(n.url, {
776
- ...s,
777
- method: i,
778
- headers: o,
779
- body: u,
780
- // @ts-ignore
781
- duplex: c
782
- });
783
- }
784
- withInheritedRequestHeaders(e, t) {
785
- const s = new Headers(t.headers);
786
- return this.inheritRequestHeader(e.request.headers, s, "cookie"), this.inheritRequestHeader(e.request.headers, s, "authorization"), new Request(t, {
787
- headers: s,
788
- // @ts-ignore
789
- duplex: t.body ? "half" : void 0
790
- });
791
- }
792
- inheritRequestHeader(e, t, s) {
793
- if (t.has(s)) return;
794
- const r = e.get(s);
795
- r && t.set(s, r);
796
- }
797
- toRequestEvent(e, t, s) {
798
- const r = new ie(e, s.pushSetCookie), n = this.config, o = {}, i = { name: "WebHTTPServer" }, u = /* @__PURE__ */ new Set(), c = {
799
- request: e,
800
- url: t,
801
- cookies: r,
802
- getClientAddress: s.getClientAddress,
803
- get locals() {
804
- return o;
805
- },
806
- get platform() {
807
- return i;
808
- },
809
- fetch: async (d, h) => l(d, h),
810
- params: {},
811
- route: { id: null },
812
- setHeaders: (d) => {
813
- for (const [h, p] of Object.entries(d)) {
814
- const m = h.toLowerCase();
815
- if (m === "set-cookie")
816
- throw new TypeError("Use event.cookies for Set-Cookie headers");
817
- if (u.has(m))
818
- throw new TypeError(`Header "${h}" has already been set`);
819
- u.add(m), s.setHeader(h, p);
820
- }
821
- }
822
- }, l = this.createEventFetch(c, s);
823
- return n.locals && Object.assign(o, n.locals(c)), n.platform && Object.assign(i, n.platform(c)), c;
824
- }
191
+ //#endregion
192
+ //#region src/middlewares/requestid/index.ts
193
+ var L = /* @__PURE__ */ S({ assign: () => R });
194
+ function R(t = {}) {
195
+ let n = t.headerName?.toLowerCase() ?? "x-request-id", r = t.generate ?? e;
196
+ return async (e, t) => {
197
+ let i = e.request.headers.get(n) ?? r();
198
+ Object.assign(e.locals, { requestId: i });
199
+ let a = await t();
200
+ if (!a) return;
201
+ if (a.headers.has(n)) return a;
202
+ let o = new Headers(a.headers);
203
+ return o.set(n, i), new Response(a.body, {
204
+ status: a.status,
205
+ statusText: a.statusText,
206
+ headers: o
207
+ });
208
+ };
825
209
  }
826
- const ce = {
827
- ".avif": "image/avif",
828
- ".css": "text/css; charset=utf-8",
829
- ".gif": "image/gif",
830
- ".html": "text/html; charset=utf-8",
831
- ".ico": "image/x-icon",
832
- ".jpg": "image/jpeg",
833
- ".jpeg": "image/jpeg",
834
- ".js": "text/javascript; charset=utf-8",
835
- ".json": "application/json; charset=utf-8",
836
- ".mjs": "text/javascript; charset=utf-8",
837
- ".pdf": "application/pdf",
838
- ".png": "image/png",
839
- ".svg": "image/svg+xml; charset=utf-8",
840
- ".txt": "text/plain; charset=utf-8",
841
- ".wasm": "application/wasm",
842
- ".webp": "image/webp",
843
- ".xml": "application/xml; charset=utf-8"
844
- }, ue = {
845
- index: "index.html",
846
- cacheControl: "public, max-age=0",
847
- dotFiles: "ignore"
210
+ //#endregion
211
+ //#region src/middlewares/timeout/index.ts
212
+ var z = /* @__PURE__ */ S({ deadline: () => B });
213
+ function B(e) {
214
+ let { ms: t, status: n = 504, body: r = "Gateway Timeout", onTimeout: i } = e;
215
+ if (!Number.isFinite(t) || t <= 0) throw TypeError("Timeout.deadline requires a positive ms value");
216
+ return async (e, a) => {
217
+ let o = e.request, s = new AbortController(), c = () => s.abort();
218
+ o.signal.addEventListener("abort", c, { once: !0 });
219
+ let l = AbortSignal.any([o.signal, s.signal]);
220
+ e.request = new Request(o, {
221
+ signal: l,
222
+ duplex: o.body ? "half" : void 0
223
+ });
224
+ let u;
225
+ try {
226
+ return await Promise.race([a(), new Promise((e) => {
227
+ u = setTimeout(() => {
228
+ s.abort(), i?.(), e(new Response(r, { status: n }));
229
+ }, t);
230
+ })]);
231
+ } finally {
232
+ o.signal.removeEventListener("abort", c), u && clearTimeout(u);
233
+ }
234
+ };
235
+ }
236
+ //#endregion
237
+ //#region src/types/RequestMethod.ts
238
+ var V = [
239
+ "GET",
240
+ "PUT",
241
+ "POST",
242
+ "DELETE",
243
+ "PATCH",
244
+ "HEAD",
245
+ "OPTIONS"
246
+ ], H = class {
247
+ static {
248
+ this.cache = /* @__PURE__ */ new Map();
249
+ }
250
+ static get(e) {
251
+ return this.cache.get(e);
252
+ }
253
+ static set(e, t) {
254
+ this.cache.set(e, t);
255
+ }
256
+ }, U = class {
257
+ constructor() {
258
+ this._routes = [], this._wsRoutes = [], this._nestedRouters = [], this._middlewares = [], this._preHandlers = [], this._postHandlers = [], this.routesSorted = !1, this.wsRoutesSorted = !1;
259
+ }
260
+ get routes() {
261
+ return this._routes;
262
+ }
263
+ get nestedRouters() {
264
+ return this._nestedRouters;
265
+ }
266
+ GET(e, t, ...n) {
267
+ return this.addHandler("GET", e, t, n);
268
+ }
269
+ POST(e, t, ...n) {
270
+ return this.addHandler("POST", e, t, n);
271
+ }
272
+ PUT(e, t, ...n) {
273
+ return this.addHandler("PUT", e, t, n);
274
+ }
275
+ PATCH(e, t, ...n) {
276
+ return this.addHandler("PATCH", e, t, n);
277
+ }
278
+ DELETE(e, t, ...n) {
279
+ return this.addHandler("DELETE", e, t, n);
280
+ }
281
+ HEAD(e, t, ...n) {
282
+ return this.addHandler("HEAD", e, t, n);
283
+ }
284
+ OPTIONS(e, t, ...n) {
285
+ return this.addHandler("OPTIONS", e, t, n);
286
+ }
287
+ USE(e, t, ...n) {
288
+ return V.forEach((r) => this.addHandler(r, e, t, n)), this;
289
+ }
290
+ action(e, t, ...n) {
291
+ return this.addHandler("POST", e, async (e) => {
292
+ try {
293
+ let n = await t(e);
294
+ return this.formatActionResult(n);
295
+ } catch (e) {
296
+ return this.handleActionError(e);
297
+ }
298
+ }, n);
299
+ }
300
+ use(e, t, ...n) {
301
+ let r, i, a = n;
302
+ Array.isArray(e) ? ([r, i] = e, a = e.length > 2 ? e.slice(2) : []) : (r = e, i = t);
303
+ let o = this.normalizePrefix(r), { regex: s, paramNames: c, isCatchAll: l, priority: u } = this.createPrefixRegex(o);
304
+ return this._nestedRouters.push({
305
+ prefix: o,
306
+ router: i,
307
+ regex: s,
308
+ paramNames: c,
309
+ isCatchAll: l,
310
+ priority: u,
311
+ middlewares: a
312
+ }), this;
313
+ }
314
+ useMiddleware(...e) {
315
+ return this._middlewares.push(...e), this;
316
+ }
317
+ pre(...e) {
318
+ return this._preHandlers.push(...e), this;
319
+ }
320
+ post(...e) {
321
+ return this._postHandlers.push(...e), this;
322
+ }
323
+ discard(e, t) {
324
+ return this._nestedRouters = this._nestedRouters.filter((t) => t.prefix !== e), this._routes = this._routes.filter((n) => n.path !== e || t && n.method !== t), this;
325
+ }
326
+ WS(e, t, ...n) {
327
+ let { regex: r, paramNames: i, isCatchAll: a, priority: o } = this.createPathRegex(e);
328
+ return this._wsRoutes.push({
329
+ path: e,
330
+ regex: r,
331
+ paramNames: i,
332
+ isCatchAll: a,
333
+ priority: o,
334
+ handler: t,
335
+ middlewares: n
336
+ }), this.wsRoutesSorted = !1, this;
337
+ }
338
+ async canHandleWebSocket(e) {
339
+ return this.canHandleWebSocketAtPath(e, e.url.pathname);
340
+ }
341
+ async canHandleWebSocketAtPath(e, t) {
342
+ this.wsRoutesSorted || this.sortWsRoutes();
343
+ for (let n of [...this._nestedRouters].sort((e, t) => t.priority - e.priority)) {
344
+ let r = t.match(n.regex);
345
+ if (!r || r.index !== 0) continue;
346
+ let i = r[0], a = t.slice(i.length) || "/", o = {
347
+ ...e,
348
+ params: {
349
+ ...e.params,
350
+ ...this.extractPrefixParams(n, i)
351
+ }
352
+ };
353
+ if (await n.router.canHandleWebSocketAtPath(o, a)) return !0;
354
+ }
355
+ for (let e of this._wsRoutes) if (e.regex.test(t)) return !0;
356
+ return !1;
357
+ }
358
+ async handleWebSocket(e, t) {
359
+ return this.handleWebSocketAtPath(e, t, e.url.pathname);
360
+ }
361
+ async handleWebSocketAtPath(e, t, n) {
362
+ this.wsRoutesSorted || this.sortWsRoutes();
363
+ for (let r of [...this._nestedRouters].sort((e, t) => t.priority - e.priority)) {
364
+ let i = n.match(r.regex);
365
+ if (!i || i.index !== 0) continue;
366
+ let a = i[0], o = n.slice(a.length) || "/", s = this.extractPrefixParams(r, a), c = {
367
+ ...e,
368
+ params: {
369
+ ...e.params,
370
+ ...s
371
+ }
372
+ }, l = [...this._middlewares, ...r.middlewares];
373
+ if (await this.applyMiddlewaresWithList(c, l, () => r.router.handleWebSocketAtPath(c, t, o))) return !0;
374
+ }
375
+ for (let r of this._wsRoutes) {
376
+ if (!r.regex.test(n)) continue;
377
+ let i = n.match(r.regex);
378
+ if (!i) continue;
379
+ let a = Object.fromEntries(r.paramNames.map((e, t) => {
380
+ let n = i[t + 1];
381
+ return n === void 0 ? void 0 : [e, decodeURIComponent(n)];
382
+ }).filter((e) => e !== void 0)), o = {
383
+ ...e,
384
+ params: {
385
+ ...e.params,
386
+ ...a
387
+ },
388
+ route: {
389
+ ...e.route,
390
+ id: r.path
391
+ },
392
+ websocket: t
393
+ }, s = [...this._middlewares, ...r.middlewares];
394
+ if (await this.applyMiddlewaresWithList(o, s, () => r.handler(o)) !== void 0) return !0;
395
+ }
396
+ return !1;
397
+ }
398
+ async handle(e) {
399
+ return this.handleAtPath(e, e.url.pathname);
400
+ }
401
+ async handleAtPath(e, t) {
402
+ try {
403
+ let n = e.request.method, r = await this.runPreHandlers(e);
404
+ r ||= await this.applyMiddlewaresWithList(e, this._middlewares, async () => await this.handleNestedRouters(e, t) || (this.routesSorted || this.sortRoutes(), this.handleLocalRoutes(e, n, t)));
405
+ let i = r || new Response("No Content", { status: 204 });
406
+ return await this.runPostHandlers(e, i);
407
+ } catch (e) {
408
+ if (T(e)) return e;
409
+ throw e;
410
+ }
411
+ }
412
+ async applyMiddlewaresWithList(e, t, n) {
413
+ let r = [...t], i = async (t) => t >= r.length ? n() : r[t](e, () => i(t + 1));
414
+ return i(0);
415
+ }
416
+ async runPreHandlers(e) {
417
+ for (let t of this._preHandlers) {
418
+ let n = await t(e);
419
+ if (n instanceof Response) return n;
420
+ }
421
+ }
422
+ async runPostHandlers(e, t) {
423
+ let n = t;
424
+ for (let t of this._postHandlers) {
425
+ let r = await t(e, n);
426
+ r instanceof Response && (n = r);
427
+ }
428
+ return n;
429
+ }
430
+ addHandler(e, t, n, r = []) {
431
+ let { regex: i, paramNames: a, isCatchAll: o, priority: s } = this.createPathRegex(t);
432
+ return this._routes.push({
433
+ method: e,
434
+ path: t,
435
+ regex: i,
436
+ paramNames: a,
437
+ isCatchAll: o,
438
+ priority: s,
439
+ handler: n,
440
+ middlewares: r
441
+ }), this.routesSorted = !1, this;
442
+ }
443
+ createPathRegex(e) {
444
+ let t = H.get(e);
445
+ if (t) return t;
446
+ let n = [], r = !1, i, a = e.split("/").filter(Boolean);
447
+ i = a.reduce((e, t) => t.startsWith("[...") ? e - 10 : t.startsWith("[[") ? e - 5 : t.startsWith("[") ? e - 1 : e + 1, 0);
448
+ let o = "^";
449
+ for (let e of a) if (e.startsWith("[...") && e.endsWith("]")) {
450
+ r = !0;
451
+ let t = e.slice(4, -1);
452
+ n.push(t), o += "/(.+)";
453
+ } else if (e.startsWith("[[") && e.endsWith("]]")) {
454
+ let t = e.slice(2, -2);
455
+ n.push(t), o += "(?:/([^/]+))?";
456
+ } else if (e.startsWith("[") && e.endsWith("]")) {
457
+ let t = e.slice(1, -1);
458
+ n.push(t), o += "/([^/]+)";
459
+ } else o += "/" + e.replace(/[-/\\^$*+?.()|[\]{}]/g, "\\$&");
460
+ o += "/?$";
461
+ let s = {
462
+ regex: new RegExp(o),
463
+ paramNames: n,
464
+ isCatchAll: r,
465
+ priority: i
466
+ };
467
+ return H.set(e, s), s;
468
+ }
469
+ createPrefixRegex(e) {
470
+ let t = [], n = !1, r, i = e.split("/").filter(Boolean);
471
+ r = i.reduce((e, t) => t.startsWith("[...") ? e - 10 : t.startsWith("[[") ? e - 5 : t.startsWith("[") ? e - 1 : e + 1, 0);
472
+ let a = "^";
473
+ for (let e of i) if (e.startsWith("[...") && e.endsWith("]")) {
474
+ n = !0;
475
+ let r = e.slice(4, -1);
476
+ t.push(r), a += "/(.+)";
477
+ } else if (e.startsWith("[[") && e.endsWith("]]")) {
478
+ let n = e.slice(2, -2);
479
+ t.push(n), a += "(?:/([^/]+))?";
480
+ } else if (e.startsWith("[") && e.endsWith("]")) {
481
+ let n = e.slice(1, -1);
482
+ t.push(n), a += "/([^/]+)";
483
+ } else a += "/" + e.replace(/[-/\\^$*+?.()|[\]{}]/g, "\\$&");
484
+ return a += "(?=/|$)", {
485
+ regex: new RegExp(a),
486
+ paramNames: t,
487
+ isCatchAll: n,
488
+ priority: r
489
+ };
490
+ }
491
+ normalizePrefix(e) {
492
+ return e.startsWith("/") ? e.replace(/\/$/, "") : `/${e.replace(/\/$/, "")}`;
493
+ }
494
+ extractPrefixParams(e, t) {
495
+ let n = t.match(e.regex);
496
+ if (!n) return {};
497
+ let r = {};
498
+ if (e.isCatchAll && e.paramNames.length === 1) {
499
+ let t = n[1]?.replace(/^\//, "");
500
+ t !== void 0 && (r[e.paramNames[0]] = decodeURIComponent(t));
501
+ } else e.paramNames.forEach((e, t) => {
502
+ let i = n[t + 1];
503
+ i !== void 0 && (r[e] = decodeURIComponent(i));
504
+ });
505
+ return r;
506
+ }
507
+ async handleNestedRouters(e, t) {
508
+ let n = [...this._nestedRouters].sort((e, t) => t.priority - e.priority);
509
+ for (let r of n) {
510
+ let n = t.match(r.regex);
511
+ if (!n || n.index !== 0) continue;
512
+ let i = n[0], a = t.slice(i.length) || "/", o = this.extractPrefixParams(r, i), s = {
513
+ ...e,
514
+ params: {
515
+ ...e.params,
516
+ ...o
517
+ }
518
+ }, c = await this.applyMiddlewaresWithList(s, r.middlewares, async () => await r.router.handleAtPath(s, a));
519
+ if (c) return c;
520
+ }
521
+ return null;
522
+ }
523
+ async handleLocalRoutes(e, t, n) {
524
+ let r = /* @__PURE__ */ new Set(), i = !1;
525
+ for (let a of this._routes) {
526
+ if (!a.regex.test(n) || (r.add(a.method), a.method === "GET" && (i = !0, r.add("HEAD")), !(a.method === t || t === "HEAD" && a.method === "GET"))) continue;
527
+ let o = n.match(a.regex);
528
+ if (!o) continue;
529
+ let s = Object.fromEntries(a.paramNames.map((e, t) => {
530
+ let n = o[t + 1];
531
+ return n === void 0 ? void 0 : [e, decodeURIComponent(n)];
532
+ }).filter((e) => e !== void 0));
533
+ return e.params = {
534
+ ...e.params,
535
+ ...s
536
+ }, e.route = {
537
+ ...e.route,
538
+ id: a.path
539
+ }, await this.applyMiddlewaresWithList(e, a.middlewares, () => a.handler(e));
540
+ }
541
+ if (r.size > 0 || t === "HEAD" && i) {
542
+ let e = [...r].join(", ");
543
+ return t === "OPTIONS" ? new Response(null, {
544
+ status: 200,
545
+ headers: { Allow: e }
546
+ }) : new Response("Method Not Allowed", {
547
+ status: 405,
548
+ headers: { Allow: e }
549
+ });
550
+ }
551
+ return new Response("Not Found", { status: 404 });
552
+ }
553
+ sortRoutes() {
554
+ this._routes.sort((e, t) => t.priority - e.priority), this.routesSorted = !0;
555
+ }
556
+ sortWsRoutes() {
557
+ this._wsRoutes.sort((e, t) => t.priority - e.priority), this.wsRoutesSorted = !0;
558
+ }
559
+ formatActionResult(e) {
560
+ return e instanceof Response ? e : e?.type === "failure" && "status" in e ? W.fail(e.status, e.data) : W.success(200, e ?? void 0);
561
+ }
562
+ handleActionError(e) {
563
+ if (C(e)) return W.error(e.status, { message: e.statusText || "Error" });
564
+ if (w(e)) {
565
+ let t = e.headers.get("Location") || "/";
566
+ return W.redirect(e.status, t);
567
+ }
568
+ return console.error(e), W.error(500, { message: "Internal Server Error" });
569
+ }
570
+ }, W = {
571
+ success: (e = 200, t) => new Response(JSON.stringify({
572
+ data: t,
573
+ type: "success",
574
+ status: e
575
+ }), {
576
+ status: e,
577
+ headers: { "Content-Type": "application/json" }
578
+ }),
579
+ redirect: (e = 302, t) => new Response(JSON.stringify({
580
+ location: t,
581
+ type: "redirect",
582
+ status: e
583
+ }), {
584
+ status: e,
585
+ headers: { "Content-Type": "application/json" }
586
+ }),
587
+ error: (e = 500, t) => new Response(JSON.stringify({
588
+ error: t,
589
+ type: "error",
590
+ status: e
591
+ }), {
592
+ status: e,
593
+ headers: { "Content-Type": "application/json" }
594
+ }),
595
+ fail: (e = 400, t) => new Response(JSON.stringify({
596
+ data: t,
597
+ type: "failure",
598
+ status: e
599
+ }), {
600
+ status: e,
601
+ headers: { "Content-Type": "application/json" }
602
+ })
603
+ }, re = class {
604
+ constructor(e, t) {
605
+ this.raw = e.headers.get("cookie") ?? "", this.setCookieHeader = t;
606
+ }
607
+ get(e, t) {
608
+ return l(this.raw, t)[e];
609
+ }
610
+ getAll(e) {
611
+ return Object.entries(l(this.raw, e)).filter(([, e]) => e !== void 0).map(([e, t]) => ({
612
+ name: e,
613
+ value: t
614
+ }));
615
+ }
616
+ set(e, t, n) {
617
+ this.setCookieHeader(u(e, t, n));
618
+ }
619
+ delete(e, t) {
620
+ this.set(e, "", {
621
+ ...t,
622
+ maxAge: 0
623
+ });
624
+ }
625
+ }, G = class extends Error {
626
+ constructor(e = "Payload Too Large") {
627
+ super(e), this.status = 413, this.name = "PayloadTooLargeError";
628
+ }
629
+ }, K = class extends U {
630
+ constructor(e) {
631
+ super(), this.upgradeHandlerInstalled = !1, this.config = e ?? {
632
+ type: "http",
633
+ options: {}
634
+ }, this.wss = new c({
635
+ noServer: !0,
636
+ maxPayload: this.config.security?.maxWebSocketPayload ?? 1024 * 1024
637
+ });
638
+ }
639
+ get server() {
640
+ if (!this._server) {
641
+ let e = (e, t) => {
642
+ this.handleRequest(e, t).catch((e) => {
643
+ console.error("Unhandled request error:", e), t.statusCode = 500, t.end("Internal Server Error");
644
+ });
645
+ };
646
+ this._server = this.config.type === "https" ? n(this.config.options, e) : t(this.config.options, e), this.configureServerTimeouts(this._server);
647
+ }
648
+ return this._server;
649
+ }
650
+ listen(...e) {
651
+ return this.upgradeHandlerInstalled ||= (this.installUpgradeHandler(), !0), this.server.listen(...e), this;
652
+ }
653
+ installUpgradeHandler() {
654
+ this.server.on("upgrade", (e, t, n) => {
655
+ if (e.headers.upgrade?.toLowerCase() !== "websocket") {
656
+ t.destroy();
657
+ return;
658
+ }
659
+ let r, i;
660
+ try {
661
+ r = this.toURL(e, !0), i = this.toRequest(e, r, !0);
662
+ } catch {
663
+ t.destroy();
664
+ return;
665
+ }
666
+ let a = this.toRequestEvent(i, r, {
667
+ getClientAddress: () => this.getClientAddress(e),
668
+ setHeader: () => {},
669
+ pushSetCookie: () => {}
670
+ });
671
+ this.canHandleWebSocket(a).then((r) => {
672
+ if (!r || !this.isAllowedWebSocketOrigin(e)) {
673
+ t.destroy();
674
+ return;
675
+ }
676
+ this.wss.handleUpgrade(e, t, n, (e) => {
677
+ this.handleWebSocket(a, e).then((t) => {
678
+ !t && e.readyState === s.OPEN && e.close(1008, "Route not found");
679
+ }).catch((t) => {
680
+ console.error("WebSocket routing error:", t), e.readyState === s.OPEN && e.close(1011, "Internal error");
681
+ });
682
+ });
683
+ }).catch(() => t.destroy());
684
+ });
685
+ }
686
+ close(e) {
687
+ this.wss.close(() => {
688
+ this.server.close(e);
689
+ });
690
+ }
691
+ address() {
692
+ return this.server.address();
693
+ }
694
+ get listening() {
695
+ return this.server.listening;
696
+ }
697
+ async handleRequest(e, t) {
698
+ if (!this.isRequestBodyAllowed(e)) {
699
+ t.statusCode = 413, t.end("Payload Too Large");
700
+ return;
701
+ }
702
+ let n = new AbortController(), r = () => n.abort();
703
+ e.once("aborted", r), e.once("close", r), t.once("close", r);
704
+ let i = this.toWebRequest(e, n.signal), a = new URL(i.url), o = {}, s = [], c = this.toRequestEvent(i, a, {
705
+ getClientAddress: () => this.getClientAddress(e),
706
+ setHeader: (e, t) => {
707
+ o[e.toLowerCase()] = t;
708
+ },
709
+ pushSetCookie: (e) => {
710
+ s.push(e);
711
+ }
712
+ }), l;
713
+ try {
714
+ l = await this.handle(c);
715
+ } catch (e) {
716
+ l = this.handleError(e);
717
+ }
718
+ for (let [e, n] of Object.entries(o)) t.setHeader(e, n);
719
+ s.length > 0 && t.setHeader("Set-Cookie", s), await this.sendWebResponse(t, l);
720
+ }
721
+ toWebRequest(e, t) {
722
+ let n = this.toURL(e, !1);
723
+ return this.toRequest(e, n, !1, t);
724
+ }
725
+ toRequest(e, t, n, r) {
726
+ let a = {
727
+ method: n ? "GET" : e.method,
728
+ headers: this.toHeaders(e.headers),
729
+ signal: r,
730
+ duplex: "half"
731
+ };
732
+ return !n && e.method !== "GET" && e.method !== "HEAD" && (a.body = i.toWeb(this.wrapRequestBody(e))), new Request(t, a);
733
+ }
734
+ wrapRequestBody(e) {
735
+ let t = this.config.security?.maxRequestBodySize;
736
+ if (!t) return e;
737
+ let n = 0, r = new a({ transform(e, r, i) {
738
+ if (n += Buffer.byteLength(e), n > t) {
739
+ i(new G());
740
+ return;
741
+ }
742
+ i(null, e);
743
+ } });
744
+ return e.on("aborted", () => r.destroy(/* @__PURE__ */ Error("Request aborted"))), e.on("error", (e) => r.destroy(e)), e.pipe(r), r;
745
+ }
746
+ toURL(e, t) {
747
+ let n = this.resolveProtocol(e, t), r = this.resolveAuthority(e);
748
+ return new URL(e.url ?? "/", `${n}://${r}`);
749
+ }
750
+ resolveProtocol(e, t) {
751
+ let n = this.getTrustedForwardedHeader(e, "x-forwarded-proto")?.split(",")[0]?.trim().toLowerCase();
752
+ return n === "http" || n === "https" ? t ? n === "https" ? "wss" : "ws" : n : e.socket instanceof r ? t ? "wss" : "https" : t ? "ws" : "http";
753
+ }
754
+ resolveAuthority(e) {
755
+ let t = this.getTrustedForwardedHeader(e, "x-forwarded-host") ?? e.headers.host, n = this.config.security?.trustHostHeader ? this.normalizeTrustedHost(t) : null;
756
+ if (n) return n;
757
+ let r = this.server.address();
758
+ return r && typeof r == "object" ? `${r.address.includes(":") ? `[${r.address}]` : r.address}:${r.port}` : e.socket.localPort ? `127.0.0.1:${e.socket.localPort}` : "localhost";
759
+ }
760
+ getClientAddress(e) {
761
+ let t = e.socket.remoteAddress ?? "127.0.0.1";
762
+ if (!this.isTrustedProxy(t)) return this.normalizeAddress(t);
763
+ let n = e.headers["x-forwarded-for"];
764
+ if (!n) return this.normalizeAddress(t);
765
+ let r = this.parseForwardedHeader(n);
766
+ r.push(t);
767
+ for (let e = r.length - 1; e >= 0; --e) {
768
+ let t = r[e];
769
+ if (!this.isTrustedProxy(t)) return this.normalizeAddress(t);
770
+ }
771
+ return this.normalizeAddress(r[0] ?? t);
772
+ }
773
+ normalizeTrustedHost(e) {
774
+ if (!e) return null;
775
+ let t;
776
+ try {
777
+ t = new URL(`http://${e}`);
778
+ } catch {
779
+ return null;
780
+ }
781
+ if (t.username || t.password || t.pathname !== "/" || t.search || t.hash) return null;
782
+ let n = t.port ? `${t.hostname}:${t.port}` : t.hostname, r = this.config.security?.allowedHosts;
783
+ return !r || this.matchesValue(n, r) ? n : null;
784
+ }
785
+ matchesValue(e, t) {
786
+ return (Array.isArray(t) ? t : [t]).some((t) => typeof t == "string" ? t === e : t instanceof RegExp ? t.test(e) : t(e));
787
+ }
788
+ configureServerTimeouts(e) {
789
+ let t = this.config.security, n = this.isDevelopment();
790
+ e.headersTimeout = t?.headersTimeoutMs ?? 3e4, e.requestTimeout = t?.requestTimeoutMs ?? (n ? 0 : 6e4), e.keepAliveTimeout = t?.keepAliveTimeoutMs ?? 5e3;
791
+ }
792
+ isDevelopment() {
793
+ return process.env.NODE_ENV !== "production";
794
+ }
795
+ getTrustedForwardedHeader(e, t) {
796
+ if (!this.isTrustedProxy(e.socket.remoteAddress ?? "")) return;
797
+ let n = e.headers[t];
798
+ return Array.isArray(n) ? n[0] : n;
799
+ }
800
+ isTrustedProxy(e) {
801
+ let t = this.config.security?.trustedProxies;
802
+ if (!t) return !1;
803
+ let n = this.normalizeAddress(e);
804
+ return n !== e && this.matchesValue(n, t) ? !0 : this.matchesValue(e, t);
805
+ }
806
+ normalizeAddress(e) {
807
+ return e.startsWith("::ffff:") ? e.slice(7) : e;
808
+ }
809
+ parseForwardedHeader(e) {
810
+ return (Array.isArray(e) ? e.join(",") : e).split(",").map((e) => this.normalizeAddress(e.trim())).filter(Boolean);
811
+ }
812
+ toHeaders(e) {
813
+ let t = new Headers();
814
+ for (let [n, r] of Object.entries(e)) if (r !== void 0) {
815
+ if (Array.isArray(r)) {
816
+ let e = n.toLowerCase() === "cookie" ? r.join("; ") : r.join(", ");
817
+ t.set(n, e);
818
+ continue;
819
+ }
820
+ t.set(n, r);
821
+ }
822
+ return t;
823
+ }
824
+ isRequestBodyAllowed(e) {
825
+ let t = this.config.security?.maxRequestBodySize;
826
+ if (!t) return !0;
827
+ let n = e.headers["content-length"];
828
+ if (!n) return !0;
829
+ let r = Number.parseInt(Array.isArray(n) ? n[0] : n, 10);
830
+ return Number.isFinite(r) && r <= t;
831
+ }
832
+ handleError(e) {
833
+ if (e instanceof G) return new Response(e.message, { status: e.status });
834
+ if (C(e)) return new Response(JSON.stringify({
835
+ error: e.statusText || "Error",
836
+ status: e.status
837
+ }), {
838
+ status: e.status,
839
+ headers: { "Content-Type": "application/json" }
840
+ });
841
+ if (w(e)) {
842
+ let t = e.headers.get("Location") || "/";
843
+ return new Response(null, {
844
+ status: e.status,
845
+ headers: { Location: t }
846
+ });
847
+ }
848
+ return console.error("Unhandled error:", e), new Response("Internal Server Error", { status: 500 });
849
+ }
850
+ async sendWebResponse(e, t) {
851
+ if (e.statusCode = t.status, t.headers.forEach((t, n) => {
852
+ e.setHeader(n, t);
853
+ }), e.hasHeader("Server") || e.setHeader("Server", "WebHTTPServer"), !t.body || this.shouldOmitResponseBody(t, e.req?.method)) {
854
+ e.end();
855
+ return;
856
+ }
857
+ let n = t.body.getReader(), r = o.toWeb(e).getWriter(), i = !1, a = async () => {
858
+ i || (i = !0, await n.cancel().catch(() => {}));
859
+ }, s = () => {
860
+ a();
861
+ };
862
+ e.once("close", s);
863
+ try {
864
+ for (;;) {
865
+ let { done: e, value: t } = await n.read();
866
+ if (e) break;
867
+ await r.write(t);
868
+ }
869
+ i = !0;
870
+ } catch (e) {
871
+ if (await a(), !this.isPrematureCloseError(e)) throw e;
872
+ } finally {
873
+ e.off("close", s), await r.close().catch(() => {});
874
+ }
875
+ }
876
+ isPrematureCloseError(e) {
877
+ if (!(e instanceof Error)) return !1;
878
+ let t = "code" in e ? e.code : void 0;
879
+ return t === "ABORT_ERR" || t === "ERR_STREAM_PREMATURE_CLOSE" ? !0 : e.name === "AbortError";
880
+ }
881
+ shouldOmitResponseBody(e, t) {
882
+ return t === "HEAD" ? !0 : e.status === 204 || e.status === 205 || e.status === 304;
883
+ }
884
+ isAllowedWebSocketOrigin(e) {
885
+ let t = e.headers.origin;
886
+ if (!t) return !0;
887
+ let n = this.config.security?.allowedWebSocketOrigins;
888
+ return n ? this.matchesValue(t, n) : !0;
889
+ }
890
+ createEventFetch(e, t) {
891
+ return async (n, r) => {
892
+ let i = this.toEventFetchRequest(e, n, r);
893
+ if (i.url.startsWith(`${e.url.origin}/`)) {
894
+ let e = this.toRequestEvent(i, new URL(i.url), t);
895
+ try {
896
+ return await this.handle(e);
897
+ } catch (e) {
898
+ return this.handleError(e);
899
+ }
900
+ }
901
+ return fetch(i);
902
+ };
903
+ }
904
+ toEventFetchRequest(e, t, n) {
905
+ let r = t instanceof URL ? t.toString() : t, i = r instanceof Request ? r : new Request(new URL(String(r), e.url), n);
906
+ if (r instanceof Request && !n) return this.withInheritedRequestHeaders(e, r);
907
+ let a = new Headers(r instanceof Request ? r.headers : n?.headers), o = n?.method ?? (r instanceof Request ? r.method : void 0), s = n?.body ?? (r instanceof Request ? r.body : void 0), c = s ? "half" : void 0;
908
+ return this.inheritRequestHeader(e.request.headers, a, "cookie"), this.inheritRequestHeader(e.request.headers, a, "authorization"), new Request(i.url, {
909
+ ...n,
910
+ method: o,
911
+ headers: a,
912
+ body: s,
913
+ signal: n?.signal ?? e.request.signal,
914
+ duplex: c
915
+ });
916
+ }
917
+ withInheritedRequestHeaders(e, t) {
918
+ let n = new Headers(t.headers);
919
+ return this.inheritRequestHeader(e.request.headers, n, "cookie"), this.inheritRequestHeader(e.request.headers, n, "authorization"), new Request(t, {
920
+ headers: n,
921
+ signal: e.request.signal,
922
+ duplex: t.body ? "half" : void 0
923
+ });
924
+ }
925
+ inheritRequestHeader(e, t, n) {
926
+ if (t.has(n)) return;
927
+ let r = e.get(n);
928
+ r && t.set(n, r);
929
+ }
930
+ toRequestEvent(e, t, n) {
931
+ let r = new re(e, n.pushSetCookie), i = this.config, a = {}, o = {
932
+ name: "node-webserver",
933
+ dev: this.isDevelopment()
934
+ }, s = /* @__PURE__ */ new Set(), c = {
935
+ request: e,
936
+ url: t,
937
+ cookies: r,
938
+ getClientAddress: n.getClientAddress,
939
+ get locals() {
940
+ return a;
941
+ },
942
+ get platform() {
943
+ return o;
944
+ },
945
+ fetch: async (e, t) => l(e, t),
946
+ params: {},
947
+ route: { id: null },
948
+ setHeaders: (e) => {
949
+ for (let [t, r] of Object.entries(e)) {
950
+ let e = t.toLowerCase();
951
+ if (e === "set-cookie") throw TypeError("Use event.cookies for Set-Cookie headers");
952
+ if (s.has(e)) throw TypeError(`Header "${t}" has already been set`);
953
+ s.add(e), n.setHeader(t, r);
954
+ }
955
+ }
956
+ }, l = this.createEventFetch(c, n);
957
+ return i.locals && Object.assign(a, i.locals(c)), i.platform && Object.assign(o, i.platform(c)), c;
958
+ }
959
+ }, q = {
960
+ ".avif": "image/avif",
961
+ ".css": "text/css; charset=utf-8",
962
+ ".gif": "image/gif",
963
+ ".html": "text/html; charset=utf-8",
964
+ ".ico": "image/x-icon",
965
+ ".jpg": "image/jpeg",
966
+ ".jpeg": "image/jpeg",
967
+ ".js": "text/javascript; charset=utf-8",
968
+ ".json": "application/json; charset=utf-8",
969
+ ".mjs": "text/javascript; charset=utf-8",
970
+ ".pdf": "application/pdf",
971
+ ".png": "image/png",
972
+ ".svg": "image/svg+xml; charset=utf-8",
973
+ ".txt": "text/plain; charset=utf-8",
974
+ ".wasm": "application/wasm",
975
+ ".webp": "image/webp",
976
+ ".xml": "application/xml; charset=utf-8"
977
+ }, J = {
978
+ index: "index.html",
979
+ cacheControl: "public, max-age=0",
980
+ dotFiles: "ignore"
848
981
  };
849
- async function le(a, e, t = {}) {
850
- const s = me(e), r = {
851
- ...ue,
852
- ...t
853
- }, n = await de(a), o = he(s, r.dotFiles);
854
- if (o instanceof Response)
855
- return o;
856
- const i = o.length > 0 ? o.join(G) : "", u = O(n, i);
857
- if (!k(n, u))
858
- return new Response("Forbidden", { status: 403 });
859
- const c = await fe(u, n, r.index);
860
- if (c instanceof Response)
861
- return c;
862
- const l = await W(c), d = new Headers({
863
- "content-length": String(l.size),
864
- "content-type": pe(c),
865
- "cache-control": r.cacheControl,
866
- "last-modified": l.mtime.toUTCString(),
867
- "x-content-type-options": "nosniff"
868
- });
869
- if (t.headers) {
870
- const h = typeof t.headers == "function" ? t.headers(c, l) : t.headers;
871
- new Headers(h).forEach((p, m) => {
872
- d.set(m, p);
873
- });
874
- }
875
- return new Response(Q.toWeb(X(c)), {
876
- status: 200,
877
- headers: d
878
- });
982
+ async function Y(e, t, n = {}) {
983
+ let r = $(t), i = {
984
+ ...J,
985
+ ...n
986
+ }, a = await X(e), o = ie(r, i.dotFiles);
987
+ if (o instanceof Response) return o;
988
+ let s = v(a, o.length > 0 ? o.join(y) : "");
989
+ if (!Q(a, s)) return new Response("Forbidden", { status: 403 });
990
+ let c = await ae(s, a, i.index);
991
+ if (c instanceof Response) return c;
992
+ let l = await m(c), u = new Headers({
993
+ "content-length": String(l.size),
994
+ "content-type": oe(c),
995
+ "cache-control": i.cacheControl,
996
+ "last-modified": l.mtime.toUTCString(),
997
+ "x-content-type-options": "nosniff"
998
+ });
999
+ if (n.headers) {
1000
+ let e = typeof n.headers == "function" ? n.headers(c, l) : n.headers;
1001
+ new Headers(e).forEach((e, t) => {
1002
+ u.set(t, e);
1003
+ });
1004
+ }
1005
+ return new Response(b.toWeb(d(c)), {
1006
+ status: 200,
1007
+ headers: u
1008
+ });
879
1009
  }
880
- async function de(a) {
881
- return v(a);
1010
+ async function X(e) {
1011
+ return p(e);
882
1012
  }
883
- function he(a, e) {
884
- if (a.includes("\0"))
885
- return new Response("Bad Request", { status: 400 });
886
- const t = a.replace(/\\/g, "/").split("/").filter(Boolean), s = [];
887
- for (const r of t) {
888
- let n;
889
- try {
890
- n = decodeURIComponent(r);
891
- } catch {
892
- return new Response("Bad Request", { status: 400 });
893
- }
894
- if (!(!n || n === ".")) {
895
- if (n === ".." || n.includes("/") || n.includes("\\") || n.includes("\0"))
896
- return new Response("Forbidden", { status: 403 });
897
- if (n.startsWith(".")) {
898
- if (e === "deny")
899
- return new Response("Forbidden", { status: 403 });
900
- if (e !== "allow")
901
- return new Response("Not Found", { status: 404 });
902
- }
903
- s.push(n);
904
- }
905
- }
906
- return s;
1013
+ function ie(e, t) {
1014
+ if (e.includes("\0")) return new Response("Bad Request", { status: 400 });
1015
+ let n = e.replace(/\\/g, "/").split("/").filter(Boolean), r = [];
1016
+ for (let e of n) {
1017
+ let n;
1018
+ try {
1019
+ n = decodeURIComponent(e);
1020
+ } catch {
1021
+ return new Response("Bad Request", { status: 400 });
1022
+ }
1023
+ if (!(!n || n === ".")) {
1024
+ if (n === ".." || n.includes("/") || n.includes("\\") || n.includes("\0")) return new Response("Forbidden", { status: 403 });
1025
+ if (n.startsWith(".")) {
1026
+ if (t === "deny") return new Response("Forbidden", { status: 403 });
1027
+ if (t !== "allow") return new Response("Not Found", { status: 404 });
1028
+ }
1029
+ r.push(n);
1030
+ }
1031
+ }
1032
+ return r;
907
1033
  }
908
- async function fe(a, e, t) {
909
- try {
910
- if ((await J(a)).isDirectory()) {
911
- const r = O(a, t);
912
- return L(r, e);
913
- }
914
- return L(a, e);
915
- } catch {
916
- return new Response("Not Found", { status: 404 });
917
- }
1034
+ async function ae(e, t, n) {
1035
+ try {
1036
+ return (await f(e)).isDirectory() ? Z(v(e, n), t) : Z(e, t);
1037
+ } catch {
1038
+ return new Response("Not Found", { status: 404 });
1039
+ }
918
1040
  }
919
- async function L(a, e) {
920
- try {
921
- const t = await v(a);
922
- return k(e, t) ? (await W(t)).isFile() ? t : new Response("Not Found", { status: 404 }) : new Response("Forbidden", { status: 403 });
923
- } catch {
924
- return new Response("Not Found", { status: 404 });
925
- }
1041
+ async function Z(e, t) {
1042
+ try {
1043
+ let n = await p(e);
1044
+ return Q(t, n) ? (await m(n)).isFile() ? n : new Response("Not Found", { status: 404 }) : new Response("Forbidden", { status: 403 });
1045
+ } catch {
1046
+ return new Response("Not Found", { status: 404 });
1047
+ }
926
1048
  }
927
- function k(a, e) {
928
- const t = V(a, e);
929
- return t === "" || !t.startsWith("..") && !K(t);
1049
+ function Q(e, t) {
1050
+ let n = _(e, t);
1051
+ return n === "" || !n.startsWith("..") && !g(n);
930
1052
  }
931
- function pe(a) {
932
- return ce[Y(a).toLowerCase()] ?? "application/octet-stream";
1053
+ function oe(e) {
1054
+ return q[h(e).toLowerCase()] ?? "application/octet-stream";
933
1055
  }
934
- function me(a) {
935
- return typeof a.params.path == "string" ? a.params.path : a.url.pathname.replace(/^\/+/, "");
1056
+ function $(e) {
1057
+ return typeof e.params.path == "string" ? e.params.path : e.url.pathname.replace(/^\/+/, "");
936
1058
  }
937
- const We = (a, e = {}) => (t) => le(a, t, e), ve = (a, ...e) => async (t) => {
938
- const s = {};
939
- for (const r of e) {
940
- const n = await r(t);
941
- if (S(n))
942
- return n;
943
- n && typeof n == "object" && Object.assign(s, n);
944
- }
945
- return a(Object.assign(t, { context: s }));
1059
+ var se = (e, t = {}) => (n) => Y(e, n, t), ce = (e, ...t) => async (n) => {
1060
+ let r = {};
1061
+ for (let e of t) {
1062
+ let t = await e(n);
1063
+ if (T(t)) return t;
1064
+ t && typeof t == "object" && Object.assign(r, t);
1065
+ }
1066
+ return e(Object.assign(n, { context: r }));
946
1067
  };
947
- function we(a, e = {}) {
948
- const t = [];
949
- if (e.comment)
950
- for (const s of e.comment.split(/\r?\n/))
951
- t.push(`: ${s}`);
952
- if (e.event && t.push(`event: ${e.event}`), e.id && t.push(`id: ${e.id}`), e.retry !== void 0 && t.push(`retry: ${e.retry}`), a !== void 0) {
953
- const s = typeof a == "string" ? a : JSON.stringify(a);
954
- for (const r of s.split(/\r?\n/))
955
- t.push(`data: ${r}`);
956
- }
957
- return `${t.join(`
958
- `)}
959
-
960
- `;
1068
+ //#endregion
1069
+ //#region src/helpers/sse.ts
1070
+ function le(e, t = {}) {
1071
+ let n = [];
1072
+ if (t.comment) for (let e of t.comment.split(/\r?\n/)) n.push(`: ${e}`);
1073
+ if (t.event && n.push(`event: ${t.event}`), t.id && n.push(`id: ${t.id}`), t.retry !== void 0 && n.push(`retry: ${t.retry}`), e !== void 0) {
1074
+ let t = typeof e == "string" ? e : JSON.stringify(e);
1075
+ for (let e of t.split(/\r?\n/)) n.push(`data: ${e}`);
1076
+ }
1077
+ return `${n.join("\n")}\n\n`;
961
1078
  }
962
- const Oe = (a, e = {}) => (t) => {
963
- const s = new TextEncoder();
964
- let r = null, n = !1, o;
965
- const i = async () => {
966
- if (!n) {
967
- n = !0;
968
- try {
969
- await o?.();
970
- } finally {
971
- r?.close();
972
- }
973
- }
974
- }, u = new ReadableStream({
975
- async start(c) {
976
- r = c;
977
- const l = (d, h = {}) => {
978
- n || c.enqueue(s.encode(we(d, h)));
979
- };
980
- t.request.signal.addEventListener("abort", () => {
981
- i();
982
- }, { once: !0 });
983
- try {
984
- if (o = await a(t, l), !t.request.signal.aborted && o === void 0)
985
- return;
986
- t.request.signal.aborted && await i();
987
- } catch (d) {
988
- n || c.error(d);
989
- }
990
- },
991
- async cancel() {
992
- await i();
993
- }
994
- });
995
- return new Response(u, {
996
- ...e,
997
- headers: {
998
- "content-type": "text/event-stream",
999
- "cache-control": "no-cache",
1000
- connection: "keep-alive",
1001
- ...e.headers
1002
- }
1003
- });
1004
- }, _e = async (a, e) => {
1005
- const t = JSON.stringify(await a);
1006
- return new Response(t, {
1007
- ...e,
1008
- headers: {
1009
- "content-type": "application/json",
1010
- "content-length": Buffer.byteLength(t).toString(),
1011
- ...e?.headers
1012
- }
1013
- });
1079
+ var ue = (e, t = {}) => (n) => {
1080
+ let r = new TextEncoder(), i = null, a = !1, o, s = async () => {
1081
+ if (!a) {
1082
+ a = !0;
1083
+ try {
1084
+ await o?.();
1085
+ } finally {
1086
+ try {
1087
+ i?.close();
1088
+ } catch {}
1089
+ }
1090
+ }
1091
+ }, c = new ReadableStream({
1092
+ async start(t) {
1093
+ i = t;
1094
+ let c = (e, n = {}) => {
1095
+ a || t.enqueue(r.encode(le(e, n)));
1096
+ };
1097
+ n.request.signal.addEventListener("abort", () => {
1098
+ s();
1099
+ }, { once: !0 });
1100
+ try {
1101
+ if (o = await e(n, c), n.request.signal.aborted) {
1102
+ await s();
1103
+ return;
1104
+ }
1105
+ o === void 0 && await s();
1106
+ } catch (e) {
1107
+ a || t.error(e);
1108
+ }
1109
+ },
1110
+ async cancel() {
1111
+ await s();
1112
+ }
1113
+ });
1114
+ return new Response(c, {
1115
+ ...t,
1116
+ headers: {
1117
+ "content-type": "text/event-stream",
1118
+ "cache-control": "no-cache",
1119
+ connection: "keep-alive",
1120
+ ...t.headers
1121
+ }
1122
+ });
1123
+ }, de = async (e, t) => {
1124
+ let n = JSON.stringify(await e);
1125
+ return new Response(n, {
1126
+ ...t,
1127
+ headers: {
1128
+ "content-type": "application/json",
1129
+ "content-length": Buffer.byteLength(n).toString(),
1130
+ ...t?.headers
1131
+ }
1132
+ });
1014
1133
  };
1015
- function Ne(a, e) {
1016
- throw new Response(null, {
1017
- status: a,
1018
- headers: {
1019
- location: e.toString()
1020
- }
1021
- });
1134
+ function fe(e, t) {
1135
+ throw new Response(null, {
1136
+ status: e,
1137
+ headers: { location: t.toString() }
1138
+ });
1022
1139
  }
1023
- function je(a, e) {
1024
- throw new Response(JSON.stringify(typeof e == "string" ? { message: e } : e), {
1025
- status: a,
1026
- headers: {
1027
- "content-type": "application/json"
1028
- }
1029
- });
1140
+ function pe(e, t) {
1141
+ throw new Response(JSON.stringify(typeof t == "string" ? { message: t } : t), {
1142
+ status: e,
1143
+ headers: { "content-type": "application/json" }
1144
+ });
1030
1145
  }
1031
- const ke = async (a, e) => {
1032
- const t = await a;
1033
- return new Response(t, {
1034
- ...e,
1035
- headers: {
1036
- "content-type": "text/plain",
1037
- "content-length": Buffer.byteLength(t).toString(),
1038
- ...e?.headers
1039
- }
1040
- });
1041
- }, qe = async (a, e) => {
1042
- const t = await a;
1043
- return new Response(t, {
1044
- ...e,
1045
- headers: {
1046
- "content-type": "text/html",
1047
- "content-length": Buffer.byteLength(t).toString(),
1048
- ...e?.headers
1049
- }
1050
- });
1146
+ var me = async (e, t) => {
1147
+ let n = await e;
1148
+ return new Response(n, {
1149
+ ...t,
1150
+ headers: {
1151
+ "content-type": "text/plain",
1152
+ "content-length": Buffer.byteLength(n).toString(),
1153
+ ...t?.headers
1154
+ }
1155
+ });
1156
+ }, he = async (e, t) => {
1157
+ let n = await e;
1158
+ return new Response(n, {
1159
+ ...t,
1160
+ headers: {
1161
+ "content-type": "text/html",
1162
+ "content-length": Buffer.byteLength(n).toString(),
1163
+ ...t?.headers
1164
+ }
1165
+ });
1051
1166
  };
1052
- export {
1053
- R as Action,
1054
- Ce as CORS,
1055
- Te as RateLimiter,
1056
- ae as RequestMethods,
1057
- E as Router,
1058
- Le as WebServer,
1059
- We as dir,
1060
- ve as enhance,
1061
- je as error,
1062
- qe as html,
1063
- _ as isHttpError,
1064
- N as isRedirect,
1065
- S as isResponse,
1066
- _e as json,
1067
- Ne as redirect,
1068
- le as serveStatic,
1069
- Oe as sse,
1070
- ke as text
1071
- };
1072
- //# sourceMappingURL=index.es.js.map
1167
+ //#endregion
1168
+ export { W as Action, ee as CORS, D as RateLimiter, L as RequestId, V as RequestMethods, U as Router, N as Security, z as Timeout, K as WebServer, se as dir, ce as enhance, pe as error, he as html, C as isHttpError, w as isRedirect, T as isResponse, de as json, fe as redirect, Y as serveStatic, ue as sse, me as text };
1169
+
1170
+ //# sourceMappingURL=index.es.js.map