keycloak-express-middleware 6.0.1 → 6.0.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (3) hide show
  1. package/README.md +193 -178
  2. package/index.js +5 -3
  3. package/package.json +1 -1
package/README.md CHANGED
@@ -26,7 +26,7 @@ application scope. By moving to this new ***one instance = one client*** model,
26
26
  - isolating middleware logic per client without risking cross-contamination of sessions or grants,
27
27
  - simplifying multitenancy or micro-service architectures where different parts of an app authenticate against different Keycloak clients.
28
28
 
29
- **To summarize:** the new version enables multi-client usage within the same app by turning the middleware into configurable,
29
+ **To summarize:** the new version (4.0.0+) enables multi-client usage within the same app by turning the middleware into configurable,
30
30
  independent object instances — something that the earlier version did not support.
31
31
 
32
32
  ### 🏗️ Migration Guide: From Old to New Version
@@ -55,15 +55,15 @@ await keycloackAdapter.configure(app,{
55
55
  });
56
56
 
57
57
  // Example of protection with keycloackAdapter.protectMiddleware middleware
58
- // whith a static client role validation string
58
+ // with a static client role validation string
59
59
  // Access is allowed only for authenticated admin users
60
60
  app.get('/privateStaticClientRole', keycloackAdapter.protectMiddleware("admin"), (req, res) => {
61
61
  // "Your Custom Code"
62
- res.send("Is its admin.");
62
+ res.send("You are an admin.");
63
63
  });
64
64
  ```
65
65
 
66
- 🆕 New Version (Object-Oriented Design) Up to 4.0.0
66
+ 🆕 New Version (Object-Oriented Design) - Version 4.0.0+
67
67
 
68
68
  ```js
69
69
  // NEW VERSION STARTING FROM 4.0.0
@@ -108,12 +108,12 @@ const keycloakB = new keycloackAdapter(app,{
108
108
 
109
109
 
110
110
  // Example protected routes
111
- app.get('/clientA/secure', keycloakA.protect(), (req, res) => {
112
- res.send('Protected route for Client A');
111
+ app.get('/clientA/secure', keycloakA.protectMiddleware(), (req, res) => {
112
+ res.send('Protected route for Client A');
113
113
  });
114
114
 
115
- app.get('/clientB/secure', keycloakB.protect(), (req, res) => {
116
- res.send('Protected route for Client B');
115
+ app.get('/clientB/secure', keycloakB.protectMiddleware(), (req, res) => {
116
+ res.send('Protected route for Client B');
117
117
  });
118
118
 
119
119
  app.listen(3000, () => console.log('Server running on port 3000'));
@@ -148,18 +148,20 @@ the Keycloak Admin Console → clients (left sidebar) → choose your client →
148
148
  ## 📄 Usage Example
149
149
  ```js
150
150
  const express = require('express');
151
- const keycloackAdapterClass = require('keycloak-express-middleware'); // import keycloackAdapter from 'keycloak-express-middleware';
151
+ // CommonJS - Default import
152
+ const keycloackAdapter = require('keycloak-express-middleware');
153
+
154
+ // ES6 - Named import (recommended for clarity)
155
+ // import { keycloackAdapter } from 'keycloak-express-middleware';
152
156
 
153
- /*
154
- Old Style up to version 3.0.9
155
- const keycloackAdapter = require('keycloak-express-middleware'); // import keycloackAdapter from 'keycloak-express-middleware';
156
- */
157
+ // ES6 - Default import
158
+ // import keycloackAdapter from 'keycloak-express-middleware';
157
159
 
158
160
  const app = express();
159
161
 
160
162
 
161
163
  // Configure and Initialize Keycloak adapter
162
- keycloackAdapter= new keycloackAdapterClass(app,{
164
+ const keycloakInstance = new keycloackAdapter(app,{
163
165
  "realm": "Realm-Project",
164
166
  "auth-server-url": "https://YourKeycloakUrl:30040/",
165
167
  "ssl-required": "external",
@@ -175,28 +177,6 @@ keycloackAdapter= new keycloackAdapterClass(app,{
175
177
  }
176
178
  });
177
179
 
178
- /*
179
- OLD STYLE UP TO VERSION 3.0.9
180
- // Configure and Initialize Keycloak adapter
181
- await keycloackAdapter.configure(app,{
182
- "realm": "Realm-Project",
183
- "auth-server-url": "https://YourKeycloakUrl:30040/",
184
- "ssl-required": "external",
185
- "resource": "keycloackclientName",
186
- "credentials": {
187
- "secret": "aaaaaaaaaa"
188
- },
189
- "confidential-port": 0
190
- },
191
- {
192
- session:{
193
- secret: 'mySecretForSession',
194
- }
195
- });
196
- */
197
-
198
-
199
-
200
180
  // -------------- Public route -----------------------
201
181
  app.get('/', (req, res) => {
202
182
  res.send('Public route: no authentication required');
@@ -205,100 +185,100 @@ app.get('/', (req, res) => {
205
185
 
206
186
  /* ############## Protected routes (any authenticated user) ########### */
207
187
 
208
- // Example of login with keycloackAdapter.login function
188
+ // Example of login with keycloakInstance.login function
209
189
  // After login redirect to "/home"
210
190
  app.get('/signIn', (req, res) => {
211
191
  console.log("Your Custom Code");
212
- keycloackAdapter.login(req,res,"/home")
192
+ keycloakInstance.login(req,res,"/home")
213
193
 
214
194
  });
215
195
 
216
- // Example of login with keycloackAdapter.loginMiddleware middleware
196
+ // Example of login with keycloakInstance.loginMiddleware middleware
217
197
  // After login redirect to "/home"
218
- app.get('/loginMiddleware', keycloackAdapter.loginMiddleware("/home") ,(req, res) => {
198
+ app.get('/loginMiddleware', keycloakInstance.loginMiddleware("/home") ,(req, res) => {
219
199
  // Response handled by middleware, this section will never be reached.
220
200
  });
221
201
 
222
- // Example of logout with keycloackAdapter.logout function
202
+ // Example of logout with keycloakInstance.logout function
223
203
  // After login redirect to "http://localhost:3001/home"
224
204
  app.get('/logout', (req, res) => {
225
205
  console.log("Your Custom Code");
226
- keycloackAdapter.logout(req,res,"http://localhost:3001/home");
206
+ keycloakInstance.logout(req,res,"http://localhost:3001/home");
227
207
  });
228
208
 
229
- // Example of logout with keycloackAdapter.logoutMiddleware middleware
209
+ // Example of logout with keycloakInstance.logoutMiddleware middleware
230
210
  // After login redirect to "http://localhost:3001/home"
231
- app.get('/logoutMiddle', keycloackAdapter.logoutMiddleware("http://redirctUrl"), (req, res) => {
211
+ app.get('/logoutMiddle', keycloakInstance.logoutMiddleware("http://redirctUrl"), (req, res) => {
232
212
  // Response handled by middleware, this section will never be reached.
233
213
  });
234
214
 
235
215
 
236
- // Example of protection with keycloackAdapter.protectMiddleware middleware
216
+ // Example of protection with keycloakInstance.protectMiddleware middleware
237
217
  // Access is allowed only for authenticated users
238
- app.get('/private', keycloackAdapter.protectMiddleware(), (req, res) => {
218
+ app.get('/private', keycloakInstance.protectMiddleware(), (req, res) => {
239
219
  console.log("Your Custom Code");
240
220
  console.log( req.session);
241
221
  res.redirect('/auth');
242
222
  });
243
223
 
244
- // Example of protection with keycloackAdapter.protectMiddleware middleware
245
- // whith a static client role validation string
224
+ // Example of protection with keycloakInstance.protectMiddleware middleware
225
+ // with a static client role validation string
246
226
  // Access is allowed only for authenticated admin users
247
- app.get('/privateStaticClientRole', keycloackAdapter.protectMiddleware("admin"), (req, res) => {
227
+ app.get('/privateStaticClientRole', keycloakInstance.protectMiddleware("admin"), (req, res) => {
248
228
  // "Your Custom Code"
249
- res.send("Is its admin.");
229
+ res.send("You are an admin.");
250
230
  });
251
231
 
252
- // Example of protection with keycloackAdapter.protectMiddleware middleware
253
- // whith a static realm role validation string
232
+ // Example of protection with keycloakInstance.protectMiddleware middleware
233
+ // with a static realm role validation string
254
234
  // Access is allowed only for authenticated realm admin users
255
- app.get('/privateStaticRealmRole', keycloackAdapter.protectMiddleware("realm:admin"), (req, res) => {
235
+ app.get('/privateStaticRealmRole', keycloakInstance.protectMiddleware("realm:admin"), (req, res) => {
256
236
  // "Your Custom Code"
257
- res.send("Is its admin realm:admin.");
237
+ res.send("You are a realm admin.");
258
238
  });
259
239
 
260
- // Example of protection with keycloackAdapter.protectMiddleware middleware
261
- // whith a static other client role validation string
240
+ // Example of protection with keycloakInstance.protectMiddleware middleware
241
+ // with a static other client role validation string
262
242
  // Access is allowed only for authenticated otherClient admin users
263
- app.get('/privateStaticRealmRole', keycloackAdapter.protectMiddleware("otherClient:admin"), (req, res) => {
243
+ app.get('/privateStaticRealmRole', keycloakInstance.protectMiddleware("otherClient:admin"), (req, res) => {
264
244
  // "Your Custom Code"
265
- res.send("Is its admin otherClient:admin.");
245
+ res.send("You are an admin of otherClient.");
266
246
  });
267
247
 
268
- // Example of protection with keycloackAdapter.protectMiddleware middleware
269
- // whith a control function tmpFunction
248
+ // Example of protection with keycloakInstance.protectMiddleware middleware
249
+ // with a control function tmpFunction
270
250
  // Access is allowed only for authenticated admin users
271
251
  let tmpFunction=function (token, req) {
272
252
  return token.hasRole('admin');
273
253
  }
274
- app.get('/isAdmin', keycloackAdapter.protectMiddleware(tmpFunction), (req, res) => {
254
+ app.get('/isAdmin', keycloakInstance.protectMiddleware(tmpFunction), (req, res) => {
275
255
  // "Your Custom Code"
276
- res.send("Is its admin tmpFunction.");
256
+ res.send("You are an admin (verified by tmpFunction).");
277
257
  });
278
258
 
279
259
 
280
- // Example of protection with keycloackAdapter.customProtectMiddleware middleware
281
- // whith a control function tmpFunctionString
260
+ // Example of protection with keycloakInstance.customProtectMiddleware middleware
261
+ // with a control function tmpFunctionString
282
262
  // Access is allowed only for authenticated users with role defined by tmpFunctionString
283
263
  let tmpFunctionString=function (req,res) {
284
264
  let id=req.params.id
285
265
  // Control String by url param Id
286
266
  return (`${id}`);
287
267
  }
288
- app.get('/:id/isAdmin', keycloackAdapter.customProtectMiddleware(tmpFunctionString), (req, res) => {
268
+ app.get('/:id/isAdmin', keycloakInstance.customProtectMiddleware(tmpFunctionString), (req, res) => {
289
269
  // "Your Custom Code"
290
- res.send("Is its admin tmpFunctionString.");
270
+ res.send("You are an admin (verified by tmpFunctionString).");
291
271
  });
292
272
 
293
273
 
294
- // Example of protection with keycloackAdapter.encodeTokenRole middleware
274
+ // Example of protection with keycloakInstance.encodeTokenRole middleware
295
275
  // Encode the token and add it to req.encodedTokenRole
296
276
  // Use req.encodedTokenRole.hasRole("role") to check whether the token has that role or not
297
- app.get('/encodeToken', keycloackAdapter.encodeTokenRole(), (req, res) => {
277
+ app.get('/encodeToken', keycloakInstance.encodeTokenRole(), (req, res) => {
298
278
  if(req.encodedTokenRole.hasRole('realm:admin'))
299
- res.send("Is its a realm admin");
279
+ res.send("You are a realm admin");
300
280
  else
301
- res.send("Is its'n a realm admin");
281
+ res.send("You are not a realm admin");
302
282
 
303
283
  });
304
284
 
@@ -309,18 +289,18 @@ app.get('/encodeToken', keycloackAdapter.encodeTokenRole(), (req, res) => {
309
289
  // #####################################################################################
310
290
 
311
291
 
312
- // Example of protection with keycloackAdapter.enforcerMiddleware middleware
313
- // whith a static control string
292
+ // Example of protection with keycloakInstance.enforcerMiddleware middleware
293
+ // with a static control string
314
294
  // Access is allowed only for users with 'ui-admin-resource' permission defined
315
295
  // in keycloak
316
- app.get('/adminResource', keycloackAdapter.enforcerMiddleware('ui-admin-resource'), (req, res) => {
296
+ app.get('/adminResource', keycloakInstance.enforcerMiddleware('ui-admin-resource'), (req, res) => {
317
297
  // If this section is reached, the user has the required privileges;
318
298
  // otherwise, the middleware responds with a 403 Access Denied.
319
299
  res.send('You are an authorized ui-admin-resource User');
320
300
  });
321
301
 
322
- // Example of protection with keycloackAdapter.enforcerMiddleware middleware
323
- // whith a control function tmpFunctionEnforceValidation
302
+ // Example of protection with keycloakInstance.enforcerMiddleware middleware
303
+ // with a control function tmpFunctionEnforceValidation
324
304
  // Access is allowed only for users with 'ui-admin-resource' or
325
305
  // ui-viewer-resource permission defined in keycloak
326
306
  let tmpFunctionEnforceValidation=function (token,req,callback) {
@@ -335,7 +315,7 @@ let tmpFunctionEnforceValidation=function (token,req,callback) {
335
315
  }));
336
316
  }));
337
317
  }
338
- app.get('/adminOrViewerResorce', keycloackAdapter.enforcerMiddleware(tmpFunctionEnforceValidation), (req, res) => {
318
+ app.get('/adminOrViewerResorce', keycloakInstance.enforcerMiddleware(tmpFunctionEnforceValidation), (req, res) => {
339
319
  // If this section is reached, the user has the required privileges
340
320
  // driven by tmpFunctionEnforceValidation; otherwise, the middleware responds
341
321
  // with a 403 Access Denied.
@@ -343,27 +323,27 @@ app.get('/adminOrViewerResorce', keycloackAdapter.enforcerMiddleware(tmpFunction
343
323
  });
344
324
 
345
325
 
346
- // Example of protection with keycloackAdapter.customEnforcerMiddleware middleware
347
- // whith a control function tmpFunctionEnforce that define the control string
326
+ // Example of protection with keycloakInstance.customEnforcerMiddleware middleware
327
+ // with a control function tmpFunctionEnforce that define the control string
348
328
  // Access is allowed only for users with a url params ':permission' permission defined
349
329
  // in keycloak
350
330
  let tmpFunctionEnforce=function (req,res) {
351
331
  // Permission that depends on a URL parameter.
352
332
  return(req.params.permission);
353
333
  }
354
- app.get('/urlParameterPermission/:permission', keycloackAdapter.customEnforcerMiddleware(tmpFunctionEnforce), (req, res) => {
334
+ app.get('/urlParameterPermission/:permission', keycloakInstance.customEnforcerMiddleware(tmpFunctionEnforce), (req, res) => {
355
335
  res.send(`You are an authorized User with ${req.params.permission} permission`);
356
336
  });
357
337
 
358
- // Example of protection with keycloackAdapter.encodeTokenPermission middleware
359
- // Encode the token permission and add it to req.encodedTokenPremission
360
- // Use req.encodedTokenPremission.hasPermission("permission") to check whether
338
+ // Example of protection with keycloakInstance.encodeTokenPermission middleware
339
+ // Encode the token permission and add it to req.encodedTokenPermission
340
+ // Use req.encodedTokenPermission.hasPermission("permission") to check whether
361
341
  // the token has that permission or not
362
- app.get('/encodeTokenPermission', keycloackAdapter.encodeTokenPermission(), (req, res) => {
342
+ app.get('/encodeTokenPermission', keycloakInstance.encodeTokenPermission(), (req, res) => {
363
343
  // Check permission using token.hasPermission, which performs the verification
364
344
  // and responds with a callback that returns true if the permission is valid,
365
345
  // and false otherwise.
366
- req.encodedTokenPremission.hasPermission('ui-admin-resource', function(permission){
346
+ req.encodedTokenPermission.hasPermission('ui-admin-resource', function(permission){
367
347
  if(permission)
368
348
  res.send('You are an authorized User by ui-admin-resource permission');
369
349
  else res.status(403).send("access Denied");
@@ -395,24 +375,60 @@ a login or error page.
395
375
  ### Example 1 — Custom Access Denied Page
396
376
 
397
377
  ```js
398
- import responseinterceptor from 'responseinterceptor';
399
- import keycloakMiddleware from 'keycloak-express-middleware';
378
+ const responseinterceptor = require('responseinterceptor');
379
+ const keycloackAdapter = require('keycloak-express-middleware');
380
+
381
+ const app = express();
382
+ const keycloakInstance = new keycloackAdapter(app, keyCloakConfig, keyCloakOptions);
400
383
 
401
384
 
402
385
  function tmpInterceptor(req, respond) {
403
- // Handling Unauthorized Access (401/403) Gracefully
404
- respond(200, '<h1>Access Denied</h1><p>You are not authorized to view this page.</p>');
386
+ /**
387
+ * Gracefully handles unauthorized access (401/403).
388
+ *
389
+ * This interceptor is executed when a protected route returns
390
+ * a forbidden status code. Instead of letting the browser show
391
+ * a blank page with the text "access_denied", it renders a
392
+ * user-friendly "access-denied" view.
393
+ *
394
+ * How it works:
395
+ * - Uses `req.app.render()` to generate HTML from the EJS template
396
+ * without sending it directly to the client.
397
+ * - If rendering succeeds, the generated HTML is passed to `respond()`,
398
+ * which replaces the original 403 response body with our custom page.
399
+ * - If rendering fails, a fallback HTML message is provided.
400
+ */
401
+
402
+ req.app.render('access-denied', {}, (err, html) => {
403
+ if (!err) {
404
+ // Successfully rendered the template → return the generated HTML
405
+ respond(200, html);
406
+ } else {
407
+ // Fallback: template error → send a simple HTML message instead
408
+ respond(
409
+ 200,
410
+ '<h1>Access Denied</h1><p>You are not authorized to view this page.</p>'
411
+ );
412
+ }
413
+ });
405
414
  }
406
415
 
407
- // if protectMiddleware('role') return a 403 with keycloak blank page then
408
- // interceptByStatusCode Handle Unauthorized Access (401/403) Gracefully
416
+ // Route example showing how to gracefully handle 403 responses produced by Keycloak
417
+ //
418
+ // If `protectMiddleware('role')` denies access, Keycloak normally returns a
419
+ // plain "access_denied" message on a blank page.
420
+ //
421
+ // By placing `interceptByStatusCode(403, tmpInterceptor)` BEFORE the protectMiddleware,
422
+ // we intercept the 403 response generated by Keycloak and replace it with a
423
+ // custom HTML page (e.g. an EJS template) instead of the default blank output.
424
+
409
425
  app.get(
410
- '/test403',
411
- responseinterceptor.interceptByStatusCode(403, tmpInterceptor),
412
- keycloakMiddleware.protectMiddleware('role'),
413
- (req, res) => {
414
- res.render('welcome');
415
- }
426
+ '/test403',
427
+ responseinterceptor.interceptByStatusCode(403, tmpInterceptor),
428
+ keycloakInstance.protectMiddleware('role'),
429
+ (req, res) => {
430
+ res.render('welcome');
431
+ }
416
432
  );
417
433
  ```
418
434
 
@@ -420,58 +436,91 @@ app.get(
420
436
 
421
437
  ```js
422
438
  function tmpInterceptorDinamic(req, respond) {
423
- //your log
424
- switch (req.path) {
425
- case '/':
426
- respond('/access-denied');
427
- break
428
- case '/help':
429
- respond('/access-denied-help');
430
- break
431
- default:
432
- respond('/access-denied-default');
433
- }
439
+ /**
440
+ * Dynamic Redirect Interceptor
441
+ *
442
+ * This function decides dynamically where the user should be redirected
443
+ * after a 403 Unauthorized response is intercepted.
444
+ *
445
+ * - `req` → the original Express request
446
+ * - `respond` → helper function that receives the final redirect route
447
+ *
448
+ * Based on the current request path, we redirect the user to different
449
+ * "access denied" pages.
450
+ */
451
+ switch (req.path) {
452
+ case '/':
453
+ respond('/access-denied');
454
+ break;
455
+
456
+ case '/help':
457
+ respond('/access-denied-help');
458
+ break;
459
+
460
+ default:
461
+ respond('/access-denied-default');
462
+ }
434
463
  }
435
464
 
465
+ // Dedicated "Access Denied" pages
436
466
  app.get('/access-denied', (req, res) => {
437
- res.render('access-denied');
467
+ res.render('access-denied');
438
468
  });
439
469
 
440
- app.get('/access-denied', (req, res) => {
470
+ app.get('/access-denied-help', (req, res) => {
441
471
  res.render('access-denied-help');
442
472
  });
443
473
 
444
- app.get('/access-denied', (req, res) => {
474
+ app.get('/access-denied-default', (req, res) => {
445
475
  res.render('access-denied-default');
446
476
  });
447
477
 
448
- // if protectMiddleware('role') return a 403 with keycloak blank page then
449
- // interceptByStatusCode Handle Unauthorized Access (401/403) Gracefully
450
- // by user redirection with tmpInterceptorDinamic logic
478
+ // -----------------------------------------------------------------------
479
+ // Example: dynamic redirection after Keycloak denies access (403)
480
+ // -----------------------------------------------------------------------
481
+ //
482
+ // If protectMiddleware('none') triggers a 403 (Keycloak default behavior),
483
+ // the `interceptByStatusCodeRedirectTo` middleware intercepts Keycloak’s
484
+ // blank "access_denied" page and replaces it with a redirect determined
485
+ // by tmpInterceptorDinamic().
486
+ //
487
+ // This allows:
488
+ //
489
+ // ✓ No more blank browser page with "access_denied"
490
+ // ✓ User-friendly redirection to custom EJS pages
491
+ // ✓ Dynamic routing logic based on the original request
492
+ //
451
493
  app.get(
452
- '/test403redirectDynamic',
453
- responseinterceptor.interceptByStatusCodeRedirectTo(403, tmpInterceptorDinamic),
454
- keycloakMiddleware.protectMiddleware('none'),
455
- (req, res) => {
456
- res.render('welcome');
457
- }
494
+ '/test403redirectDynamic',
495
+ responseinterceptor.interceptByStatusCodeRedirectTo(403, tmpInterceptorDinamic),
496
+ keycloakInstance.protectMiddleware('none'),
497
+ (req, res) => {
498
+ res.render('welcome');
499
+ }
458
500
  );
459
501
  ```
460
502
 
461
503
  ### Example 3 — Static Redirect to a Route
462
504
 
463
505
  ```js
464
- // if protectMiddleware('role') return a 403 with keycloak blank page then
465
- // interceptByStatusCode Handle Unauthorized Access (401/403) Gracefully
466
- // by user redirection
506
+ // If protectMiddleware('role') triggers a 403 (forbidden) and Keycloak returns
507
+ // the default blank 403 page, we use interceptByStatusCodeRedirectTo()
508
+ // to gracefully handle the unauthorized response.
509
+ //
510
+ // When a 403 is detected, the interceptor forces an HTTP redirect to the
511
+ // custom '/access-denied' route, allowing us to show a friendly UI instead
512
+ // of Keycloak’s default error page.
513
+ //
514
+ // This ensures consistent UX and keeps request flow under our control.
467
515
  app.get(
468
- '/test403redirectStatic',
469
- responseinterceptor.interceptByStatusCodeRedirectTo(403, '/access-denied'),
470
- keycloakMiddleware.protectMiddleware('none'),
471
- (req, res) => {
472
- res.render('welcome');
473
- }
516
+ '/test403redirectStatic',
517
+ responseinterceptor.interceptByStatusCodeRedirectTo(403, '/access-denied'),
518
+ keycloakInstance.protectMiddleware('none'),
519
+ (req, res) => {
520
+ res.render('welcome');
521
+ }
474
522
  );
523
+
475
524
  ```
476
525
 
477
526
  ### Summary
@@ -489,10 +538,10 @@ app.get(
489
538
  ## 🧩 Configuration
490
539
  In your Express application:
491
540
  ```js
492
- import keycloakAdapterClass from 'keycloak-express-middleware';
541
+ const keycloackAdapter = require('keycloak-express-middleware');
493
542
 
494
543
  // Configure and Initialize Keycloak adapter
495
- keycloackAdapter=new keycloakAdapterClass(app,{
544
+ const keycloakInstance = new keycloackAdapter(app,{
496
545
  "realm": "Realm-Project",
497
546
  "auth-server-url": "https://YourKeycloakUrl:30040/",
498
547
  "ssl-required": "external",
@@ -508,9 +557,9 @@ keycloackAdapter=new keycloakAdapterClass(app,{
508
557
  }
509
558
  })
510
559
  ```
511
- `keycloak-express-middleware constructor` instantiate and configure the object for the Keycloak
512
- adapter in an Express application. It must be called at app startup, before defining any protected routes.
513
- It is an async function and returns a promise
560
+ `keycloak-express-middleware constructor` instantiates and configures the Keycloak
561
+ adapter for an Express application. It must be called at app startup, before defining any protected routes.
562
+ The constructor is synchronous and returns the configured instance immediately.
514
563
 
515
564
  **` -- @parameters -- `**
516
565
  - **app**: `[required]` Express application instance (e.g., const app = express();) or express router (e.g., var router = express.Router();)
@@ -536,58 +585,24 @@ It is an async function and returns a promise
536
585
  - **idpHint:** to suggest an identity provider to Keycloak during login
537
586
  - **cookies:** to enable cookie handling
538
587
  - **realmUrl:** to override the realm URL
539
- ---
540
- ## 🔧 Available Middlewares
541
- ### `underKeycloakProtection(callback) - deprecated - `
542
- **@deprecated Method**. Use the `configure` Method with **`await keycloakAdapter.configure({..})`**, then define your resources as you normally would in Express:
543
- ```js
544
- await keycloakAdapter.configure(config_Parameters);
545
-
546
- // Define all your routes here
547
-
548
- app.get('/my-route', handler);
549
- ```
550
- Alternatively, if you prefer to define your resources inside a container after configuration, you can use the `then` syntax:
551
- ```js
552
- keycloakAdapter.configure(configParameters).then(() => {
553
- // Define all your routes to protect here
554
- app.get('/my-route', handler);
555
- });
556
- ```
557
- This Method is deprecated and will be removed in future versions. It must be called **after** Keycloak has been configured with `configure()`.
558
- The routes declared inside the provided callback will be protected and will have access to authentication/authorization features managed by Keycloak.
559
588
 
560
- 📌 Public (unprotected) routes should be declared **before** calling this method.
589
+ ### Import Alternatives
561
590
 
562
- **` -- @parameters -- `**
563
- - **{Function} callback:** `[required]` A function that defines all routes to be protected. It must contain exclusively routes requiring authentication.
591
+ While the examples use CommonJS (`require`), the library also supports ES6 module syntax:
564
592
 
565
- ✅ Usage example:
566
593
  ```js
567
- // Public route not protected by Keycloak
568
- app.get('/public', (req, res) => {
569
- res.send('Public content');
570
- });
571
-
572
- // Section of routes protected by Keycloak
573
- keycloakAdapter.underKeycloakProtection(() => {
594
+ // CommonJS (Default)
595
+ const keycloackAdapter = require('keycloak-express-middleware');
574
596
 
575
- // This function is deprecated and will be removed in future versions.
576
- // It is retained only for backward compatibility with older versions
577
-
578
- // Route protected by authentication
579
- app.get('/confidential', keycloakAdapter.protectMiddleware(), (req, res) => {
580
- res.send('Confidential content visible only to authenticated users');
581
- });
597
+ // ES6 - Named import (recommended for clarity)
598
+ import { keycloackAdapter } from 'keycloak-express-middleware';
582
599
 
583
- // Route with forced login: handled directly by middleware
584
- app.get('/loginMiddleware', keycloakAdapter.loginMiddleware("/home"), (req, res) => {
585
- // This response will never be sent because the middleware handles the
586
- // request directly
587
- });
588
- });
600
+ // ES6 - Default import
601
+ import keycloackAdapter from 'keycloak-express-middleware';
589
602
  ```
603
+
590
604
  ---
605
+ ## 🔧 Available Middlewares
591
606
  ### `protectMiddleware([conditions])`
592
607
  Middleware to protect Express routes based on authentication and, optionally, authorization via Keycloak roles.
593
608
  Allows restricting access to a resource only to authenticated users or to those possessing specific roles in the realm or in a Keycloak client.
@@ -963,7 +978,7 @@ After successful login, the user is redirected to the URL specified in the `redi
963
978
  - **redirectTo:** `[required]` URL to redirect the user to after successful login
964
979
 
965
980
  --- Behavior ---
966
- 1. Attempts to protect the request using `keycloak.protect()`.
981
+ 1. Attempts to protect the request using `protectMiddleware()`.
967
982
  2. If the user **is authenticated**, it performs `res.redirect(redirectTo)`.
968
983
  3. If **not authenticated**, Keycloak automatically handles redirection to the login page.
969
984
 
package/index.js CHANGED
@@ -838,7 +838,7 @@ class keycloakExpressMiddleware {
838
838
  * --- Aggiunte a `req` ---
839
839
  * Dopo l'applicazione del middleware, `req` contiene:
840
840
  *
841
- * @property {Object} req.encodedTokenPremission
841
+ * @property {Object} req.encodedTokenPermission
842
842
  * Un oggetto che espone il metodo:
843
843
  *
844
844
  * - `hasPermission(permission: string, callback: function(boolean))`
@@ -851,7 +851,7 @@ class keycloakExpressMiddleware {
851
851
  * app.get('/encodeTokenPermission',
852
852
  * keycloakAdapter.encodeTokenPermission(),
853
853
  * (req, res) => {
854
- * req.encodedTokenPremission.hasPermission('ui-admin-resource', function(perm) {
854
+ * req.encodedTokenPermission.hasPermission('ui-admin-resource', function(perm) {
855
855
  * if (perm)
856
856
  * res.send('You are an authorized admin User by function permission parameters');
857
857
  * else
@@ -907,7 +907,7 @@ class keycloakExpressMiddleware {
907
907
  encodeTokenPermission(){
908
908
  const self = this;
909
909
  return(function (req,res,next){
910
- req.encodedTokenPremission={
910
+ req.encodedTokenPermission={
911
911
  "hasPermission":function(permission,callback){
912
912
  self.#encodeTokenPermissionHandler(permission,req,res,callback);
913
913
  }
@@ -1286,6 +1286,8 @@ class keycloakExpressMiddleware {
1286
1286
 
1287
1287
 
1288
1288
  module.exports = keycloakExpressMiddleware;
1289
+ module.exports.keycloackAdapter = keycloakExpressMiddleware; // Named export for backward compatibility and ES6 support
1290
+ module.exports.default = keycloakExpressMiddleware; // Default export for ES6 modules
1289
1291
 
1290
1292
  /*
1291
1293
  <table><tbody>
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "keycloak-express-middleware",
3
- "version": "6.0.1",
3
+ "version": "6.0.3",
4
4
  "description": "Adapter API to integrate Node.js (Express) applications with Keycloak. Provides middleware for authentication, authorization, token validation, and route protection via OpenID Connect.",
5
5
  "main": "index.js",
6
6
  "scripts": {