@kevisual/router 0.0.43 → 0.0.45

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/router.d.ts CHANGED
@@ -1,10 +1,12 @@
1
- import http$1, { IncomingMessage, ServerResponse } from 'node:http';
1
+ import * as http from 'node:http';
2
+ import http__default, { IncomingMessage, ServerResponse } from 'node:http';
2
3
  import https from 'node:https';
3
4
  import http2 from 'node:http2';
4
- import * as http from 'http';
5
- import { IncomingMessage as IncomingMessage$1, ServerResponse as ServerResponse$1 } from 'http';
5
+ import EventEmitter from 'node:events';
6
+ import { EventEmitter as EventEmitter$1 } from 'events';
6
7
  import { WebSocketServer, WebSocket } from 'ws';
7
8
  import { z } from 'zod';
9
+ import { IncomingMessage as IncomingMessage$1, ServerResponse as ServerResponse$1 } from 'http';
8
10
  import { RouteOpts as RouteOpts$1, QueryRouterServer as QueryRouterServer$1, RouteMiddleware as RouteMiddleware$1, Run as Run$1 } from '@kevisual/router';
9
11
  import { Query, DataOpts, Result } from '@kevisual/query/query';
10
12
 
@@ -383,14 +385,6 @@ declare class QueryConnect {
383
385
  }[];
384
386
  }
385
387
 
386
- type Listener$1 = {
387
- id?: string;
388
- io?: boolean;
389
- path?: string;
390
- fun: (...args: any[]) => Promise<void> | void;
391
- };
392
- type ListenerFun = (...args: any[]) => Promise<void> | void;
393
- type OnListener = Listener$1 | ListenerFun | (Listener$1 | ListenerFun)[];
394
388
  type Cors$2 = {
395
389
  /**
396
390
  * @default '*''
@@ -432,18 +426,41 @@ interface ServerType {
432
426
  * @param listener
433
427
  */
434
428
  on(listener: OnListener): void;
435
- onWebSocket({ ws, message, pathname, token, id }: {
436
- ws: WS;
437
- message: string | Buffer;
438
- pathname: string;
439
- token?: string;
440
- id?: string;
441
- }): void;
429
+ onWebSocket({ ws, message, pathname, token, id }: OnWebSocketOptions): void;
442
430
  }
431
+ type OnWebSocketOptions = {
432
+ ws: WS;
433
+ message: string | Buffer;
434
+ pathname: string;
435
+ token?: string;
436
+ id?: string;
437
+ };
438
+ type OnWebSocketFn = (options: OnWebSocketOptions) => Promise<void> | void;
443
439
  type WS = {
444
440
  send: (data: any) => void;
445
- close: () => void;
441
+ close: (code?: number, reason?: string) => void;
446
442
  };
443
+ type Listener$1 = {
444
+ id?: string;
445
+ io?: boolean;
446
+ path?: string;
447
+ fun: WebScoketListenerFun | HttpListenerFun;
448
+ };
449
+ type WebScoketListenerFun = (req: WebSocketReq, res: WebSocketRes) => Promise<void> | void;
450
+ type HttpListenerFun = (req: RouterReq, res: RouterRes) => Promise<void> | void;
451
+ type WebSocketReq = {
452
+ emitter?: EventEmitter;
453
+ ws: WS;
454
+ data: any;
455
+ pathname?: string;
456
+ token?: string;
457
+ id?: string;
458
+ };
459
+ type WebSocketRes = {
460
+ end: (data: any) => void;
461
+ };
462
+ type ListenerFun = WebScoketListenerFun | HttpListenerFun;
463
+ type OnListener = Listener$1 | ListenerFun | (Listener$1 | ListenerFun)[];
447
464
  type RouterReq<T = {}> = {
448
465
  url: string;
449
466
  method: string;
@@ -588,6 +605,7 @@ declare class ServerBase implements ServerType {
588
605
  _callback: any;
589
606
  cors: Cors$1;
590
607
  listeners: Listener$1[];
608
+ emitter: EventEmitter$1<any>;
591
609
  constructor(opts?: ServerOpts);
592
610
  listen(port: number, hostname?: string, backlog?: number, listeningListener?: () => void): void;
593
611
  listen(port: number, hostname?: string, listeningListener?: () => void): void;
@@ -613,13 +631,7 @@ declare class ServerBase implements ServerType {
613
631
  */
614
632
  createCallback(): (req: IncomingMessage, res: ServerResponse) => Promise<void>;
615
633
  on(listener: OnListener): void;
616
- onWebSocket({ ws, message, pathname, token, id }: {
617
- ws: any;
618
- message: any;
619
- pathname: any;
620
- token: any;
621
- id: any;
622
- }): Promise<void>;
634
+ onWebSocket({ ws, message, pathname, token, id }: OnWebSocketOptions): Promise<void>;
623
635
  }
624
636
 
625
637
  type WsServerBaseOpts = {
@@ -661,7 +673,7 @@ type ServerNodeOpts = ServerOpts<{
661
673
  httpsCert?: string;
662
674
  }>;
663
675
  declare class ServerNode extends ServerBase implements ServerType {
664
- _server: http$1.Server | https.Server | http2.Http2SecureServer;
676
+ _server: http__default.Server | https.Server | http2.Http2SecureServer;
665
677
  _callback: any;
666
678
  cors: Cors;
667
679
  private httpType;
@@ -670,7 +682,7 @@ declare class ServerNode extends ServerBase implements ServerType {
670
682
  io: WsServer | undefined;
671
683
  constructor(opts?: ServerNodeOpts);
672
684
  customListen(...args: any[]): void;
673
- createServer(): http$1.Server<typeof http$1.IncomingMessage, typeof http$1.ServerResponse> | http2.Http2SecureServer<typeof http$1.IncomingMessage, typeof http$1.ServerResponse, typeof http2.Http2ServerRequest, typeof http2.Http2ServerResponse>;
685
+ createServer(): http__default.Server<typeof http__default.IncomingMessage, typeof http__default.ServerResponse> | http2.Http2SecureServer<typeof http__default.IncomingMessage, typeof http__default.ServerResponse, typeof http2.Http2ServerRequest, typeof http2.Http2ServerResponse>;
674
686
  }
675
687
 
676
688
  /**
@@ -912,4 +924,4 @@ declare class App<U = {}> {
912
924
  }
913
925
 
914
926
  export { App, Connect, CustomError, Mini, QueryConnect, QueryRouter, QueryRouterServer, QueryUtil, Route, ServerNode, createSchema, define, handleServer, util };
915
- export type { RouteArray, RouteContext, RouteMiddleware, RouteObject, RouteOpts, RouterReq, RouterRes, Rule, Run, Schema };
927
+ export type { OnWebSocketFn, RouteArray, RouteContext, RouteMiddleware, RouteObject, RouteOpts, RouterReq, RouterRes, Rule, Run, Schema };
package/dist/router.js CHANGED
@@ -3,7 +3,7 @@ import require$$2 from 'node:http';
3
3
  import require$$1$1 from 'node:https';
4
4
  import http2 from 'node:http2';
5
5
  import url from 'node:url';
6
- import require$$0$3 from 'node:events';
6
+ import require$$0$3, { EventEmitter } from 'node:events';
7
7
  import require$$3 from 'node:net';
8
8
  import require$$4 from 'node:tls';
9
9
  import require$$0$2 from 'node:stream';
@@ -1214,6 +1214,7 @@ class ServerBase {
1214
1214
  _callback;
1215
1215
  cors;
1216
1216
  listeners = [];
1217
+ emitter = new EventEmitter();
1217
1218
  constructor(opts) {
1218
1219
  this.path = opts?.path || '/api/router';
1219
1220
  this.handle = opts?.handle;
@@ -1348,6 +1349,7 @@ class ServerBase {
1348
1349
  ws.send(JSON.stringify(data));
1349
1350
  };
1350
1351
  listener.fun({
1352
+ emitter: this.emitter,
1351
1353
  data,
1352
1354
  token,
1353
1355
  id,
@@ -6662,7 +6664,7 @@ class BunServer extends ServerBase {
6662
6664
  },
6663
6665
  websocket: {
6664
6666
  open: (ws) => {
6665
- ws.send('connected');
6667
+ ws.send(JSON.stringify({ type: 'connected' }));
6666
6668
  },
6667
6669
  message: async (ws, message) => {
6668
6670
  const pathname = ws.data.pathname || '';
@@ -6672,6 +6674,15 @@ class BunServer extends ServerBase {
6672
6674
  },
6673
6675
  close: (ws) => {
6674
6676
  // WebSocket 连接关闭
6677
+ const id = ws?.data?.id || '';
6678
+ if (id) {
6679
+ this.emitter.emit('close--' + id, { type: 'close', ws, id });
6680
+ setTimeout(() => {
6681
+ // 关闭后 5 秒清理监听器, 避免内存泄漏, 理论上原本的自己就应该被清理掉了,这里是保险起见
6682
+ this.emitter.removeAllListeners('close--' + id);
6683
+ this.emitter.removeAllListeners(id);
6684
+ }, 5000);
6685
+ }
6675
6686
  },
6676
6687
  },
6677
6688
  });
@@ -11158,7 +11169,7 @@ class App {
11158
11169
  }
11159
11170
  this.server.on({
11160
11171
  id: 'app-request-listener',
11161
- fun: fn
11172
+ fun: fn,
11162
11173
  });
11163
11174
  }
11164
11175
  }
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "$schema": "https://json.schemastore.org/package",
3
3
  "name": "@kevisual/router",
4
- "version": "0.0.43",
4
+ "version": "0.0.45",
5
5
  "description": "",
6
6
  "type": "module",
7
7
  "main": "./dist/router.js",
package/src/app.ts CHANGED
@@ -134,7 +134,7 @@ export class App<U = {}> {
134
134
  }
135
135
  this.server.on({
136
136
  id: 'app-request-listener',
137
- fun: fn
137
+ fun: fn as any,
138
138
  });
139
139
  }
140
140
  }
package/src/index.ts CHANGED
@@ -20,4 +20,4 @@ export { App } from './app.ts';
20
20
  export * from './router-define.ts';
21
21
 
22
22
 
23
- export { RouterReq, RouterRes } from './server/server-type.ts';
23
+ export { RouterReq, RouterRes, OnWebSocketFn } from './server/server-type.ts';
@@ -1,9 +1,9 @@
1
1
  import type { IncomingMessage, ServerResponse } from 'node:http';
2
2
  import { handleServer } from './handle-server.ts';
3
3
  import * as cookie from './cookie.ts';
4
- import { ServerType, Listener, OnListener, ServerOpts } from './server-type.ts';
4
+ import { ServerType, Listener, OnListener, ServerOpts, OnWebSocketOptions, OnWebSocketFn, WebScoketListenerFun, ListenerFun, HttpListenerFun } from './server-type.ts';
5
5
  import { parseIfJson } from '../utils/parse.ts';
6
-
6
+ import { EventEmitter } from 'events';
7
7
  type CookieFn = (name: string, value: string, options?: cookie.SerializeOptions, end?: boolean) => void;
8
8
 
9
9
  export type HandleCtx = {
@@ -63,6 +63,7 @@ export class ServerBase implements ServerType {
63
63
  _callback: any;
64
64
  cors: Cors;
65
65
  listeners: Listener[] = [];
66
+ emitter = new EventEmitter();
66
67
  constructor(opts?: ServerOpts) {
67
68
  this.path = opts?.path || '/api/router';
68
69
  this.handle = opts?.handle;
@@ -118,7 +119,7 @@ export class ServerBase implements ServerType {
118
119
  }
119
120
  const listeners = that.listeners || [];
120
121
  for (const item of listeners) {
121
- const fun = item.fun;
122
+ const fun = item.fun as any;
122
123
  if (typeof fun === 'function' && !item.io) {
123
124
  await fun(req, res);
124
125
  }
@@ -193,7 +194,7 @@ export class ServerBase implements ServerType {
193
194
  this.listeners.push(listener);
194
195
  }
195
196
  }
196
- async onWebSocket({ ws, message, pathname, token, id }) {
197
+ async onWebSocket({ ws, message, pathname, token, id }: OnWebSocketOptions) {
197
198
  const listener = this.listeners.find((item) => item.path === pathname && item.io);
198
199
  const data: any = parseIfJson(message);
199
200
 
@@ -201,7 +202,8 @@ export class ServerBase implements ServerType {
201
202
  const end = (data: any) => {
202
203
  ws.send(JSON.stringify(data));
203
204
  }
204
- listener.fun({
205
+ (listener.fun as WebScoketListenerFun)({
206
+ emitter: this.emitter,
205
207
  data,
206
208
  token,
207
209
  id,
@@ -223,7 +223,7 @@ export class BunServer extends ServerBase implements ServerType {
223
223
  },
224
224
  websocket: {
225
225
  open: (ws: any) => {
226
- ws.send('connected');
226
+ ws.send(JSON.stringify({ type: 'connected' }));
227
227
  },
228
228
  message: async (ws: any, message: string | Buffer) => {
229
229
  const pathname = ws.data.pathname || '';
@@ -233,6 +233,15 @@ export class BunServer extends ServerBase implements ServerType {
233
233
  },
234
234
  close: (ws: any) => {
235
235
  // WebSocket 连接关闭
236
+ const id = ws?.data?.id || '';
237
+ if (id) {
238
+ this.emitter.emit('close--' + id, { type: 'close', ws, id });
239
+ setTimeout(() => {
240
+ // 关闭后 5 秒清理监听器, 避免内存泄漏, 理论上原本的自己就应该被清理掉了,这里是保险起见
241
+ this.emitter.removeAllListeners('close--' + id);
242
+ this.emitter.removeAllListeners(id);
243
+ }, 5000);
244
+ }
236
245
  },
237
246
  },
238
247
  });
@@ -1,13 +1,7 @@
1
- import * as http from 'http';
1
+ import EventEmitter from 'node:events';
2
+ import * as http from 'node:http';
3
+
2
4
 
3
- export type Listener = {
4
- id?: string;
5
- io?: boolean;
6
- path?: string;
7
- fun: (...args: any[]) => Promise<void> | void;
8
- }
9
- export type ListenerFun = (...args: any[]) => Promise<void> | void;
10
- export type OnListener = Listener | ListenerFun | (Listener | ListenerFun)[];
11
5
  export type Cors = {
12
6
  /**
13
7
  * @default '*''
@@ -44,14 +38,38 @@ export interface ServerType {
44
38
  * @param listener
45
39
  */
46
40
  on(listener: OnListener): void;
47
- onWebSocket({ ws, message, pathname, token, id }: { ws: WS; message: string | Buffer; pathname: string, token?: string, id?: string }): void;
41
+ onWebSocket({ ws, message, pathname, token, id }: OnWebSocketOptions): void;
48
42
  }
49
43
 
44
+ export type OnWebSocketOptions = { ws: WS; message: string | Buffer; pathname: string, token?: string, id?: string }
45
+ export type OnWebSocketFn = (options: OnWebSocketOptions) => Promise<void> | void;
50
46
  type WS = {
51
47
  send: (data: any) => void;
52
- close: () => void;
48
+ close: (code?: number, reason?: string) => void;
53
49
  }
50
+ export type Listener = {
51
+ id?: string;
52
+ io?: boolean;
53
+ path?: string;
54
+ fun: WebScoketListenerFun | HttpListenerFun;
55
+ }
56
+
57
+ export type WebScoketListenerFun = (req: WebSocketReq, res: WebSocketRes) => Promise<void> | void;
58
+ export type HttpListenerFun = (req: RouterReq, res: RouterRes) => Promise<void> | void;
54
59
 
60
+ export type WebSocketReq = {
61
+ emitter?: EventEmitter;
62
+ ws: WS;
63
+ data: any;
64
+ pathname?: string;
65
+ token?: string;
66
+ id?: string;
67
+ }
68
+ export type WebSocketRes = {
69
+ end: (data: any) => void;
70
+ }
71
+ export type ListenerFun = WebScoketListenerFun | HttpListenerFun;;
72
+ export type OnListener = Listener | ListenerFun | (Listener | ListenerFun)[];
55
73
  export type RouterReq<T = {}> = {
56
74
  url: string;
57
75
  method: string;