bxo 0.0.7 → 0.0.8

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.
@@ -9,19 +9,26 @@ async function main() {
9
9
  <!DOCTYPE html>
10
10
  <html>
11
11
  <head>
12
- <title>BXO WebSocket Example</title>
12
+ <title>BXO WebSocket Example with Client ID & Cookies</title>
13
13
  </head>
14
14
  <body>
15
- <h1>BXO WebSocket Example</h1>
15
+ <h1>BXO WebSocket Example with Client ID & Cookies</h1>
16
16
  <div id="messages"></div>
17
17
  <input type="text" id="messageInput" placeholder="Type a message...">
18
18
  <button onclick="sendMessage()">Send</button>
19
19
  <button onclick="connect()">Connect</button>
20
20
  <button onclick="disconnect()">Disconnect</button>
21
+ <button onclick="setCookie()">Set Test Cookie</button>
21
22
 
22
23
  <script>
23
24
  let ws = null;
24
25
 
26
+ function setCookie() {
27
+ document.cookie = "testCookie=hello_from_client; path=/";
28
+ document.cookie = "sessionId=abc123; path=/";
29
+ addMessage('Cookies set! Refresh and reconnect to see them in server logs.');
30
+ }
31
+
25
32
  function connect() {
26
33
  ws = new WebSocket('ws://localhost:3000/ws');
27
34
 
@@ -73,60 +80,86 @@ async function main() {
73
80
  }
74
81
  });
75
82
  </script>
76
- `, 200, {
77
- "Content-Type": "text/html"
78
- });
83
+ `, 200);
79
84
  });
80
85
 
81
- // WebSocket route
86
+ // WebSocket route with enhanced client identification
82
87
  app.ws("/ws", {
83
88
  open(ws) {
84
- console.log("WebSocket connection opened");
85
- ws.send("Welcome to BXO WebSocket!");
89
+ const clientInfo = ws.data;
90
+ console.log("šŸ”Œ WebSocket connection opened:");
91
+ console.log(` šŸ†” Client ID: ${clientInfo.id}`);
92
+ console.log(` šŸ”— Connection ID: ${clientInfo.connectionId}`);
93
+ console.log(` 🌐 Client IP: ${clientInfo.ip}`);
94
+ console.log(` šŸ–„ļø User Agent: ${clientInfo.userAgent}`);
95
+ console.log(` šŸŽÆ Origin: ${clientInfo.origin}`);
96
+ console.log(` šŸ  Host: ${clientInfo.host}`);
97
+ console.log(` šŸ“ Path: ${clientInfo.path}`);
98
+ console.log(` šŸŖ Cookies:`, clientInfo.cookies);
99
+
100
+ ws.send(`Welcome! Your WebSocket ID is: ${clientInfo.id}`);
86
101
  },
87
102
 
88
103
  message(ws, message) {
89
- console.log("Received message:", message);
90
- // Echo the message back
91
- ws.send(`Echo: ${message}`);
104
+ const clientInfo = ws.data;
105
+ console.log(`šŸ’¬ Message from ${clientInfo.id} (${clientInfo.ip}):`, message);
106
+ console.log(` šŸŖ Client cookies:`, clientInfo.cookies);
107
+
108
+ // Echo the message back with client ID
109
+ ws.send(`[${clientInfo.id}] Echo: ${message}`);
92
110
  },
93
111
 
94
112
  close(ws, code, reason) {
95
- console.log(`WebSocket connection closed: ${code} ${reason}`);
113
+ const clientInfo = ws.data;
114
+ console.log(`āŒ WebSocket connection closed for ${clientInfo.id}: ${code} ${reason}`);
96
115
  },
97
116
 
98
117
  ping(ws, data) {
99
- console.log("Ping received:", data);
118
+ const clientInfo = ws.data;
119
+ console.log(`šŸ“ Ping received from ${clientInfo.id}:`, data);
100
120
  },
101
121
 
102
122
  pong(ws, data) {
103
- console.log("Pong received:", data);
123
+ const clientInfo = ws.data;
124
+ console.log(`šŸ“ Pong received from ${clientInfo.id}:`, data);
104
125
  }
105
126
  });
106
127
 
107
- // Another WebSocket route with parameters
128
+ // Chat room WebSocket with client identification
108
129
  app.ws("/chat/:room", {
109
130
  open(ws) {
110
- console.log(`WebSocket connection opened for room: ${ws.data?.room || 'unknown'}`);
111
- ws.send(`Welcome to chat room: ${ws.data?.room || 'unknown'}`);
131
+ const clientInfo = ws.data;
132
+ const room = clientInfo.path.split('/').pop() || 'unknown';
133
+ console.log(`šŸ  Chat room connection opened for room: ${room}`);
134
+ console.log(` šŸ†” Client: ${clientInfo.id} (${clientInfo.ip})`);
135
+ console.log(` šŸŖ Cookies:`, clientInfo.cookies);
136
+ ws.send(`Welcome to chat room: ${room}! Your ID is: ${clientInfo.id}`);
112
137
  },
113
138
 
114
139
  message(ws, message) {
115
- const room = ws.data?.room || 'unknown';
116
- console.log(`Message in room ${room}:`, message);
117
- ws.send(`[${room}] Echo: ${message}`);
140
+ const clientInfo = ws.data;
141
+ const room = clientInfo.path.split('/').pop() || 'unknown';
142
+ console.log(`šŸ’¬ Message in room ${room} from ${clientInfo.id}:`, message);
143
+ console.log(` šŸŖ Client cookies:`, clientInfo.cookies);
144
+ ws.send(`[${room}] [${clientInfo.id}] Echo: ${message}`);
118
145
  },
119
146
 
120
147
  close(ws, code, reason) {
121
- const room = ws.data?.room || 'unknown';
122
- console.log(`WebSocket connection closed for room ${room}: ${code} ${reason}`);
148
+ const clientInfo = ws.data;
149
+ const room = clientInfo.path.split('/').pop() || 'unknown';
150
+ console.log(`āŒ Chat room connection closed for room ${room} (${clientInfo.id}): ${code} ${reason}`);
123
151
  }
124
152
  });
125
153
 
126
154
  app.start();
127
- console.log(`Server is running on http://localhost:${app.server?.port}`);
128
- console.log(`WebSocket available at ws://localhost:${app.server?.port}/ws`);
129
- console.log(`Chat WebSocket available at ws://localhost:${app.server?.port}/chat/:room`);
155
+ console.log(`šŸš€ Server is running on http://localhost:${app.server?.port}`);
156
+ console.log(`šŸ”Œ WebSocket available at ws://localhost:${app.server?.port}/ws`);
157
+ console.log(`šŸ’¬ Chat WebSocket available at ws://localhost:${app.server?.port}/chat/:room`);
158
+ console.log(`\nšŸ“ Features demonstrated:`);
159
+ console.log(` • ws.id - Short, unique client identifier`);
160
+ console.log(` • ws.data.connectionId - Detailed connection ID`);
161
+ console.log(` • ws.data.cookies - Parsed cookies from handshake`);
162
+ console.log(` • Client IP, User Agent, Origin tracking`);
130
163
  }
131
164
 
132
- main().catch(console.error);
165
+ main().catch(console.error);
package/package.json CHANGED
@@ -5,7 +5,7 @@
5
5
  ".": "./src/index.ts",
6
6
  "./plugins": "./plugins/index.ts"
7
7
  },
8
- "version": "0.0.7",
8
+ "version": "0.0.8",
9
9
  "type": "module",
10
10
  "devDependencies": {
11
11
  "@types/bun": "latest"
package/src/index.ts CHANGED
@@ -92,6 +92,18 @@ type Handler<P extends string, S extends RouteSchema | undefined = undefined> =
92
92
  app: BXO
93
93
  ) => Response | string | BunFile | Promise<Response | string | BunFile>
94
94
 
95
+ // WebSocket client information type
96
+ export type WebSocketClientInfo = {
97
+ id: string; // Short, unique identifier for the WebSocket connection
98
+ path: string;
99
+ ip: string;
100
+ userAgent: string;
101
+ origin: string;
102
+ host: string;
103
+ connectionId: string; // Longer, more detailed connection identifier
104
+ cookies: Record<string, string>; // Parsed cookies from the handshake
105
+ };
106
+
95
107
  // WebSocket handler types
96
108
  export type WebSocketHandler<T = any> = {
97
109
  message?(ws: Bun.ServerWebSocket<T>, message: string | Buffer): void | Promise<void>;
@@ -436,22 +448,22 @@ export default class BXO {
436
448
 
437
449
  // Create WebSocket configuration if we have WebSocket routes
438
450
  const websocketConfig = hasWebSocketRoutes ? {
439
- message: (ws: Bun.ServerWebSocket<{ path: string }>, message: string | Buffer) => {
451
+ message: (ws: Bun.ServerWebSocket<WebSocketClientInfo>, message: string | Buffer) => {
440
452
  this.handleWebSocketMessage(ws, message);
441
453
  },
442
- open: (ws: Bun.ServerWebSocket<{ path: string }>) => {
454
+ open: (ws: Bun.ServerWebSocket<WebSocketClientInfo>) => {
443
455
  this.handleWebSocketOpen(ws);
444
456
  },
445
- close: (ws: Bun.ServerWebSocket<{ path: string }>, code: number, reason: string) => {
457
+ close: (ws: Bun.ServerWebSocket<WebSocketClientInfo>, code: number, reason: string) => {
446
458
  this.handleWebSocketClose(ws, code, reason);
447
459
  },
448
- drain: (ws: Bun.ServerWebSocket<{ path: string }>) => {
460
+ drain: (ws: Bun.ServerWebSocket<WebSocketClientInfo>) => {
449
461
  this.handleWebSocketDrain(ws);
450
462
  },
451
- ping: (ws: Bun.ServerWebSocket<{ path: string }>, data: Buffer) => {
463
+ ping: (ws: Bun.ServerWebSocket<WebSocketClientInfo>, data: Buffer) => {
452
464
  this.handleWebSocketPing(ws, data);
453
465
  },
454
- pong: (ws: Bun.ServerWebSocket<{ path: string }>, data: Buffer) => {
466
+ pong: (ws: Bun.ServerWebSocket<WebSocketClientInfo>, data: Buffer) => {
455
467
  this.handleWebSocketPong(ws, data);
456
468
  }
457
469
  } : undefined;
@@ -467,8 +479,26 @@ export default class BXO {
467
479
  const url = new URL(req.url);
468
480
  const wsRoute = this.findWebSocketRoute(url.pathname);
469
481
  if (wsRoute) {
482
+ // Capture client information during handshake
483
+ const shortId = Math.random().toString(36).substr(2, 8);
484
+ const connectionId = `${Date.now()}-${Math.random().toString(36).substr(2, 9)}`;
485
+ const cookieHeader = req.headers.get("cookie");
486
+
487
+ const clientInfo = {
488
+ id: shortId, // Short, easy-to-use ID
489
+ path: url.pathname,
490
+ ip: req.headers.get("x-forwarded-for") ||
491
+ req.headers.get("x-real-ip") ||
492
+ "unknown",
493
+ userAgent: req.headers.get("user-agent") || "unknown",
494
+ origin: req.headers.get("origin") || "unknown",
495
+ host: req.headers.get("host") || "unknown",
496
+ connectionId: connectionId, // Longer, more detailed ID
497
+ cookies: cookieHeader ? parseCookies(cookieHeader) : {}
498
+ };
499
+
470
500
  const success = server.upgrade(req, {
471
- data: { path: url.pathname }
501
+ data: clientInfo
472
502
  });
473
503
  if (success) {
474
504
  return; // WebSocket upgrade successful
@@ -533,7 +563,7 @@ export default class BXO {
533
563
  return null;
534
564
  }
535
565
 
536
- private handleWebSocketMessage(ws: Bun.ServerWebSocket<{ path: string }>, message: string | Buffer): void {
566
+ private handleWebSocketMessage(ws: Bun.ServerWebSocket<WebSocketClientInfo>, message: string | Buffer): void {
537
567
  const route = this.findWebSocketRoute(ws.data?.path || "");
538
568
  if (route?.websocketHandler?.message) {
539
569
  try {
@@ -544,7 +574,7 @@ export default class BXO {
544
574
  }
545
575
  }
546
576
 
547
- private handleWebSocketOpen(ws: Bun.ServerWebSocket<{ path: string }>): void {
577
+ private handleWebSocketOpen(ws: Bun.ServerWebSocket<WebSocketClientInfo>): void {
548
578
  const route = this.findWebSocketRoute(ws.data?.path || "");
549
579
  if (route?.websocketHandler?.open) {
550
580
  try {
@@ -555,7 +585,7 @@ export default class BXO {
555
585
  }
556
586
  }
557
587
 
558
- private handleWebSocketClose(ws: Bun.ServerWebSocket<{ path: string }>, code: number, reason: string): void {
588
+ private handleWebSocketClose(ws: Bun.ServerWebSocket<WebSocketClientInfo>, code: number, reason: string): void {
559
589
  const route = this.findWebSocketRoute(ws.data?.path || "");
560
590
  if (route?.websocketHandler?.close) {
561
591
  try {
@@ -566,7 +596,7 @@ export default class BXO {
566
596
  }
567
597
  }
568
598
 
569
- private handleWebSocketDrain(ws: Bun.ServerWebSocket<{ path: string }>): void {
599
+ private handleWebSocketDrain(ws: Bun.ServerWebSocket<WebSocketClientInfo>): void {
570
600
  const route = this.findWebSocketRoute(ws.data?.path || "");
571
601
  if (route?.websocketHandler?.drain) {
572
602
  try {
@@ -577,7 +607,7 @@ export default class BXO {
577
607
  }
578
608
  }
579
609
 
580
- private handleWebSocketPing(ws: Bun.ServerWebSocket<{ path: string }>, data: Buffer): void {
610
+ private handleWebSocketPing(ws: Bun.ServerWebSocket<WebSocketClientInfo>, data: Buffer): void {
581
611
  const route = this.findWebSocketRoute(ws.data?.path || "");
582
612
  if (route?.websocketHandler?.ping) {
583
613
  try {
@@ -588,7 +618,7 @@ export default class BXO {
588
618
  }
589
619
  }
590
620
 
591
- private handleWebSocketPong(ws: Bun.ServerWebSocket<{ path: string }>, data: Buffer): void {
621
+ private handleWebSocketPong(ws: Bun.ServerWebSocket<WebSocketClientInfo>, data: Buffer): void {
592
622
  const route = this.findWebSocketRoute(ws.data?.path || "");
593
623
  if (route?.websocketHandler?.pong) {
594
624
  try {