@naman_deep_singh/server-utils 1.0.8 → 1.2.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.
Files changed (51) hide show
  1. package/README.md +401 -11
  2. package/dist/{index.d.ts → cjs/index.d.ts} +1 -1
  3. package/dist/{index.js → cjs/index.js} +3 -1
  4. package/dist/{middleware.d.ts → cjs/middleware.d.ts} +2 -0
  5. package/dist/{middleware.js → cjs/middleware.js} +137 -10
  6. package/dist/{server.d.ts → cjs/server.d.ts} +1 -0
  7. package/dist/{server.js → cjs/server.js} +119 -4
  8. package/dist/{types.d.ts → cjs/types.d.ts} +17 -0
  9. package/dist/{utils.js → cjs/utils.js} +14 -8
  10. package/dist/esm/health.d.ts +5 -0
  11. package/dist/esm/health.js +40 -0
  12. package/dist/esm/index.d.ts +46 -0
  13. package/dist/esm/index.js +58 -0
  14. package/dist/esm/middleware.d.ts +39 -0
  15. package/dist/esm/middleware.js +327 -0
  16. package/dist/esm/periodic-health.d.ts +11 -0
  17. package/dist/esm/periodic-health.js +64 -0
  18. package/dist/esm/server.d.ts +70 -0
  19. package/dist/esm/server.js +386 -0
  20. package/dist/esm/shutdown.d.ts +5 -0
  21. package/dist/esm/shutdown.js +52 -0
  22. package/dist/esm/types.d.ts +87 -0
  23. package/dist/esm/types.js +1 -0
  24. package/dist/esm/utils.d.ts +3 -0
  25. package/dist/esm/utils.js +38 -0
  26. package/dist/types/health.d.ts +5 -0
  27. package/dist/types/index.d.ts +46 -0
  28. package/dist/types/middleware.d.ts +39 -0
  29. package/dist/types/periodic-health.d.ts +11 -0
  30. package/dist/types/server.d.ts +70 -0
  31. package/dist/types/shutdown.d.ts +5 -0
  32. package/dist/types/types.d.ts +87 -0
  33. package/dist/types/utils.d.ts +3 -0
  34. package/package.json +26 -10
  35. package/src/health.ts +0 -47
  36. package/src/index.ts +0 -126
  37. package/src/middleware.ts +0 -275
  38. package/src/periodic-health.ts +0 -83
  39. package/src/server.ts +0 -412
  40. package/src/shutdown.ts +0 -69
  41. package/src/types.ts +0 -80
  42. package/src/utils.ts +0 -34
  43. package/tsconfig.json +0 -21
  44. /package/dist/{health.d.ts → cjs/health.d.ts} +0 -0
  45. /package/dist/{health.js → cjs/health.js} +0 -0
  46. /package/dist/{periodic-health.d.ts → cjs/periodic-health.d.ts} +0 -0
  47. /package/dist/{periodic-health.js → cjs/periodic-health.js} +0 -0
  48. /package/dist/{shutdown.d.ts → cjs/shutdown.d.ts} +0 -0
  49. /package/dist/{shutdown.js → cjs/shutdown.js} +0 -0
  50. /package/dist/{types.js → cjs/types.js} +0 -0
  51. /package/dist/{utils.d.ts → cjs/utils.d.ts} +0 -0
package/README.md CHANGED
@@ -1,6 +1,8 @@
1
1
  # @naman_deep_singh/server-utils
2
2
 
3
- Extensible server utilities for Express.js microservices with multi-protocol support and TypeScript.
3
+ **Version:** 1.2.0 (with integrated cache & session support)
4
+
5
+ Extensible server utilities for Express.js microservices with multi-protocol support, integrated caching, session management, and TypeScript.
4
6
 
5
7
  ## Installation
6
8
 
@@ -11,13 +13,15 @@ npm install @naman_deep_singh/server-utils
11
13
  ## Features
12
14
 
13
15
  - ✅ **Multi-protocol support** - HTTP, gRPC, JSON-RPC, WebSockets, Webhooks
16
+ - ✅ **Integrated caching** - Redis, Memcache, in-memory with automatic fallback
17
+ - ✅ **Session management** - Distributed session store with configurable TTL
14
18
  - ✅ **Express.js integration** with middleware collection
15
- - ✅ **Graceful shutdown** handling
16
- - ✅ **Health checks** with custom checks support
19
+ - ✅ **Graceful shutdown** handling with cache/session cleanup
20
+ - ✅ **Health checks** with custom checks and cache health integration
17
21
  - ✅ **TypeScript support** with full type safety
18
22
  - ✅ **Hybrid exports** - use named imports or namespace imports
19
23
  - ✅ **Plugin architecture** for extensibility
20
- - ✅ **Built-in middleware** - logging, validation, rate limiting, auth
24
+ - ✅ **Built-in middleware** - logging, validation, rate limiting, auth, caching, sessions
21
25
 
22
26
  ## Quick Start
23
27
 
@@ -180,9 +184,24 @@ server.app.use('/protected', requireAuth({
180
184
 
181
185
  ## Health Checks
182
186
 
187
+ ### Basic Health Check
183
188
  ```typescript
184
- import { addHealthCheck } from '@naman_deep_singh/server-utils';
189
+ import { addHealthCheck, createHealthCheck, withHealthCheck } from '@naman_deep_singh/server-utils';
190
+
191
+ // Method 1: Direct addition
192
+ addHealthCheck(server.app, '/health');
193
+
194
+ // Method 2: As middleware
195
+ server.app.get('/health', createHealthCheck());
196
+
197
+ // Method 3: As plugin
198
+ const server = createServerWithPlugins('My API', '1.0.0', [
199
+ withHealthCheck('/health')
200
+ ]);
201
+ ```
185
202
 
203
+ ### Advanced Health Checks
204
+ ```typescript
186
205
  addHealthCheck(server.app, '/health', {
187
206
  customChecks: [
188
207
  {
@@ -200,6 +219,17 @@ addHealthCheck(server.app, '/health', {
200
219
  }
201
220
  ]
202
221
  });
222
+
223
+ // Response format:
224
+ // {
225
+ // "status": "healthy",
226
+ // "checks": {
227
+ // "server": true,
228
+ // "timestamp": 1640995200000,
229
+ // "database": true,
230
+ // "redis": false
231
+ // }
232
+ // }
203
233
  ```
204
234
 
205
235
  ## Server Management
@@ -246,12 +276,78 @@ interface ServerConfig {
246
276
  }
247
277
  ```
248
278
 
279
+ ## Environment Utilities
280
+
281
+ ```typescript
282
+ import { getEnv, getEnvNumber, getEnvBoolean } from '@naman_deep_singh/server-utils';
283
+
284
+ // Get string environment variable
285
+ const dbUrl = getEnv('DATABASE_URL'); // Throws if missing
286
+ const dbUrl = getEnv('DATABASE_URL', 'localhost'); // With default
287
+
288
+ // Get number environment variable
289
+ const port = getEnvNumber('PORT', 3000);
290
+ const maxConnections = getEnvNumber('MAX_CONNECTIONS'); // Throws if missing
291
+
292
+ // Get boolean environment variable
293
+ const enableLogging = getEnvBoolean('ENABLE_LOGGING', true);
294
+ const isProduction = getEnvBoolean('NODE_ENV'); // Must be 'true' or 'false'
295
+ ```
296
+
297
+ ## Periodic Health Monitoring
298
+
299
+ ```typescript
300
+ import { PeriodicHealthMonitor } from '@naman_deep_singh/server-utils';
301
+
302
+ const server = createServer('My API', '1.0.0', {
303
+ periodicHealthCheck: {
304
+ enabled: true,
305
+ interval: 30000, // 30 seconds
306
+ services: [
307
+ {
308
+ name: 'database',
309
+ url: 'http://localhost:5432/health',
310
+ timeout: 5000
311
+ },
312
+ {
313
+ name: 'redis',
314
+ url: 'http://localhost:6379/ping'
315
+ }
316
+ ]
317
+ }
318
+ });
319
+
320
+ // Manual health check
321
+ const monitor = new PeriodicHealthMonitor(config, 'My Service');
322
+ monitor.start();
323
+ const status = await monitor.getHealthStatus();
324
+ console.log(status); // { database: true, redis: false }
325
+ ```
326
+
327
+ ## Express Re-exports
328
+
329
+ ```typescript
330
+ // Import Express types and classes directly from server-utils
331
+ import { Request, Response, NextFunction, Router, Application } from '@naman_deep_singh/server-utils';
332
+ import type { RequestHandler, ErrorRequestHandler } from '@naman_deep_singh/server-utils';
333
+
334
+ // No need to install Express separately in your services
335
+ ```
336
+
249
337
  ## API Reference
250
338
 
251
339
  ### Core Functions
252
340
  - `createServer(name?, version?, config?)` - Create server instance
253
341
  - `ExpressServer` - Server class for advanced usage
254
342
 
343
+ ### Environment Utilities
344
+ - `getEnv(key, defaultValue?)` - Get string environment variable
345
+ - `getEnvNumber(key, defaultValue?)` - Get number environment variable
346
+ - `getEnvBoolean(key, defaultValue?)` - Get boolean environment variable
347
+
348
+ ### Health Monitoring
349
+ - `PeriodicHealthMonitor` - Automated service health checking
350
+
255
351
  ### Middleware Functions
256
352
  - `createLoggingMiddleware(format?)` - Request logging
257
353
  - `createErrorHandler()` - Error handling
@@ -260,8 +356,10 @@ interface ServerConfig {
260
356
  - `createAuthMiddleware(config)` - Authentication
261
357
 
262
358
  ### Health & Monitoring
263
- - `createHealthCheck(config?)` - Health check endpoint
359
+ - `createHealthCheck(config?)` - Create health check middleware
360
+ - `withHealthCheck(path?, config?)` - Health check plugin
264
361
  - `addHealthCheck(app, path?, config?)` - Add health check to app
362
+ - `PeriodicHealthMonitor` - Automated service health checking
265
363
 
266
364
  ### Graceful Shutdown
267
365
  - `createGracefulShutdown(server, config?)` - Setup graceful shutdown
@@ -270,12 +368,304 @@ interface ServerConfig {
270
368
  ## Dependencies
271
369
 
272
370
  ### Required
273
- - **express** - Web framework
274
- - **cors** - CORS middleware
275
- - **helmet** - Security middleware
276
- - **cookie-parser** - Cookie parsing
371
+ - **express** - Web framework (v5.1.0+)
277
372
 
278
373
  ### Optional (for specific features)
374
+ - **cors** - CORS middleware (if using CORS)
375
+ - **helmet** - Security middleware (if using Helmet)
376
+ - **cookie-parser** - Cookie parsing (if using cookies)
279
377
  - **@grpc/grpc-js** - For gRPC support
280
378
  - **jayson** - For JSON-RPC support
281
- - **socket.io** - For WebSocket support
379
+ - **socket.io** - For WebSocket support
380
+
381
+ ## Response Format
382
+
383
+ All middleware responses follow the consistent format:
384
+
385
+ ```json
386
+ {
387
+ "success": true/false,
388
+ "message": "Operation message",
389
+ "data": {...} | undefined,
390
+ "error": {
391
+ "message": "Error message",
392
+ "details": {...}
393
+ } | null,
394
+ "meta": {...} | null
395
+ }
396
+ ```
397
+
398
+ ### Integration with @naman_deep_singh/response-utils
399
+
400
+ For advanced error handling, use with `@naman_deep_singh/errors-utils`:
401
+
402
+ ```typescript
403
+ import { expressErrorHandler } from '@naman_deep_singh/errors-utils';
404
+
405
+ // Replace basic error handler with advanced one
406
+ server.app.use(expressErrorHandler);
407
+ ```
408
+
409
+ ### Integration with @naman_deep_singh/response-utils
410
+
411
+ For consistent API responses, use with `@naman_deep_singh/response-utils`:
412
+
413
+ ```typescript
414
+ import { responderMiddleware } from '@naman_deep_singh/response-utils';
415
+
416
+ server.app.use(responderMiddleware());
417
+
418
+ // Now use responder in routes
419
+ server.app.get('/users', (req, res) => {
420
+ const responder = (res as any).responder();
421
+ return responder.okAndSend({ users: [] });
422
+ });
423
+ ```
424
+
425
+ ## Cache & Session Integration
426
+
427
+ Built-in support for distributed caching and session management (disabled by default).
428
+
429
+ ### Enable Redis Cache
430
+
431
+ ```typescript
432
+ const server = createServer('My API', '1.0.0', {
433
+ port: 3000,
434
+ cache: {
435
+ enabled: true,
436
+ adapter: 'redis',
437
+ options: {
438
+ host: 'localhost',
439
+ port: 6379,
440
+ password: 'your_password'
441
+ },
442
+ defaultTTL: 3600 // seconds
443
+ }
444
+ });
445
+
446
+ // Access cache in routes
447
+ server.app.get('/user/:id', async (req, res) => {
448
+ const key = `user:${req.params.id}`;
449
+ const cached = await (req as any).cache.get(key);
450
+ if (cached) return res.json(cached);
451
+
452
+ // Fetch from DB, then cache
453
+ const user = { id: req.params.id, name: 'John' };
454
+ await (req as any).cache.set(key, user, 3600);
455
+ return res.json(user);
456
+ });
457
+ ```
458
+
459
+ ### Enable Redis Cluster Cache
460
+
461
+ ```typescript
462
+ const server = createServer('My API', '1.0.0', {
463
+ port: 3000,
464
+ cache: {
465
+ enabled: true,
466
+ adapter: 'redis',
467
+ options: {
468
+ cluster: [
469
+ { host: 'redis-node-1', port: 6379 },
470
+ { host: 'redis-node-2', port: 6379 },
471
+ { host: 'redis-node-3', port: 6379 }
472
+ ]
473
+ }
474
+ }
475
+ });
476
+ ```
477
+
478
+ ### Enable Memcache
479
+
480
+ ```typescript
481
+ const server = createServer('My API', '1.0.0', {
482
+ port: 3000,
483
+ cache: {
484
+ enabled: true,
485
+ adapter: 'memcache',
486
+ options: {
487
+ servers: ['localhost:11211', 'localhost:11212']
488
+ }
489
+ }
490
+ });
491
+ ```
492
+
493
+ ### Enable Sessions
494
+
495
+ ```typescript
496
+ const server = createServer('My API', '1.0.0', {
497
+ port: 3000,
498
+ cache: {
499
+ enabled: true,
500
+ adapter: 'redis',
501
+ options: { host: 'localhost', port: 6379 }
502
+ },
503
+ session: {
504
+ enabled: true,
505
+ cookieName: 'my_app.sid', // Defaults to {servername}.sid
506
+ ttl: 3600, // 1 hour
507
+ cookieOptions: {
508
+ httpOnly: true,
509
+ secure: true, // HTTPS only
510
+ sameSite: 'strict'
511
+ }
512
+ }
513
+ });
514
+
515
+ // Use sessions in routes
516
+ server.app.post('/login', async (req, res) => {
517
+ const sessionStore = (req.app as any).locals.sessionStore;
518
+ const sessionId = Math.random().toString(36).substring(7);
519
+
520
+ await sessionStore.create(sessionId, {
521
+ userId: 123,
522
+ username: 'john_doe',
523
+ loginTime: new Date()
524
+ });
525
+
526
+ res.cookie((req.app as any).locals.sessionCookieName, sessionId, {
527
+ httpOnly: true,
528
+ secure: true
529
+ });
530
+
531
+ return res.json({ message: 'Logged in' });
532
+ });
533
+
534
+ server.app.get('/profile', async (req, res) => {
535
+ const sessionId = (req as any).sessionId;
536
+ if (!sessionId) return res.status(401).json({ error: 'No session' });
537
+
538
+ const session = await (req as any).getSession();
539
+ if (!session) return res.status(401).json({ error: 'Session expired' });
540
+
541
+ return res.json({ user: session.username, loginTime: session.loginTime });
542
+ });
543
+ ```
544
+
545
+ ### Per-Route Response Caching
546
+
547
+ ```typescript
548
+ import { cacheResponse } from '@naman_deep_singh/server-utils';
549
+
550
+ // Cache GET response for 1 hour (3600 seconds)
551
+ server.app.get('/api/posts', cacheResponse(3600), (req, res) => {
552
+ // This endpoint's response is cached
553
+ res.json({ posts: [...] });
554
+ });
555
+
556
+ // Cache with default TTL from server config
557
+ server.app.get('/api/trending', cacheResponse(), (req, res) => {
558
+ res.json({ trending: [...] });
559
+ });
560
+ ```
561
+
562
+ ### Health Check with Cache Status
563
+
564
+ ```typescript
565
+ const server = createServer('My API', '1.0.0', {
566
+ healthCheck: '/health', // Automatic health endpoint
567
+ cache: { enabled: true, adapter: 'redis', ... }
568
+ });
569
+
570
+ // Health endpoint now includes cache status
571
+ // GET /health returns:
572
+ // {
573
+ // "status": "healthy",
574
+ // "service": "My API",
575
+ // "version": "1.0.0",
576
+ // "uptime": 12345,
577
+ // "timestamp": "2025-12-12T...",
578
+ // "cache": {
579
+ // "isAlive": true,
580
+ // "adapter": "redis",
581
+ // "timestamp": "2025-12-12T..."
582
+ // }
583
+ // }
584
+ ```
585
+
586
+ ### Cache Configuration Options
587
+
588
+ All configuration is optional — cache and session are disabled by default:
589
+
590
+ ```typescript
591
+ interface CacheConfig {
592
+ enabled?: boolean; // Default: false
593
+ adapter?: 'redis' | 'memcache' | 'memory'; // Default: 'memory'
594
+ options?: {
595
+ // Redis single instance
596
+ host?: string; // Default: 'localhost'
597
+ port?: number; // Default: 6379
598
+ username?: string;
599
+ password?: string;
600
+ db?: number; // 0-15
601
+ tls?: boolean;
602
+
603
+ // Redis cluster
604
+ cluster?: Array<{ host: string; port: number }> | {
605
+ nodes: Array<{ host: string; port: number }>;
606
+ options?: { maxRedirections?: number; ... };
607
+ };
608
+
609
+ // Memcache
610
+ servers?: string | string[]; // e.g., 'localhost:11211'
611
+
612
+ namespace?: string; // Key prefix
613
+ ttl?: number; // Default TTL in seconds
614
+ };
615
+ defaultTTL?: number; // Fallback TTL for routes
616
+ }
617
+
618
+ interface SessionConfig {
619
+ enabled?: boolean; // Default: false
620
+ cookieName?: string; // Default: {servername}.sid
621
+ ttl?: number; // Default: 3600 (1 hour)
622
+ cookieOptions?: {
623
+ path?: string;
624
+ httpOnly?: boolean; // Default: true
625
+ secure?: boolean; // HTTPS only
626
+ sameSite?: 'lax' | 'strict' | 'none';
627
+ };
628
+ }
629
+ ```
630
+
631
+ ### Graceful Shutdown
632
+
633
+ Cache and session stores are automatically closed on graceful shutdown:
634
+
635
+ ```typescript
636
+ const server = createServer('My API', '1.0.0', {
637
+ gracefulShutdown: true, // Enabled by default
638
+ cache: { enabled: true, adapter: 'redis', ... },
639
+ session: { enabled: true, ... }
640
+ });
641
+
642
+ // On SIGTERM/SIGINT, server will:
643
+ // 1. Stop accepting requests
644
+ // 2. Close cache connection (Redis/Memcache)
645
+ // 3. Close session store
646
+ // 4. Exit gracefully
647
+ ```
648
+
649
+ ## Feature Flags
650
+
651
+ All major features can be toggled independently:
652
+
653
+ ```typescript
654
+ const server = createServer('My API', '1.0.0', {
655
+ port: 3000,
656
+ cors: true, // Default: true
657
+ helmet: true, // Default: true
658
+ json: true, // Default: true
659
+ cookieParser: false, // Default: false
660
+ healthCheck: '/health', // Default: true
661
+ gracefulShutdown: true, // Default: true
662
+ cache: { enabled: false }, // Default: disabled
663
+ session: { enabled: false }, // Default: disabled
664
+ socketIO: { enabled: false }, // Default: disabled
665
+ periodicHealthCheck: { // Default: disabled
666
+ enabled: false,
667
+ interval: 30000,
668
+ services: [...]
669
+ }
670
+ });
671
+ ```
@@ -4,7 +4,7 @@ export { Request, Response, NextFunction, Router, Application } from 'express';
4
4
  export type { RequestHandler, ErrorRequestHandler } from 'express';
5
5
  export { createHealthCheck, withHealthCheck, addHealthCheck } from './health';
6
6
  export { createGracefulShutdown, withGracefulShutdown, startServerWithShutdown } from './shutdown';
7
- export { createLoggingMiddleware, createErrorHandler, createRequestIdMiddleware, createValidationMiddleware, createRateLimitMiddleware, createAuthMiddleware, withLogging, withErrorHandler, withRequestId, withValidation, withRateLimit, withAuth, validateFields, rateLimit, requireAuth, type ValidationRule, type RateLimitConfig, type AuthConfig } from './middleware';
7
+ export { createLoggingMiddleware, createErrorHandler, createRequestIdMiddleware, createValidationMiddleware, createRateLimitMiddleware, createAuthMiddleware, withLogging, withErrorHandler, withRequestId, withValidation, withRateLimit, withAuth, validateFields, rateLimit, requireAuth, cacheResponse, useSession, type ValidationRule, type RateLimitConfig, type AuthConfig } from './middleware';
8
8
  export { getEnv, getEnvNumber, getEnvBoolean } from './utils';
9
9
  export { PeriodicHealthMonitor } from './periodic-health';
10
10
  export type { ServerConfig, HealthCheckConfig, HealthCheck, GracefulShutdownConfig, ServerPlugin, SocketIOConfig, SocketInstance, PeriodicHealthCheckConfig, HealthCheckService } from './types';
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.PeriodicHealthMonitor = exports.getEnvBoolean = exports.getEnvNumber = exports.getEnv = exports.requireAuth = exports.rateLimit = exports.validateFields = exports.withAuth = exports.withRateLimit = exports.withValidation = exports.withRequestId = exports.withErrorHandler = exports.withLogging = exports.createAuthMiddleware = exports.createRateLimitMiddleware = exports.createValidationMiddleware = exports.createRequestIdMiddleware = exports.createErrorHandler = exports.createLoggingMiddleware = exports.startServerWithShutdown = exports.withGracefulShutdown = exports.createGracefulShutdown = exports.addHealthCheck = exports.withHealthCheck = exports.createHealthCheck = exports.Router = exports.createServer = exports.ExpressServer = void 0;
3
+ exports.PeriodicHealthMonitor = exports.getEnvBoolean = exports.getEnvNumber = exports.getEnv = exports.useSession = exports.cacheResponse = exports.requireAuth = exports.rateLimit = exports.validateFields = exports.withAuth = exports.withRateLimit = exports.withValidation = exports.withRequestId = exports.withErrorHandler = exports.withLogging = exports.createAuthMiddleware = exports.createRateLimitMiddleware = exports.createValidationMiddleware = exports.createRequestIdMiddleware = exports.createErrorHandler = exports.createLoggingMiddleware = exports.startServerWithShutdown = exports.withGracefulShutdown = exports.createGracefulShutdown = exports.addHealthCheck = exports.withHealthCheck = exports.createHealthCheck = exports.Router = exports.createServer = exports.ExpressServer = void 0;
4
4
  // Core server utilities
5
5
  var server_1 = require("./server");
6
6
  Object.defineProperty(exports, "ExpressServer", { enumerable: true, get: function () { return server_1.ExpressServer; } });
@@ -35,6 +35,8 @@ Object.defineProperty(exports, "withAuth", { enumerable: true, get: function ()
35
35
  Object.defineProperty(exports, "validateFields", { enumerable: true, get: function () { return middleware_1.validateFields; } });
36
36
  Object.defineProperty(exports, "rateLimit", { enumerable: true, get: function () { return middleware_1.rateLimit; } });
37
37
  Object.defineProperty(exports, "requireAuth", { enumerable: true, get: function () { return middleware_1.requireAuth; } });
38
+ Object.defineProperty(exports, "cacheResponse", { enumerable: true, get: function () { return middleware_1.cacheResponse; } });
39
+ Object.defineProperty(exports, "useSession", { enumerable: true, get: function () { return middleware_1.useSession; } });
38
40
  // Utility functions
39
41
  var utils_1 = require("./utils");
40
42
  Object.defineProperty(exports, "getEnv", { enumerable: true, get: function () { return utils_1.getEnv; } });
@@ -35,3 +35,5 @@ export declare function withAuth(config: AuthConfig): ServerPlugin;
35
35
  export declare function validateFields(rules: ValidationRule[]): express.RequestHandler;
36
36
  export declare function rateLimit(config?: RateLimitConfig): express.RequestHandler;
37
37
  export declare function requireAuth(config: AuthConfig): express.RequestHandler;
38
+ export declare function cacheResponse(ttl?: number): express.RequestHandler;
39
+ export declare function useSession(cookieName?: string): express.RequestHandler;
@@ -15,6 +15,8 @@ exports.withAuth = withAuth;
15
15
  exports.validateFields = validateFields;
16
16
  exports.rateLimit = rateLimit;
17
17
  exports.requireAuth = requireAuth;
18
+ exports.cacheResponse = cacheResponse;
19
+ exports.useSession = useSession;
18
20
  // Logging middleware
19
21
  function createLoggingMiddleware(format = 'simple') {
20
22
  return (req, res, next) => {
@@ -45,9 +47,14 @@ function createErrorHandler() {
45
47
  ? 'Internal Server Error'
46
48
  : errorObj.message || 'Unknown error';
47
49
  res.status(status).json({
48
- status: false,
50
+ success: false,
49
51
  message,
50
- ...(process.env.NODE_ENV !== 'production' && { stack: errorObj.stack })
52
+ data: undefined,
53
+ error: {
54
+ message,
55
+ ...(process.env.NODE_ENV !== 'production' && { details: { stack: errorObj.stack } })
56
+ },
57
+ meta: null
51
58
  });
52
59
  };
53
60
  }
@@ -114,9 +121,14 @@ function createValidationMiddleware(rules) {
114
121
  }
115
122
  if (errors.length > 0) {
116
123
  return res.status(400).json({
117
- status: false,
124
+ success: false,
118
125
  message: 'Validation failed',
119
- errors
126
+ data: undefined,
127
+ error: {
128
+ message: 'Validation failed',
129
+ details: errors
130
+ },
131
+ meta: null
120
132
  });
121
133
  }
122
134
  next();
@@ -138,9 +150,16 @@ function createRateLimitMiddleware(config = {}) {
138
150
  }
139
151
  if (record.count >= maxRequests) {
140
152
  return res.status(429).json({
141
- status: false,
153
+ success: false,
142
154
  message,
143
- retryAfter: Math.ceil((record.resetTime - now) / 1000)
155
+ data: undefined,
156
+ error: {
157
+ message,
158
+ details: {
159
+ retryAfter: Math.ceil((record.resetTime - now) / 1000)
160
+ }
161
+ },
162
+ meta: null
144
163
  });
145
164
  }
146
165
  record.count++;
@@ -160,8 +179,13 @@ function createAuthMiddleware(config) {
160
179
  const token = tokenExtractor(req);
161
180
  if (!token) {
162
181
  return res.status(401).json({
163
- status: false,
164
- message: unauthorizedMessage
182
+ success: false,
183
+ message: unauthorizedMessage,
184
+ data: undefined,
185
+ error: {
186
+ message: unauthorizedMessage
187
+ },
188
+ meta: null
165
189
  });
166
190
  }
167
191
  const user = await tokenValidator(token);
@@ -170,8 +194,13 @@ function createAuthMiddleware(config) {
170
194
  }
171
195
  catch (error) {
172
196
  return res.status(401).json({
173
- status: false,
174
- message: unauthorizedMessage
197
+ success: false,
198
+ message: unauthorizedMessage,
199
+ data: undefined,
200
+ error: {
201
+ message: unauthorizedMessage
202
+ },
203
+ meta: null
175
204
  });
176
205
  }
177
206
  };
@@ -217,3 +246,101 @@ function rateLimit(config = {}) {
217
246
  function requireAuth(config) {
218
247
  return createAuthMiddleware(config);
219
248
  }
249
+ // Cache response middleware (per-route opt-in)
250
+ function cacheResponse(ttl) {
251
+ return async (req, res, next) => {
252
+ try {
253
+ if (req.method !== 'GET')
254
+ return next();
255
+ const cache = req.cache || req.app.locals.cache;
256
+ const defaultTTL = req.app.locals.cacheDefaultTTL;
257
+ if (!cache)
258
+ return next();
259
+ const key = `${req.originalUrl}`;
260
+ try {
261
+ const cached = await cache.get(key);
262
+ if (cached !== null && cached !== undefined) {
263
+ res.setHeader('X-Cache', 'HIT');
264
+ return res.json(cached);
265
+ }
266
+ }
267
+ catch (cacheErr) {
268
+ console.error(`[Cache] Failed to retrieve key "${key}":`, cacheErr);
269
+ // Continue without cache hit
270
+ }
271
+ const originalJson = res.json.bind(res);
272
+ res.json = (body) => {
273
+ try {
274
+ const expiry = ttl ?? defaultTTL;
275
+ if (expiry && cache) {
276
+ cache.set(key, body, expiry).catch((err) => {
277
+ console.error(`[Cache] Failed to set key "${key}" with TTL ${expiry}:`, err);
278
+ });
279
+ }
280
+ else if (cache) {
281
+ cache.set(key, body).catch((err) => {
282
+ console.error(`[Cache] Failed to set key "${key}":`, err);
283
+ });
284
+ }
285
+ }
286
+ catch (e) {
287
+ console.error(`[Cache] Error during cache.set operation:`, e);
288
+ }
289
+ res.setHeader('X-Cache', 'MISS');
290
+ return originalJson(body);
291
+ };
292
+ next();
293
+ }
294
+ catch (err) {
295
+ console.error('[Cache] Unexpected error in cacheResponse middleware:', err);
296
+ next();
297
+ }
298
+ };
299
+ }
300
+ // Session middleware helper (attaches sessionStore and helpers to req)
301
+ function useSession(cookieName) {
302
+ return async (req, res, next) => {
303
+ try {
304
+ const store = req.app.locals.sessionStore;
305
+ if (!store)
306
+ return next();
307
+ const name = cookieName || req.app.locals.sessionCookieName || 'sid';
308
+ let sid = req.cookies?.[name] || req.cookies?.[name];
309
+ if (!sid) {
310
+ const cookieHeader = req.headers.cookie;
311
+ if (cookieHeader) {
312
+ const match = cookieHeader.split(';').map(s => s.trim()).find(s => s.startsWith(name + '='));
313
+ if (match)
314
+ sid = match.split('=')[1];
315
+ }
316
+ }
317
+ req.sessionId = sid;
318
+ req.sessionStore = store;
319
+ req.getSession = async () => {
320
+ if (!sid)
321
+ return null;
322
+ try {
323
+ return await store.get(sid);
324
+ }
325
+ catch (err) {
326
+ console.error(`[Session] Failed to get session "${sid}":`, err);
327
+ throw err;
328
+ }
329
+ };
330
+ req.createSession = async (id, data, ttl) => {
331
+ try {
332
+ return await store.create(id, data, ttl);
333
+ }
334
+ catch (err) {
335
+ console.error(`[Session] Failed to create session "${id}":`, err);
336
+ throw err;
337
+ }
338
+ };
339
+ next();
340
+ }
341
+ catch (err) {
342
+ console.error('[Session] Unexpected error in useSession middleware:', err);
343
+ next();
344
+ }
345
+ };
346
+ }