ui5-lib-guard-router 1.5.0 → 1.5.1

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.
@@ -16,7 +16,7 @@
16
16
  },
17
17
  "buildManifest": {
18
18
  "manifestVersion": "0.2",
19
- "timestamp": "2026-03-23T12:27:04.576Z",
19
+ "timestamp": "2026-03-23T15:59:01.881Z",
20
20
  "versions": {
21
21
  "builderVersion": "4.1.4",
22
22
  "projectVersion": "4.0.13",
@@ -31,7 +31,7 @@
31
31
  "includedTasks": [],
32
32
  "excludedTasks": []
33
33
  },
34
- "version": "1.5.0",
34
+ "version": "1.5.1",
35
35
  "namespace": "ui5/guard/router",
36
36
  "tags": {
37
37
  "/resources/ui5/guard/router/GuardPipeline-dbg.js": {
package/dist/index.d.ts CHANGED
@@ -32,8 +32,8 @@
32
32
  // - @types/istanbul-lib-report@3.0.3
33
33
  // - @types/istanbul-lib-coverage@2.0.6
34
34
  // - @types/qunit@2.19.13
35
- /// <reference path="./resources/ui5/guard/router/NavigationOutcome.d.ts"/>
36
35
  /// <reference path="./resources/ui5/guard/router/library.d.ts"/>
37
36
  /// <reference path="./resources/ui5/guard/router/Router.d.ts"/>
38
- /// <reference path="./resources/ui5/guard/router/GuardPipeline.d.ts"/>
39
- /// <reference path="./resources/ui5/guard/router/types.d.ts"/>
37
+ /// <reference path="./resources/ui5/guard/router/types.d.ts"/>
38
+ /// <reference path="./resources/ui5/guard/router/NavigationOutcome.d.ts"/>
39
+ /// <reference path="./resources/ui5/guard/router/GuardPipeline.d.ts"/>
@@ -2,7 +2,7 @@
2
2
  <library xmlns="http://www.sap.com/sap.ui.library.xsd">
3
3
  <name>ui5.guard.router</name>
4
4
  <vendor>Marco</vendor>
5
- <version>1.5.0</version>
5
+ <version>1.5.1</version>
6
6
  <copyright></copyright>
7
7
  <title>UI5 Router extension with async navigation guards</title>
8
8
  <documentation>Extends sap.m.routing.Router with async navigation guards, running before route matching begins.</documentation>
@@ -84,6 +84,11 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
84
84
  exportKey
85
85
  };
86
86
  }
87
+ /** Log a warning about a guard module entry in the manifest. */
88
+ function guardWarning(modulePath, detail) {
89
+ Log.warning(`guardRouter.guards: "${modulePath}" ${detail}`, undefined, LOG_COMPONENT);
90
+ }
91
+
87
92
  /**
88
93
  * Detect the export shape of a loaded guard module and extract guard functions.
89
94
  *
@@ -101,7 +106,7 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
101
106
  // Shape 1: function
102
107
  if (typeof moduleExport === "function") {
103
108
  if (exportKey !== undefined) {
104
- Log.debug(`guardRouter.guards: "${modulePath}#${exportKey}" exports a single function, ignoring export key`, undefined, LOG_COMPONENT);
109
+ Log.debug(`guardRouter.guards: "${modulePath}#${exportKey}" is a single function, ignoring export key`, undefined, LOG_COMPONENT);
105
110
  }
106
111
  return [{
107
112
  name: descriptorName,
@@ -112,18 +117,18 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
112
117
  // Shape 2: array
113
118
  if (Array.isArray(moduleExport)) {
114
119
  if (moduleExport.length === 0) {
115
- Log.warning(`guardRouter.guards: module "${modulePath}" exported an empty array, skipping`, undefined, LOG_COMPONENT);
120
+ guardWarning(modulePath, "exported an empty array, skipping");
116
121
  return [];
117
122
  }
118
123
  if (exportKey !== undefined) {
119
124
  const index = parseInt(exportKey, 10);
120
125
  if (Number.isNaN(index) || index < 0 || index >= moduleExport.length) {
121
- Log.warning(`guardRouter.guards: "${modulePath}#${exportKey}" - index out of range or invalid, skipping`, undefined, LOG_COMPONENT);
126
+ guardWarning(modulePath, `#${exportKey} - index out of range, skipping`);
122
127
  return [];
123
128
  }
124
129
  const entry = moduleExport[index];
125
130
  if (typeof entry !== "function") {
126
- Log.warning(`guardRouter.guards: "${modulePath}#${exportKey}" is not a function, skipping`, undefined, LOG_COMPONENT);
131
+ guardWarning(modulePath, `#${exportKey} is not a function, skipping`);
127
132
  return [];
128
133
  }
129
134
  return [{
@@ -135,7 +140,7 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
135
140
  for (let i = 0; i < moduleExport.length; i++) {
136
141
  const entry = moduleExport[i];
137
142
  if (typeof entry !== "function") {
138
- Log.warning(`guardRouter.guards: "${modulePath}"[${i}] is not a function, skipping`, undefined, LOG_COMPONENT);
143
+ guardWarning(modulePath, `[${i}] is not a function, skipping`);
139
144
  continue;
140
145
  }
141
146
  results.push({
@@ -150,7 +155,7 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
150
155
  if (isRecord(moduleExport)) {
151
156
  const entries = Object.entries(moduleExport);
152
157
  if (entries.length === 0) {
153
- Log.warning(`guardRouter.guards: module "${modulePath}" exported an empty object, skipping`, undefined, LOG_COMPONENT);
158
+ guardWarning(modulePath, "exported an empty object, skipping");
154
159
  return [];
155
160
  }
156
161
  if (exportKey !== undefined) {
@@ -165,11 +170,11 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
165
170
  }
166
171
  }
167
172
  if (value === undefined) {
168
- Log.warning(`guardRouter.guards: "${modulePath}#${exportKey}" - key not found, skipping`, undefined, LOG_COMPONENT);
173
+ guardWarning(modulePath, `#${exportKey} - key not found, skipping`);
169
174
  return [];
170
175
  }
171
176
  if (typeof value !== "function") {
172
- Log.warning(`guardRouter.guards: "${modulePath}#${exportKey}" is not a function, skipping`, undefined, LOG_COMPONENT);
177
+ guardWarning(modulePath, `#${exportKey} is not a function, skipping`);
173
178
  return [];
174
179
  }
175
180
  return [{
@@ -180,7 +185,7 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
180
185
  const results = [];
181
186
  for (const [key, value] of entries) {
182
187
  if (typeof value !== "function") {
183
- Log.warning(`guardRouter.guards: "${modulePath}".${key} is not a function, skipping`, undefined, LOG_COMPONENT);
188
+ guardWarning(modulePath, `.${key} is not a function, skipping`);
184
189
  continue;
185
190
  }
186
191
  results.push({
@@ -190,7 +195,7 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
190
195
  }
191
196
  return results;
192
197
  }
193
- Log.warning(`guardRouter.guards: module "${modulePath}" did not export a function, array, or plain object, skipping`, undefined, LOG_COMPONENT);
198
+ guardWarning(modulePath, "did not export a function, array, or plain object, skipping");
194
199
  return [];
195
200
  }
196
201
 
@@ -389,7 +394,7 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
389
394
  */
390
395
  addGuard: function _addGuard(guard) {
391
396
  if (typeof guard !== "function") {
392
- Log.warning("addGuard called with invalid guard, ignoring", undefined, LOG_COMPONENT);
397
+ Log.warning("addGuard: not a function, ignoring", undefined, LOG_COMPONENT);
393
398
  return this;
394
399
  }
395
400
  this._pipeline.addGlobalGuard(guard);
@@ -403,7 +408,7 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
403
408
  */
404
409
  removeGuard: function _removeGuard(guard) {
405
410
  if (typeof guard !== "function") {
406
- Log.warning("removeGuard called with invalid guard, ignoring", undefined, LOG_COMPONENT);
411
+ Log.warning("removeGuard: not a function, ignoring", undefined, LOG_COMPONENT);
407
412
  return this;
408
413
  }
409
414
  this._pipeline.removeGlobalGuard(guard);
@@ -428,7 +433,7 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
428
433
  if (guard.beforeEnter !== undefined) {
429
434
  hasHandler = true;
430
435
  if (typeof guard.beforeEnter !== "function") {
431
- Log.warning("addRouteGuard called with invalid guard, ignoring", routeName, LOG_COMPONENT);
436
+ Log.warning("addRouteGuard: not a function, ignoring", routeName, LOG_COMPONENT);
432
437
  } else {
433
438
  this._pipeline.addEnterGuard(routeName, guard.beforeEnter);
434
439
  }
@@ -436,19 +441,19 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
436
441
  if (guard.beforeLeave !== undefined) {
437
442
  hasHandler = true;
438
443
  if (typeof guard.beforeLeave !== "function") {
439
- Log.warning("addRouteGuard called with invalid guard, ignoring", routeName, LOG_COMPONENT);
444
+ Log.warning("addRouteGuard: not a function, ignoring", routeName, LOG_COMPONENT);
440
445
  } else {
441
446
  this._pipeline.addLeaveGuard(routeName, guard.beforeLeave);
442
447
  }
443
448
  }
444
449
  if (!hasHandler) {
445
- Log.info("addRouteGuard called with config missing both beforeEnter and beforeLeave", routeName, LOG_COMPONENT);
450
+ Log.info("addRouteGuard: config has no beforeEnter or beforeLeave", routeName, LOG_COMPONENT);
446
451
  return this;
447
452
  }
448
453
  return this;
449
454
  }
450
455
  if (typeof guard !== "function") {
451
- Log.warning("addRouteGuard called with invalid guard, ignoring", routeName, LOG_COMPONENT);
456
+ Log.warning("addRouteGuard: not a function, ignoring", routeName, LOG_COMPONENT);
452
457
  return this;
453
458
  }
454
459
  if (!this._handleUnknownRouteRegistration(routeName, "addRouteGuard")) {
@@ -479,7 +484,7 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
479
484
  return this;
480
485
  }
481
486
  if (typeof guard !== "function") {
482
- Log.warning("removeRouteGuard called with invalid guard, ignoring", routeName, LOG_COMPONENT);
487
+ Log.warning("removeRouteGuard: not a function, ignoring", routeName, LOG_COMPONENT);
483
488
  return this;
484
489
  }
485
490
  this._pipeline.removeEnterGuard(routeName, guard);
@@ -498,7 +503,7 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
498
503
  */
499
504
  addLeaveGuard: function _addLeaveGuard(routeName, guard) {
500
505
  if (typeof guard !== "function") {
501
- Log.warning("addLeaveGuard called with invalid guard, ignoring", routeName, LOG_COMPONENT);
506
+ Log.warning("addLeaveGuard: not a function, ignoring", routeName, LOG_COMPONENT);
502
507
  return this;
503
508
  }
504
509
  if (!this._handleUnknownRouteRegistration(routeName, "addLeaveGuard")) {
@@ -520,7 +525,7 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
520
525
  throw new Error(`${methodName} called for unknown route "${routeName}". ` + `Set guardRouter.unknownRouteGuardRegistration to "warn" or "ignore" to allow this.`);
521
526
  case "warn":
522
527
  default:
523
- Log.warning(`${methodName} called for unknown route; guard will still register. ` + `If the route is added later via addRoute(), this warning can be ignored.`, routeName, LOG_COMPONENT);
528
+ Log.warning(`${methodName}: unknown route, guard registered anyway`, routeName, LOG_COMPONENT);
524
529
  return true;
525
530
  }
526
531
  },
@@ -533,7 +538,7 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
533
538
  */
534
539
  removeLeaveGuard: function _removeLeaveGuard(routeName, guard) {
535
540
  if (typeof guard !== "function") {
536
- Log.warning("removeLeaveGuard called with invalid guard, ignoring", routeName, LOG_COMPONENT);
541
+ Log.warning("removeLeaveGuard: not a function, ignoring", routeName, LOG_COMPONENT);
537
542
  return this;
538
543
  }
539
544
  this._pipeline.removeLeaveGuard(routeName, guard);
@@ -682,15 +687,7 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
682
687
  generation
683
688
  }
684
689
  };
685
- const context = {
686
- toRoute,
687
- toHash: targetHash,
688
- toArguments: routeInfo?.arguments ?? {},
689
- fromRoute: this._currentRoute,
690
- fromHash: this._currentHash ?? "",
691
- signal: controller.signal,
692
- bag: new Map()
693
- };
690
+ const context = this._createGuardContext(toRoute, targetHash, routeInfo, controller.signal);
694
691
  const decision = this._pipeline.evaluate(context);
695
692
  if (isPromiseLike(decision)) {
696
693
  decision.then(d => {
@@ -749,25 +746,8 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
749
746
  this._blockNavigation(targetHash, false);
750
747
  break;
751
748
  case "redirect":
752
- {
753
- // Safe: sync path sets phase to evaluating; async .then() checks kind before calling here.
754
- const {
755
- attempt
756
- } = this._phase;
757
- const visited = new Set();
758
- visited.add(targetHash);
759
- this._redirect(decision.target, {
760
- visited,
761
- attemptedHash: targetHash,
762
- restoreHash: false,
763
- fromRoute: this._currentRoute,
764
- fromHash: this._currentHash ?? "",
765
- signal: attempt.controller.signal,
766
- generation: attempt.generation,
767
- bag
768
- });
769
- break;
770
- }
749
+ this._startRedirectChain(decision.target, targetHash, false, bag);
750
+ break;
771
751
  case "error":
772
752
  this._errorNavigation(decision.error, targetHash, false);
773
753
  break;
@@ -815,15 +795,7 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
815
795
  generation
816
796
  }
817
797
  };
818
- const context = {
819
- toRoute,
820
- toHash: newHash,
821
- toArguments: routeInfo?.arguments ?? {},
822
- fromRoute: this._currentRoute,
823
- fromHash: this._currentHash ?? "",
824
- signal: controller.signal,
825
- bag: new Map()
826
- };
798
+ const context = this._createGuardContext(toRoute, newHash, routeInfo, controller.signal);
827
799
  const decision = this._pipeline.evaluate(context);
828
800
  if (isPromiseLike(decision)) {
829
801
  decision.then(d => {
@@ -899,25 +871,8 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
899
871
  this._blockNavigation(hash);
900
872
  break;
901
873
  case "redirect":
902
- {
903
- // Safe: sync path sets phase to evaluating; async .then() checks kind before calling here.
904
- const {
905
- attempt
906
- } = this._phase;
907
- const visited = new Set();
908
- visited.add(hash);
909
- this._redirect(decision.target, {
910
- visited,
911
- attemptedHash: hash,
912
- restoreHash: true,
913
- fromRoute: this._currentRoute,
914
- fromHash: this._currentHash ?? "",
915
- signal: attempt.controller.signal,
916
- generation: attempt.generation,
917
- bag
918
- });
919
- break;
920
- }
874
+ this._startRedirectChain(decision.target, hash, true, bag);
875
+ break;
921
876
  case "error":
922
877
  this._errorNavigation(decision.error, hash);
923
878
  break;
@@ -1106,6 +1061,44 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
1106
1061
  break;
1107
1062
  }
1108
1063
  },
1064
+ /**
1065
+ * Build a guard context for a new navigation.
1066
+ * Called by {@link navTo} (preflight path) and {@link parse} (browser-initiated path).
1067
+ */
1068
+ _createGuardContext: function _createGuardContext(toRoute, toHash, routeInfo, signal) {
1069
+ return {
1070
+ toRoute,
1071
+ toHash,
1072
+ toArguments: routeInfo?.arguments ?? {},
1073
+ fromRoute: this._currentRoute,
1074
+ fromHash: this._currentHash ?? "",
1075
+ signal,
1076
+ bag: new Map()
1077
+ };
1078
+ },
1079
+ /**
1080
+ * Start a new redirect chain from the current evaluating phase.
1081
+ * Called by {@link _applyPreflightDecision} and {@link _applyDecision}
1082
+ * when a guard returns a redirect. Delegates to {@link _redirect} with
1083
+ * a fresh {@link RedirectChainContext}.
1084
+ */
1085
+ _startRedirectChain: function _startRedirectChain(target, hash, restoreHash, bag) {
1086
+ const {
1087
+ attempt
1088
+ } = this._phase;
1089
+ const visited = new Set();
1090
+ visited.add(hash);
1091
+ this._redirect(target, {
1092
+ visited,
1093
+ attemptedHash: hash,
1094
+ restoreHash,
1095
+ fromRoute: this._currentRoute,
1096
+ fromHash: this._currentHash ?? "",
1097
+ signal: attempt.controller.signal,
1098
+ generation: attempt.generation,
1099
+ bag
1100
+ });
1101
+ },
1109
1102
  /**
1110
1103
  * Clear pending state and flush a Blocked settlement.
1111
1104
  * When `restoreHash` is true (default), also restores the browser hash
@@ -1123,7 +1116,7 @@ sap.ui.define(["sap/m/routing/Router", "sap/base/Log", "sap/ui/core/library", ".
1123
1116
  },
1124
1117
  /**
1125
1118
  * Clear pending state and flush an Error settlement.
1126
- * Same structure as `_blockNavigation` but with `NavigationOutcome.Error`
1119
+ * Same structure as {@link _blockNavigation} but with `NavigationOutcome.Error`
1127
1120
  * and the error that caused the failure.
1128
1121
  */
1129
1122
  _errorNavigation: function _errorNavigation(error, attemptedHash, restoreHash = true) {