@real-router/core 0.52.0 → 0.53.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 (87) hide show
  1. package/README.md +22 -10
  2. package/dist/cjs/Router-CJihdrWA.d.ts +67 -0
  3. package/dist/cjs/Router-CJihdrWA.d.ts.map +1 -0
  4. package/dist/cjs/Router-DlmLM8Yo.js +6 -0
  5. package/dist/cjs/Router-DlmLM8Yo.js.map +1 -0
  6. package/dist/cjs/RouterError-Bm9YnZ6e.d.ts +310 -0
  7. package/dist/cjs/RouterError-Bm9YnZ6e.d.ts.map +1 -0
  8. package/dist/cjs/api.d.ts +2 -1
  9. package/dist/cjs/api.d.ts.map +1 -1
  10. package/dist/cjs/api.js +1 -1
  11. package/dist/cjs/api.js.map +1 -1
  12. package/dist/cjs/cloneRouter-jNfrYcI_.js +2 -0
  13. package/dist/cjs/cloneRouter-jNfrYcI_.js.map +1 -0
  14. package/dist/cjs/index-8oPDJBQc.d.ts +306 -0
  15. package/dist/cjs/index-8oPDJBQc.d.ts.map +1 -0
  16. package/dist/cjs/{Router-DrBkBdZ5.d.ts → index-EwbhzRQw.d.ts} +4 -69
  17. package/dist/cjs/index-EwbhzRQw.d.ts.map +1 -0
  18. package/dist/cjs/index.d.ts +4 -197
  19. package/dist/cjs/index.d.ts.map +1 -1
  20. package/dist/cjs/index.js +1 -1
  21. package/dist/cjs/index.js.map +1 -1
  22. package/dist/cjs/{internals-na15rxo_.js → internals-CM6oaz9n.js} +1 -1
  23. package/dist/cjs/internals-CM6oaz9n.js.map +1 -0
  24. package/dist/cjs/utils.d.ts +2 -91
  25. package/dist/cjs/utils.js +1 -1
  26. package/dist/cjs/utils.js.map +1 -1
  27. package/dist/cjs/validation.d.ts +55 -44
  28. package/dist/cjs/validation.d.ts.map +1 -1
  29. package/dist/cjs/validation.js +1 -1
  30. package/dist/esm/Router-BmhiDQUJ.d.mts +67 -0
  31. package/dist/esm/Router-BmhiDQUJ.d.mts.map +1 -0
  32. package/dist/esm/Router-DRM2Fd06.mjs +6 -0
  33. package/dist/esm/Router-DRM2Fd06.mjs.map +1 -0
  34. package/dist/esm/RouterError-hhfSVGtY.d.mts +310 -0
  35. package/dist/esm/RouterError-hhfSVGtY.d.mts.map +1 -0
  36. package/dist/esm/api.d.mts +2 -1
  37. package/dist/esm/api.d.mts.map +1 -1
  38. package/dist/esm/api.mjs +1 -1
  39. package/dist/esm/api.mjs.map +1 -1
  40. package/dist/esm/cloneRouter-DdGGwYdL.mjs +2 -0
  41. package/dist/esm/cloneRouter-DdGGwYdL.mjs.map +1 -0
  42. package/dist/esm/{Router-BeXr2zW4.d.mts → index-DNjaY7KH.d.mts} +4 -69
  43. package/dist/esm/index-DNjaY7KH.d.mts.map +1 -0
  44. package/dist/esm/index-r_JTvSBH.d.mts +306 -0
  45. package/dist/esm/index-r_JTvSBH.d.mts.map +1 -0
  46. package/dist/esm/index.d.mts +4 -197
  47. package/dist/esm/index.d.mts.map +1 -1
  48. package/dist/esm/index.mjs +1 -1
  49. package/dist/esm/index.mjs.map +1 -1
  50. package/dist/esm/{internals-CCymabFj.mjs → internals-C59msvHY.mjs} +1 -1
  51. package/dist/esm/internals-C59msvHY.mjs.map +1 -0
  52. package/dist/esm/utils.d.mts +2 -91
  53. package/dist/esm/utils.mjs +1 -1
  54. package/dist/esm/utils.mjs.map +1 -1
  55. package/dist/esm/validation.d.mts +56 -43
  56. package/dist/esm/validation.d.mts.map +1 -1
  57. package/dist/esm/validation.mjs +1 -1
  58. package/package.json +1 -1
  59. package/src/Router.ts +13 -16
  60. package/src/internals.ts +13 -1
  61. package/src/utils/createRequestScope.ts +174 -0
  62. package/src/utils/hydrateRouter.ts +68 -12
  63. package/src/utils/index.ts +17 -1
  64. package/src/utils/serializeRouterState.ts +50 -3
  65. package/src/utils/serializeState.ts +46 -5
  66. package/dist/cjs/Router-DrBkBdZ5.d.ts.map +0 -1
  67. package/dist/cjs/Router-Pztue5fk.js +0 -6
  68. package/dist/cjs/Router-Pztue5fk.js.map +0 -1
  69. package/dist/cjs/RouterError-BmvAyBlx.js +0 -2
  70. package/dist/cjs/RouterError-BmvAyBlx.js.map +0 -1
  71. package/dist/cjs/RouterValidator-DLy_W2du.d.ts +0 -114
  72. package/dist/cjs/RouterValidator-DLy_W2du.d.ts.map +0 -1
  73. package/dist/cjs/getPluginApi-CUcFDzuA.js +0 -2
  74. package/dist/cjs/getPluginApi-CUcFDzuA.js.map +0 -1
  75. package/dist/cjs/internals-na15rxo_.js.map +0 -1
  76. package/dist/cjs/utils.d.ts.map +0 -1
  77. package/dist/esm/Router-BeXr2zW4.d.mts.map +0 -1
  78. package/dist/esm/Router-CK8U23pP.mjs +0 -6
  79. package/dist/esm/Router-CK8U23pP.mjs.map +0 -1
  80. package/dist/esm/RouterError-D-Zjbdv9.mjs +0 -2
  81. package/dist/esm/RouterError-D-Zjbdv9.mjs.map +0 -1
  82. package/dist/esm/RouterValidator-C-PvV00i.d.mts +0 -114
  83. package/dist/esm/RouterValidator-C-PvV00i.d.mts.map +0 -1
  84. package/dist/esm/getPluginApi-CsTfDB-O.mjs +0 -2
  85. package/dist/esm/getPluginApi-CsTfDB-O.mjs.map +0 -1
  86. package/dist/esm/internals-CCymabFj.mjs.map +0 -1
  87. package/dist/esm/utils.d.mts.map +0 -1
@@ -0,0 +1,310 @@
1
+ import { State } from "@real-router/types";
2
+
3
+ //#region src/types/RouterValidator.d.ts
4
+ /**
5
+ * RouterValidator interface - defines all validation methods used by the router.
6
+ *
7
+ * This interface is implemented by the validation plugin and injected into RouterInternals.
8
+ * When ctx.validator is null (default), validation is skipped.
9
+ * When ctx.validator is set (by validation plugin), all methods are called.
10
+ *
11
+ * All parameters use `unknown` type to avoid coupling to internal type names.
12
+ */
13
+ interface RouterValidator {
14
+ /**
15
+ * Route validation methods
16
+ */
17
+ routes: {
18
+ validateBuildPathArgs: (route: unknown) => void;
19
+ validateMatchPathArgs: (path: unknown) => void;
20
+ validateIsActiveRouteArgs: (name: unknown, params: unknown, strict: unknown, ignoreQP: unknown) => void;
21
+ validateShouldUpdateNodeArgs: (name: unknown) => void;
22
+ validateStateBuilderArgs: (name: unknown, params: unknown, caller: string) => void;
23
+ validateAddRouteArgs: (routes: unknown) => void;
24
+ validateRoutes: (routes: unknown[], tree: unknown) => void;
25
+ validateRemoveRouteArgs: (name: unknown) => void;
26
+ validateUpdateRouteBasicArgs: (name: unknown, updates: unknown) => void;
27
+ validateUpdateRoutePropertyTypes: (name: string, updates: unknown) => void;
28
+ validateUpdateRoute: (name: string, updates: unknown, tree: unknown) => void;
29
+ validateParentOption: (parent: unknown, tree: unknown) => void;
30
+ validateRouteName: (name: unknown, caller: string) => void;
31
+ throwIfInternalRoute: (name: unknown, caller: string) => void;
32
+ throwIfInternalRouteInArray: (routes: unknown[], caller: string) => void;
33
+ validateExistingRoutes: (store: unknown) => void;
34
+ validateForwardToConsistency: (store: unknown) => void;
35
+ validateSetRootPathArgs: (rootPath: unknown) => void;
36
+ guardRouteCallbacks: (route: unknown) => void;
37
+ guardNoAsyncCallbacks: (route: unknown) => void;
38
+ };
39
+ /**
40
+ * Options validation methods
41
+ */
42
+ options: {
43
+ validateLimitValue: (name: string, value: unknown) => void;
44
+ validateLimits: (limits: unknown) => void;
45
+ validateOptions: (options: unknown, methodName: string) => void;
46
+ validateResolvedDefaultRoute: (routeName: unknown, store: unknown) => void;
47
+ };
48
+ /**
49
+ * Dependencies validation methods
50
+ */
51
+ dependencies: {
52
+ validateDependencyName: (name: unknown, caller: string) => void;
53
+ validateSetDependencyArgs: (name: unknown, value: unknown, caller: string) => void;
54
+ validateDependenciesObject: (deps: unknown, caller: string) => void;
55
+ validateDependencyExists: (name: string, store: unknown) => void;
56
+ validateDependencyLimit: (store: unknown, limits: unknown) => void;
57
+ validateDependenciesStructure: (store: unknown) => void;
58
+ validateDependencyCount: (store: unknown, methodName: string) => void;
59
+ validateCloneArgs: (dependencies: unknown) => void;
60
+ warnOverwrite: (name: string, methodName: string) => void;
61
+ warnBatchOverwrite: (keys: string[], methodName: string) => void;
62
+ warnRemoveNonExistent: (name: unknown) => void;
63
+ };
64
+ /**
65
+ * Plugin validation methods
66
+ */
67
+ plugins: {
68
+ validatePluginLimit: (count: number, limits: unknown) => void;
69
+ validateNoDuplicatePlugins: (factory: unknown, factories: unknown[]) => void;
70
+ validatePluginKeys: (plugin: unknown) => void;
71
+ validateCountThresholds: (count: number) => void;
72
+ warnBatchDuplicates: (plugins: unknown[]) => void;
73
+ warnPluginMethodType: (methodName: string) => void;
74
+ warnPluginAfterStart: (methodName: string) => void;
75
+ validateAddInterceptorArgs: (method: unknown, fn: unknown) => void;
76
+ };
77
+ /**
78
+ * Lifecycle guard validation methods
79
+ */
80
+ lifecycle: {
81
+ validateHandler: (handler: unknown, caller: string) => void;
82
+ validateNotRegistering: (name: string, guards: unknown, caller: string) => void;
83
+ validateHandlerLimit: (count: number, limits: unknown, caller: string) => void;
84
+ validateCountThresholds: (count: number, methodName: string) => void;
85
+ warnOverwrite: (name: string, type: string, methodName: string) => void;
86
+ warnAsyncGuardSync: (name: string, methodName: string) => void;
87
+ };
88
+ /**
89
+ * Navigation validation methods
90
+ */
91
+ navigation: {
92
+ validateNavigateArgs: (name: unknown) => void;
93
+ validateNavigateToDefaultArgs: (options: unknown) => void;
94
+ validateNavigateToStateArgs: (state: unknown) => void;
95
+ validateNavigationOptions: (options: unknown, caller: string) => void;
96
+ validateParams: (params: unknown, methodName: string) => void;
97
+ validateStartArgs: (path: unknown) => void;
98
+ };
99
+ /**
100
+ * State validation methods
101
+ */
102
+ state: {
103
+ validateMakeStateArgs: (name: unknown, params: unknown, path: unknown) => void;
104
+ validateAreStatesEqualArgs: (s1: unknown, s2: unknown, ignoreQP: unknown) => void;
105
+ };
106
+ /**
107
+ * Event bus validation methods
108
+ */
109
+ eventBus: {
110
+ validateEventName: (name: unknown) => void;
111
+ validateListenerArgs: (name: unknown, cb: unknown) => void;
112
+ };
113
+ }
114
+ //#endregion
115
+ //#region src/RouterError.d.ts
116
+ declare class RouterError extends Error {
117
+ [key: string]: unknown;
118
+ readonly segment: string | undefined;
119
+ readonly path: string | undefined;
120
+ readonly redirect: State | undefined;
121
+ code: string;
122
+ /**
123
+ * Creates a new RouterError instance.
124
+ *
125
+ * The options object accepts built-in fields (message, segment, path, redirect)
126
+ * and any additional custom fields, which will all be attached to the error instance.
127
+ *
128
+ * @param code - The error code (e.g., "ROUTE_NOT_FOUND", "CANNOT_ACTIVATE")
129
+ * @param options - Optional configuration object
130
+ * @param options.message - Custom error message (defaults to code if not provided)
131
+ * @param options.segment - The route segment where the error occurred
132
+ * @param options.path - The full path where the error occurred
133
+ * @param options.redirect - Optional redirect state for navigation errors
134
+ *
135
+ * @example
136
+ * ```typescript
137
+ * // Basic error
138
+ * const err1 = new RouterError("ROUTE_NOT_FOUND");
139
+ *
140
+ * // Error with custom message
141
+ * const err2 = new RouterError("ERR", { message: "Something went wrong" });
142
+ *
143
+ * // Error with context and custom fields
144
+ * const err3 = new RouterError("CANNOT_ACTIVATE", {
145
+ * message: "Insufficient permissions",
146
+ * segment: "admin",
147
+ * path: "/admin/users",
148
+ * userId: "123" // custom field
149
+ * });
150
+ *
151
+ * // Error with redirect
152
+ * const err4 = new RouterError("TRANSITION_ERR", {
153
+ * redirect: { name: "home", path: "/", params: {} }
154
+ * });
155
+ * ```
156
+ */
157
+ constructor(code: string, {
158
+ message,
159
+ segment,
160
+ path,
161
+ redirect,
162
+ ...rest
163
+ }?: {
164
+ [key: string]: unknown;
165
+ message?: string | undefined;
166
+ segment?: string | undefined;
167
+ path?: string | undefined;
168
+ redirect?: State | undefined;
169
+ });
170
+ /**
171
+ * Updates the error code and conditionally updates the message.
172
+ *
173
+ * If the current message is one of the standard error code values
174
+ * (e.g., "ROUTE_NOT_FOUND", "SAME_STATES"), it will be replaced with the new code.
175
+ * This allows keeping error messages in sync with codes when using standard error codes.
176
+ *
177
+ * If the message is custom (not a standard error code), it will be preserved.
178
+ *
179
+ * @param newCode - The new error code to set
180
+ *
181
+ * @example
182
+ * // Message follows code (standard error code as message)
183
+ * const err = new RouterError("ROUTE_NOT_FOUND", { message: "ROUTE_NOT_FOUND" });
184
+ * err.setCode("CUSTOM_ERROR"); // message becomes "CUSTOM_ERROR"
185
+ *
186
+ * @example
187
+ * // Custom message is preserved
188
+ * const err = new RouterError("ERR", { message: "Custom error message" });
189
+ * err.setCode("NEW_CODE"); // message stays "Custom error message"
190
+ */
191
+ setCode(newCode: string): void;
192
+ /**
193
+ * Copies properties from another Error instance to this RouterError.
194
+ *
195
+ * This method updates the message, cause, and stack trace from the provided error.
196
+ * Useful for wrapping native errors while preserving error context.
197
+ *
198
+ * @param err - The Error instance to copy properties from
199
+ * @throws {TypeError} If err is null or undefined
200
+ *
201
+ * @example
202
+ * ```typescript
203
+ * const routerErr = new RouterError("TRANSITION_ERR");
204
+ * try {
205
+ * // some operation that might fail
206
+ * } catch (nativeErr) {
207
+ * routerErr.setErrorInstance(nativeErr);
208
+ * throw routerErr;
209
+ * }
210
+ * ```
211
+ */
212
+ setErrorInstance(err: Error): void;
213
+ /**
214
+ * Adds custom fields to the error object.
215
+ *
216
+ * This method allows attaching arbitrary data to the error for debugging or logging purposes.
217
+ * All fields become accessible as properties on the error instance and are included in JSON serialization.
218
+ *
219
+ * Reserved method names (setCode, setErrorInstance, setAdditionalFields, hasField, getField, toJSON)
220
+ * are automatically filtered out to prevent accidental overwriting of class methods.
221
+ *
222
+ * @param fields - Object containing custom fields to add to the error
223
+ *
224
+ * @example
225
+ * ```typescript
226
+ * const err = new RouterError("CANNOT_ACTIVATE");
227
+ * err.setAdditionalFields({
228
+ * userId: "123",
229
+ * attemptedRoute: "/admin",
230
+ * reason: "insufficient permissions"
231
+ * });
232
+ *
233
+ * console.log(err.userId); // "123"
234
+ * console.log(JSON.stringify(err)); // includes all custom fields
235
+ * ```
236
+ */
237
+ setAdditionalFields(fields: Record<string, unknown>): void;
238
+ /**
239
+ * Checks if a custom field exists on the error object.
240
+ *
241
+ * This method checks for both custom fields added via setAdditionalFields()
242
+ * and built-in fields (code, message, segment, etc.).
243
+ *
244
+ * @param key - The field name to check
245
+ * @returns `true` if the field exists, `false` otherwise
246
+ *
247
+ * @example
248
+ * ```typescript
249
+ * const err = new RouterError("ERR", { segment: "users" });
250
+ * err.setAdditionalFields({ userId: "123" });
251
+ *
252
+ * err.hasField("userId"); // true
253
+ * err.hasField("segment"); // true
254
+ * err.hasField("unknown"); // false
255
+ * ```
256
+ */
257
+ hasField(key: string): boolean;
258
+ /**
259
+ * Retrieves a custom field value from the error object.
260
+ *
261
+ * This method can access both custom fields and built-in fields.
262
+ * Returns `undefined` if the field doesn't exist.
263
+ *
264
+ * @param key - The field name to retrieve
265
+ * @returns The field value, or `undefined` if it doesn't exist
266
+ *
267
+ * @example
268
+ * ```typescript
269
+ * const err = new RouterError("ERR");
270
+ * err.setAdditionalFields({ userId: "123", role: "admin" });
271
+ *
272
+ * err.getField("userId"); // "123"
273
+ * err.getField("role"); // "admin"
274
+ * err.getField("code"); // "ERR" (built-in field)
275
+ * err.getField("unknown"); // undefined
276
+ * ```
277
+ */
278
+ getField(key: string): unknown;
279
+ /**
280
+ * Serializes the error to a JSON-compatible object.
281
+ *
282
+ * This method is automatically called by JSON.stringify() and includes:
283
+ * - Built-in fields: code, message, segment (if set), path (if set), redirect (if set)
284
+ * - All custom fields added via setAdditionalFields() or constructor
285
+ * - Excludes: stack trace (for security/cleanliness)
286
+ *
287
+ * @returns A plain object representation of the error, suitable for JSON serialization
288
+ *
289
+ * @example
290
+ * ```typescript
291
+ * const err = new RouterError("ROUTE_NOT_FOUND", {
292
+ * message: "Route not found",
293
+ * path: "/admin/users/123"
294
+ * });
295
+ * err.setAdditionalFields({ userId: "123" });
296
+ *
297
+ * JSON.stringify(err);
298
+ * // {
299
+ * // "code": "ROUTE_NOT_FOUND",
300
+ * // "message": "Route not found",
301
+ * // "path": "/admin/users/123",
302
+ * // "userId": "123"
303
+ * // }
304
+ * ```
305
+ */
306
+ toJSON(): Record<string, unknown>;
307
+ }
308
+ //#endregion
309
+ export { RouterValidator as n, RouterError as t };
310
+ //# sourceMappingURL=RouterError-hhfSVGtY.d.mts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"RouterError-hhfSVGtY.d.mts","names":[],"sources":["../../src/types/RouterValidator.ts","../../src/RouterError.ts"],"mappings":"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"}
@@ -1,4 +1,5 @@
1
- import { f as RouteTree, t as Router$1 } from "./Router-BeXr2zW4.mjs";
1
+ import { i as RouteTree } from "./index-DNjaY7KH.mjs";
2
+ import { t as Router$1 } from "./Router-BmhiDQUJ.mjs";
2
3
  import { DefaultDependencies, DependenciesApi, LifecycleApi, PluginApi as PluginApi$1, Router, RoutesApi } from "@real-router/types";
3
4
 
4
5
  //#region src/api/types.d.ts
@@ -1 +1 @@
1
- {"version":3,"file":"api.d.mts","names":[],"sources":["../../src/api/types.ts","../../src/api/getPluginApi.ts","../../src/api/getRoutesApi.ts","../../src/api/getDependenciesApi.ts","../../src/api/getLifecycleApi.ts","../../src/api/cloneRouter.ts"],"mappings":";;;;UAGiB,SAAA,SAAkB,IAAA,CAAK,WAAA;EACtC,OAAA,QAAe,SAAA;AAAA;;;iBCkBD,YAAA,sBACO,mBAAA,GAAsB,mBAAA,CAAA,CAC3C,MAAA,EAAQ,MAAA,CAAO,YAAA,IAAgB,SAAA;;;iBC8XjB,YAAA,sBACO,mBAAA,GAAsB,mBAAA,CAAA,CAC3C,MAAA,EAAQ,MAAA,CAAO,YAAA,IAAgB,SAAA,CAAU,YAAA;;;iBCvU3B,kBAAA,sBACO,mBAAA,GAAsB,mBAAA,CAAA,CAC3C,MAAA,EAAQ,MAAA,CAAO,YAAA,IAAgB,eAAA,CAAgB,YAAA;;;iBC7EjC,eAAA,sBACO,mBAAA,GAAsB,mBAAA,CAAA,CAC3C,MAAA,EAAQ,MAAA,CAAO,YAAA,IAAgB,YAAA,CAAa,YAAA;;;iBCG9B,WAAA,sBACO,mBAAA,GAAsB,mBAAA,CAAA,CAE3C,MAAA,EAAQ,MAAA,CAAO,YAAA,GACf,YAAA,GAAe,YAAA,GACd,QAAA,CAAY,YAAA"}
1
+ {"version":3,"file":"api.d.mts","names":[],"sources":["../../src/api/types.ts","../../src/api/getPluginApi.ts","../../src/api/getRoutesApi.ts","../../src/api/getDependenciesApi.ts","../../src/api/getLifecycleApi.ts","../../src/api/cloneRouter.ts"],"mappings":";;;;;UAGiB,SAAA,SAAkB,IAAA,CAAK,WAAA;EACtC,OAAA,QAAe,SAAA;AAAA;;;iBCkBD,YAAA,sBACO,mBAAA,GAAsB,mBAAA,CAAA,CAC3C,MAAA,EAAQ,MAAA,CAAO,YAAA,IAAgB,SAAA;;;iBC8XjB,YAAA,sBACO,mBAAA,GAAsB,mBAAA,CAAA,CAC3C,MAAA,EAAQ,MAAA,CAAO,YAAA,IAAgB,SAAA,CAAU,YAAA;;;iBCvU3B,kBAAA,sBACO,mBAAA,GAAsB,mBAAA,CAAA,CAC3C,MAAA,EAAQ,MAAA,CAAO,YAAA,IAAgB,eAAA,CAAgB,YAAA;;;iBC7EjC,eAAA,sBACO,mBAAA,GAAsB,mBAAA,CAAA,CAC3C,MAAA,EAAQ,MAAA,CAAO,YAAA,IAAgB,YAAA,CAAa,YAAA;;;iBCG9B,WAAA,sBACO,mBAAA,GAAsB,mBAAA,CAAA,CAE3C,MAAA,EAAQ,MAAA,CAAO,YAAA,GACf,YAAA,GAAe,YAAA,GACd,QAAA,CAAY,YAAA"}
package/dist/esm/api.mjs CHANGED
@@ -1,2 +1,2 @@
1
- import{c as e,i as t,l as n,n as r,o as i,r as a,s as o,t as s,u as c}from"./Router-CK8U23pP.mjs";import{t as l,u}from"./RouterError-D-Zjbdv9.mjs";import{r as d,t as f}from"./internals-CCymabFj.mjs";import{n as p,t as m}from"./getPluginApi-CsTfDB-O.mjs";import{logger as h}from"@real-router/logger";function g(e,t,n){if(t){let n=t===e,r=t.startsWith(`${e}.`);if(n||r){let r=n?``:` (current: "${t}")`;return h.warn(`router.removeRoute`,`Cannot remove route "${e}" — it is currently active${r}. Navigate away first.`),!1}}return n&&h.warn(`router.removeRoute`,`Route "${e}" removed while navigation is in progress. This may cause unexpected behavior.`),!0}function _(e){return e?(h.error(`router.clearRoutes`,`Cannot clear routes while navigation is in progress. Wait for navigation to complete.`),!1):!0}function v(e,t,n=``){for(let r of e){let e=n?`${n}.${r.name}`:r.name;if(e===t)return r;if(r.children&&t.startsWith(`${e}.`))return v(r.children,t,e)}}function y(e,t,n,r){let a=t=>t===e||t.startsWith(`${e}.`);i(t.decoders,a),i(t.encoders,a),i(t.defaultParams,a),i(t.forwardMap,a),i(t.forwardFnMap,a),i(n,a),i(t.forwardMap,e=>a(t.forwardMap[e]));let[o,s]=r.getFactories();for(let e of Object.keys(s))a(e)&&r.clearCanActivate(e);for(let e of Object.keys(o))a(e)&&r.clearCanDeactivate(e)}function b(e,t,n,r){return t===null?(delete n.forwardMap[e],delete n.forwardFnMap[e]):typeof t==`string`?(delete n.forwardFnMap[e],n.forwardMap[e]=t):(delete n.forwardMap[e],n.forwardFnMap[e]=t),r(n)}function x(e,t,n,r){let i={name:e.name,path:e.path},a=n.forwardFnMap[t],o=n.forwardMap[t];a===void 0?o!==void 0&&(i.forwardTo=o):i.forwardTo=a,t in n.defaultParams&&(i.defaultParams=n.defaultParams[t]),t in n.decoders&&(i.decodeParams=n.decoders[t]),t in n.encoders&&(i.encodeParams=n.encoders[t]);let[s,c]=r;return t in c&&(i.canActivate=c[t]),t in s&&(i.canDeactivate=s[t]),e.children&&(i.children=e.children.map(e=>x(e,`${t}.${e.name}`,n,r))),i}function S(n,r,i){if(i){let t=v(n.definitions,i);t.children??=[];for(let n of r)t.children.push(e(n))}else for(let t of r)n.definitions.push(e(t));t(r,n.config,n.routeCustomFields,n.pendingCanActivate,n.pendingCanDeactivate,n.depsStore,i??``),n.treeOperations.commitTreeChanges(n)}function C(n,i,a,o,s){r(n),n.lifecycleNamespace.clearDefinitionGuards();for(let t of i)n.definitions.push(e(t));if(t(i,n.config,n.routeCustomFields,n.pendingCanActivate,n.pendingCanDeactivate,n.depsStore,``),n.treeOperations.commitTreeChanges(n),o!==void 0){let e=a.matchPath(o,a.getOptions());e?a.setState({...e,transition:s}):a.clearState()}}function w(e,t){return o(e.definitions,t)?(y(t,e.config,e.routeCustomFields,e.lifecycleNamespace),e.treeOperations.commitTreeChanges(e),!0):!1}function T(e,t,n){if(n.forwardTo!==void 0&&(e.resolvedForwardMap=b(t,n.forwardTo,e.config,e=>a(e))),n.defaultParams!==void 0&&(n.defaultParams===null?delete e.config.defaultParams[t]:e.config.defaultParams[t]=n.defaultParams),n.decodeParams!==void 0)if(n.decodeParams===null)delete e.config.decoders[t];else{let r=n.decodeParams;e.config.decoders[t]=e=>r(e)??e}if(n.encodeParams!==void 0)if(n.encodeParams===null)delete e.config.encoders[t];else{let r=n.encodeParams;e.config.encoders[t]=e=>r(e)??e}}function E(e,t){let n=e.matcher.getSegmentsByName(t);if(!n)return;let r=n.at(-1),i=e.treeOperations.nodeToDefinition(r),a=e.lifecycleNamespace.getFactories();return x(i,t,e.config,a)}function D(e){let t=d(e),n=t.routeGetStore(),r=f(`add`,(e,t)=>{S(n,e,t?.parent)},t.interceptors);return{add:(e,i)=>{p(t.isDisposed);let a=Array.isArray(e)?e:[e],o=i?.parent;c(a,t.validator),o!==void 0&&t.validator?.routes.validateParentOption(o,n.tree),t.validator?.routes.throwIfInternalRouteInArray(a,`addRoute`),t.validator?.routes.validateAddRouteArgs(a),t.validator?.routes.validateRoutes(a,n),r(a,o===void 0?void 0:{parent:o})},remove:e=>{p(t.isDisposed),t.validator?.routes.validateRemoveRouteArgs(e),t.validator?.routes.throwIfInternalRoute(e,`removeRoute`),g(e,t.getStateName(),t.isTransitioning())&&(w(n,e)||h.warn(`router.removeRoute`,`Route "${e}" not found. No changes made.`))},update:(e,r)=>{p(t.isDisposed),t.validator?.routes.validateUpdateRouteBasicArgs(e,r),t.validator?.routes.throwIfInternalRoute(e,`updateRoute`);let{forwardTo:i,defaultParams:a,decodeParams:o,encodeParams:s,canActivate:c,canDeactivate:l}=r;t.validator?.routes.validateUpdateRoutePropertyTypes(e,r),t.isTransitioning()&&h.error(`router.updateRoute`,`Updating route "${e}" while navigation is in progress. This may cause unexpected behavior.`),t.validator?.routes.validateUpdateRoute(e,r,n),T(n,e,{forwardTo:i,defaultParams:a,decodeParams:o,encodeParams:s}),c!==void 0&&(c===null?n.lifecycleNamespace.clearCanActivate(e):n.lifecycleNamespace.addCanActivate(e,c,!0)),l!==void 0&&(l===null?n.lifecycleNamespace.clearCanDeactivate(e):n.lifecycleNamespace.addCanDeactivate(e,l,!0))},clear:()=>{p(t.isDisposed),_(t.isTransitioning())&&(n.treeOperations.resetStore(n),n.lifecycleNamespace.clearAll(),t.clearState())},has:e=>(t.validator?.routes.validateRouteName(e,`hasRoute`),n.matcher.hasRoute(e)),get:e=>(t.validator?.routes.validateRouteName(e,`getRoute`),E(n,e)),replace:r=>{p(t.isDisposed);let i=Array.isArray(r)?r:[r];if(!_(t.isTransitioning()))return;c(i,t.validator),t.validator?.routes.throwIfInternalRouteInArray(i,`replaceRoutes`),t.validator?.routes.validateAddRouteArgs(i),t.validator?.routes.validateRoutes(i,n);let a=e.getState();C(n,i,t,a?.path,a?.transition)}}}function O(e,t,n,r){if(n===void 0)return!1;if(!Object.hasOwn(e.dependencies,t))r?.dependencies.validateDependencyCount(e,`setDependency`);else{let i=e.dependencies[t];i!==n&&!(Number.isNaN(i)&&Number.isNaN(n))&&r?.dependencies.warnOverwrite(t,`setDependency`)}return e.dependencies[t]=n,!0}function k(e,t,n){let r=[];for(let i in t)t[i]!==void 0&&(Object.hasOwn(e.dependencies,i)?r.push(i):n?.dependencies.validateDependencyCount(e,`setDependencies`),e.dependencies[i]=t[i]);r.length>0&&n?.dependencies.warnBatchOverwrite(r,`setDependencies`)}function A(e){let t=d(e);return{get:e=>{t.validator?.dependencies.validateDependencyName(e,`getDependency`);let n=t.dependenciesGetStore(),r=n.dependencies[e];return t.validator?.dependencies.validateDependencyExists(e,n),r},getAll:()=>({...t.dependenciesGetStore().dependencies}),set:(e,n)=>{p(t.isDisposed),t.validator?.dependencies.validateSetDependencyArgs(e,n,`setDependency`),O(t.dependenciesGetStore(),e,n,t.validator)},setAll:e=>{p(t.isDisposed);let n=t.dependenciesGetStore();t.validator?.dependencies.validateDependenciesObject(e,`setDependencies`),t.validator?.dependencies.validateDependencyLimit(n,n.limits),k(n,e,t.validator)},remove:e=>{p(t.isDisposed),t.validator?.dependencies.validateDependencyName(e,`removeDependency`);let n=t.dependenciesGetStore();Object.hasOwn(n.dependencies,e)||t.validator?.dependencies.warnRemoveNonExistent(e),delete n.dependencies[e]},reset:()=>{p(t.isDisposed);let e=t.dependenciesGetStore();e.dependencies=Object.create(null)},has:e=>(t.validator?.dependencies.validateDependencyName(e,`hasDependency`),Object.hasOwn(t.dependenciesGetStore().dependencies,e))}}function j(e){let t=d(e),n=t.routeGetStore().lifecycleNamespace;return{addActivateGuard(e,r){p(t.isDisposed),t.validator?.routes.validateRouteName(e,`addActivateGuard`),t.validator?.lifecycle.validateHandler(r,`addActivateGuard`);let i=n.getHandlerCount(`activate`);t.validator?.lifecycle.validateHandlerLimit(i,t.dependenciesGetStore().limits,`canActivate`),n.addCanActivate(e,r)},addDeactivateGuard(e,r){p(t.isDisposed),t.validator?.routes.validateRouteName(e,`addDeactivateGuard`),t.validator?.lifecycle.validateHandler(r,`addDeactivateGuard`);let i=n.getHandlerCount(`deactivate`);t.validator?.lifecycle.validateHandlerLimit(i,t.dependenciesGetStore().limits,`canDeactivate`),n.addCanDeactivate(e,r)},removeActivateGuard(e){p(t.isDisposed),t.validator?.routes.validateRouteName(e,`removeActivateGuard`),n.clearCanActivate(e)},removeDeactivateGuard(e){p(t.isDisposed),t.validator?.routes.validateRouteName(e,`removeDeactivateGuard`),n.clearCanDeactivate(e)}}}function M(e,t){let r=d(e);if(r.isDisposed())throw new l(u.ROUTER_DISPOSED);r.validator?.dependencies.validateCloneArgs(t);let i=r.routeGetStore(),a=n(i.tree),o=i.config,c=i.resolvedForwardMap,f=i.routeCustomFields,p=r.cloneOptions(),m=r.cloneDependencies(),[h,g]=r.getLifecycleFactories(),_=r.getPluginFactories(),v=new s(a,p,{...m,...t}),y=j(v);for(let[e,t]of Object.entries(h))y.addDeactivateGuard(e,t);for(let[e,t]of Object.entries(g))y.addActivateGuard(e,t);_.length>0&&v.usePlugin(..._);let b=d(v).routeGetStore();return Object.assign(b.config.decoders,o.decoders),Object.assign(b.config.encoders,o.encoders),Object.assign(b.config.defaultParams,o.defaultParams),Object.assign(b.config.forwardMap,o.forwardMap),Object.assign(b.config.forwardFnMap,o.forwardFnMap),Object.assign(b.resolvedForwardMap,c),Object.assign(b.routeCustomFields,f),v}export{M as cloneRouter,A as getDependenciesApi,j as getLifecycleApi,m as getPluginApi,D as getRoutesApi};
1
+ import{a as e,c as t,d as n,i as r,l as i,r as a,s as o}from"./Router-DRM2Fd06.mjs";import{r as s,t as c}from"./internals-C59msvHY.mjs";import{i as l,n as u,r as d,t as f}from"./cloneRouter-DdGGwYdL.mjs";import{logger as p}from"@real-router/logger";function m(e,t,n){if(t){let n=t===e,r=t.startsWith(`${e}.`);if(n||r){let r=n?``:` (current: "${t}")`;return p.warn(`router.removeRoute`,`Cannot remove route "${e}" — it is currently active${r}. Navigate away first.`),!1}}return n&&p.warn(`router.removeRoute`,`Route "${e}" removed while navigation is in progress. This may cause unexpected behavior.`),!0}function h(e){return e?(p.error(`router.clearRoutes`,`Cannot clear routes while navigation is in progress. Wait for navigation to complete.`),!1):!0}function g(e,t,n=``){for(let r of e){let e=n?`${n}.${r.name}`:r.name;if(e===t)return r;if(r.children&&t.startsWith(`${e}.`))return g(r.children,t,e)}}function _(e,t,n,r){let i=t=>t===e||t.startsWith(`${e}.`);o(t.decoders,i),o(t.encoders,i),o(t.defaultParams,i),o(t.forwardMap,i),o(t.forwardFnMap,i),o(n,i),o(t.forwardMap,e=>i(t.forwardMap[e]));let[a,s]=r.getFactories();for(let e of Object.keys(s))i(e)&&r.clearCanActivate(e);for(let e of Object.keys(a))i(e)&&r.clearCanDeactivate(e)}function v(e,t,n,r){return t===null?(delete n.forwardMap[e],delete n.forwardFnMap[e]):typeof t==`string`?(delete n.forwardFnMap[e],n.forwardMap[e]=t):(delete n.forwardMap[e],n.forwardFnMap[e]=t),r(n)}function y(e,t,n,r){let i={name:e.name,path:e.path},a=n.forwardFnMap[t],o=n.forwardMap[t];a===void 0?o!==void 0&&(i.forwardTo=o):i.forwardTo=a,t in n.defaultParams&&(i.defaultParams=n.defaultParams[t]),t in n.decoders&&(i.decodeParams=n.decoders[t]),t in n.encoders&&(i.encodeParams=n.encoders[t]);let[s,c]=r;return t in c&&(i.canActivate=c[t]),t in s&&(i.canDeactivate=s[t]),e.children&&(i.children=e.children.map(e=>y(e,`${t}.${e.name}`,n,r))),i}function b(t,n,r){if(r){let e=g(t.definitions,r);e.children??=[];for(let t of n)e.children.push(i(t))}else for(let e of n)t.definitions.push(i(e));e(n,t.config,t.routeCustomFields,t.pendingCanActivate,t.pendingCanDeactivate,t.depsStore,r??``),t.treeOperations.commitTreeChanges(t)}function x(t,n,r,o,s){a(t),t.lifecycleNamespace.clearDefinitionGuards();for(let e of n)t.definitions.push(i(e));if(e(n,t.config,t.routeCustomFields,t.pendingCanActivate,t.pendingCanDeactivate,t.depsStore,``),t.treeOperations.commitTreeChanges(t),o!==void 0){let e=r.matchPath(o,r.getOptions());e?r.setState({...e,transition:s}):r.clearState()}}function S(e,n){return t(e.definitions,n)?(_(n,e.config,e.routeCustomFields,e.lifecycleNamespace),e.treeOperations.commitTreeChanges(e),!0):!1}function C(e,t,n){if(n.forwardTo!==void 0&&(e.resolvedForwardMap=v(t,n.forwardTo,e.config,e=>r(e))),n.defaultParams!==void 0&&(n.defaultParams===null?delete e.config.defaultParams[t]:e.config.defaultParams[t]=n.defaultParams),n.decodeParams!==void 0)if(n.decodeParams===null)delete e.config.decoders[t];else{let r=n.decodeParams;e.config.decoders[t]=e=>r(e)??e}if(n.encodeParams!==void 0)if(n.encodeParams===null)delete e.config.encoders[t];else{let r=n.encodeParams;e.config.encoders[t]=e=>r(e)??e}}function w(e,t){let n=e.matcher.getSegmentsByName(t);if(!n)return;let r=n.at(-1),i=e.treeOperations.nodeToDefinition(r),a=e.lifecycleNamespace.getFactories();return y(i,t,e.config,a)}function T(e){let t=s(e),r=t.routeGetStore(),i=c(`add`,(e,t)=>{b(r,e,t?.parent)},t.interceptors);return{add:(e,a)=>{l(t.isDisposed);let o=Array.isArray(e)?e:[e],s=a?.parent;n(o,t.validator),s!==void 0&&t.validator?.routes.validateParentOption(s,r.tree),t.validator?.routes.throwIfInternalRouteInArray(o,`addRoute`),t.validator?.routes.validateAddRouteArgs(o),t.validator?.routes.validateRoutes(o,r),i(o,s===void 0?void 0:{parent:s})},remove:e=>{l(t.isDisposed),t.validator?.routes.validateRemoveRouteArgs(e),t.validator?.routes.throwIfInternalRoute(e,`removeRoute`),m(e,t.getStateName(),t.isTransitioning())&&(S(r,e)||p.warn(`router.removeRoute`,`Route "${e}" not found. No changes made.`))},update:(e,n)=>{l(t.isDisposed),t.validator?.routes.validateUpdateRouteBasicArgs(e,n),t.validator?.routes.throwIfInternalRoute(e,`updateRoute`);let{forwardTo:i,defaultParams:a,decodeParams:o,encodeParams:s,canActivate:c,canDeactivate:u}=n;t.validator?.routes.validateUpdateRoutePropertyTypes(e,n),t.isTransitioning()&&p.error(`router.updateRoute`,`Updating route "${e}" while navigation is in progress. This may cause unexpected behavior.`),t.validator?.routes.validateUpdateRoute(e,n,r),C(r,e,{forwardTo:i,defaultParams:a,decodeParams:o,encodeParams:s}),c!==void 0&&(c===null?r.lifecycleNamespace.clearCanActivate(e):r.lifecycleNamespace.addCanActivate(e,c,!0)),u!==void 0&&(u===null?r.lifecycleNamespace.clearCanDeactivate(e):r.lifecycleNamespace.addCanDeactivate(e,u,!0))},clear:()=>{l(t.isDisposed),h(t.isTransitioning())&&(r.treeOperations.resetStore(r),r.lifecycleNamespace.clearAll(),t.clearState())},has:e=>(t.validator?.routes.validateRouteName(e,`hasRoute`),r.matcher.hasRoute(e)),get:e=>(t.validator?.routes.validateRouteName(e,`getRoute`),w(r,e)),replace:i=>{l(t.isDisposed);let a=Array.isArray(i)?i:[i];if(!h(t.isTransitioning()))return;n(a,t.validator),t.validator?.routes.throwIfInternalRouteInArray(a,`replaceRoutes`),t.validator?.routes.validateAddRouteArgs(a),t.validator?.routes.validateRoutes(a,r);let o=e.getState();x(r,a,t,o?.path,o?.transition)}}}function E(e,t,n,r){if(n===void 0)return!1;if(!Object.hasOwn(e.dependencies,t))r?.dependencies.validateDependencyCount(e,`setDependency`);else{let i=e.dependencies[t];i!==n&&!(Number.isNaN(i)&&Number.isNaN(n))&&r?.dependencies.warnOverwrite(t,`setDependency`)}return e.dependencies[t]=n,!0}function D(e,t,n){let r=[];for(let i in t)t[i]!==void 0&&(Object.hasOwn(e.dependencies,i)?r.push(i):n?.dependencies.validateDependencyCount(e,`setDependencies`),e.dependencies[i]=t[i]);r.length>0&&n?.dependencies.warnBatchOverwrite(r,`setDependencies`)}function O(e){let t=s(e);return{get:e=>{t.validator?.dependencies.validateDependencyName(e,`getDependency`);let n=t.dependenciesGetStore(),r=n.dependencies[e];return t.validator?.dependencies.validateDependencyExists(e,n),r},getAll:()=>({...t.dependenciesGetStore().dependencies}),set:(e,n)=>{l(t.isDisposed),t.validator?.dependencies.validateSetDependencyArgs(e,n,`setDependency`),E(t.dependenciesGetStore(),e,n,t.validator)},setAll:e=>{l(t.isDisposed);let n=t.dependenciesGetStore();t.validator?.dependencies.validateDependenciesObject(e,`setDependencies`),t.validator?.dependencies.validateDependencyLimit(n,n.limits),D(n,e,t.validator)},remove:e=>{l(t.isDisposed),t.validator?.dependencies.validateDependencyName(e,`removeDependency`);let n=t.dependenciesGetStore();Object.hasOwn(n.dependencies,e)||t.validator?.dependencies.warnRemoveNonExistent(e),delete n.dependencies[e]},reset:()=>{l(t.isDisposed);let e=t.dependenciesGetStore();e.dependencies=Object.create(null)},has:e=>(t.validator?.dependencies.validateDependencyName(e,`hasDependency`),Object.hasOwn(t.dependenciesGetStore().dependencies,e))}}export{f as cloneRouter,O as getDependenciesApi,u as getLifecycleApi,d as getPluginApi,T as getRoutesApi};
2
2
  //# sourceMappingURL=api.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"api.mjs","names":["routeTreeToDefinitions","RouterClass"],"sources":["../../src/namespaces/RoutesNamespace/routeGuards.ts","../../src/api/getRoutesApi.ts","../../src/api/getDependenciesApi.ts","../../src/api/getLifecycleApi.ts","../../src/api/cloneRouter.ts"],"sourcesContent":["import { logger } from \"@real-router/logger\";\n\n/**\n * Validates removeRoute constraints.\n * Returns false if removal should be blocked (route is active).\n * Logs warnings for edge cases.\n *\n * @param name - Route name to remove\n * @param currentStateName - Current active route name (or undefined)\n * @param isNavigating - Whether navigation is in progress\n * @returns true if removal can proceed, false if blocked\n */\nexport function validateRemoveRoute(\n name: string,\n currentStateName: string | undefined,\n isNavigating: boolean,\n): boolean {\n if (currentStateName) {\n const isExactMatch = currentStateName === name;\n const isParentOfCurrent = currentStateName.startsWith(`${name}.`);\n\n if (isExactMatch || isParentOfCurrent) {\n const suffix = isExactMatch ? \"\" : ` (current: \"${currentStateName}\")`;\n\n logger.warn(\n \"router.removeRoute\",\n `Cannot remove route \"${name}\" — it is currently active${suffix}. Navigate away first.`,\n );\n\n return false;\n }\n }\n\n if (isNavigating) {\n logger.warn(\n \"router.removeRoute\",\n `Route \"${name}\" removed while navigation is in progress. This may cause unexpected behavior.`,\n );\n }\n\n return true;\n}\n\n/**\n * Validates clearRoutes operation.\n * Returns false if operation should be blocked (navigation in progress).\n *\n * @param isNavigating - Whether navigation is in progress\n * @returns true if clearRoutes can proceed, false if blocked\n */\nexport function validateClearRoutes(isNavigating: boolean): boolean {\n if (isNavigating) {\n logger.error(\n \"router.clearRoutes\",\n \"Cannot clear routes while navigation is in progress. Wait for navigation to complete.\",\n );\n\n return false;\n }\n\n return true;\n}\n","import { logger } from \"@real-router/logger\";\n\nimport { throwIfDisposed } from \"./helpers\";\nimport { guardRouteStructure } from \"../guards\";\nimport { createInterceptable, getInternals } from \"../internals\";\nimport {\n clearConfigEntries,\n removeFromDefinitions,\n sanitizeRoute,\n} from \"../namespaces/RoutesNamespace/helpers\";\nimport {\n validateClearRoutes,\n validateRemoveRoute,\n} from \"../namespaces/RoutesNamespace/routeGuards\";\nimport {\n clearRouteData,\n refreshForwardMap,\n registerAllRouteHandlers,\n} from \"../namespaces/RoutesNamespace/routesStore\";\n\nimport type { RoutesApi } from \"./types\";\nimport type { RouterInternals } from \"../internals\";\nimport type { RouteLifecycleNamespace, RouteConfig } from \"../namespaces\";\nimport type { RoutesStore } from \"../namespaces/RoutesNamespace\";\nimport type { GuardFnFactory, Route } from \"../types\";\nimport type {\n DefaultDependencies,\n ForwardToCallback,\n Params,\n Router,\n TransitionMeta,\n} from \"@real-router/types\";\nimport type { RouteDefinition, RouteTree } from \"route-tree\";\n\n// ============================================================================\n// Helpers\n// ============================================================================\n\n/**\n * Recursively finds a route definition by its full dotted name.\n */\nfunction findDefinition(\n definitions: RouteDefinition[],\n fullName: string,\n parentPrefix = \"\",\n): RouteDefinition | undefined {\n for (const def of definitions) {\n const currentFullName = parentPrefix\n ? `${parentPrefix}.${def.name}`\n : def.name;\n\n if (currentFullName === fullName) {\n return def;\n }\n\n if (def.children && fullName.startsWith(`${currentFullName}.`)) {\n return findDefinition(def.children, fullName, currentFullName);\n }\n }\n\n /* v8 ignore next -- @preserve: defensive return, callers validate route exists before calling */\n return undefined;\n}\n\n/**\n * Clears all config entries and lifecycle handlers for a removed route\n * (and all its descendants).\n */\nfunction clearRouteConfigurations<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n routeName: string,\n config: RouteConfig,\n routeCustomFields: Record<string, Record<string, unknown>>,\n lifecycleNamespace: RouteLifecycleNamespace<Dependencies>,\n): void {\n const shouldClear = (name: string): boolean =>\n name === routeName || name.startsWith(`${routeName}.`);\n\n clearConfigEntries(config.decoders, shouldClear);\n clearConfigEntries(config.encoders, shouldClear);\n clearConfigEntries(config.defaultParams, shouldClear);\n clearConfigEntries(config.forwardMap, shouldClear);\n clearConfigEntries(config.forwardFnMap, shouldClear);\n clearConfigEntries(routeCustomFields, shouldClear);\n\n // Clear forwardMap entries pointing TO the deleted route (or its descendants)\n clearConfigEntries(config.forwardMap, (key) =>\n shouldClear(config.forwardMap[key]),\n );\n\n // Clear lifecycle handlers\n const [canDeactivateFactories, canActivateFactories] =\n lifecycleNamespace.getFactories();\n\n for (const name of Object.keys(canActivateFactories)) {\n if (shouldClear(name)) {\n lifecycleNamespace.clearCanActivate(name);\n }\n }\n\n for (const name of Object.keys(canDeactivateFactories)) {\n if (shouldClear(name)) {\n lifecycleNamespace.clearCanDeactivate(name);\n }\n }\n}\n\n/**\n * Updates forwardTo for a route in config and returns the refreshed resolved\n * forward map (REPLACE semantics — caller must call ctx.setResolvedForwardMap).\n */\nfunction updateForwardTo<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n name: string,\n forwardTo: string | ForwardToCallback<Dependencies> | null,\n config: RouteConfig,\n refreshForwardMapFn: (config: RouteConfig) => Record<string, string>,\n): Record<string, string> {\n if (forwardTo === null) {\n delete config.forwardMap[name];\n delete config.forwardFnMap[name];\n } else if (typeof forwardTo === \"string\") {\n delete config.forwardFnMap[name];\n config.forwardMap[name] = forwardTo;\n } else {\n delete config.forwardMap[name];\n config.forwardFnMap[name] = forwardTo;\n }\n\n return refreshForwardMapFn(config);\n}\n\n/**\n * Builds a full Route object from a bare RouteDefinition by re-attaching\n * config entries and lifecycle factories.\n *\n * RECURSIVE — call with the factories tuple obtained ONCE from\n * `lifecycleNamespace.getFactories()` and pass it through to children.\n */\nfunction enrichRoute<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n routeDef: RouteDefinition,\n routeName: string,\n config: RouteConfig,\n factories: [\n Record<string, GuardFnFactory<Dependencies>>,\n Record<string, GuardFnFactory<Dependencies>>,\n ],\n): Route<Dependencies> {\n const route: Route<Dependencies> = {\n name: routeDef.name,\n path: routeDef.path,\n };\n\n const forwardToFn = config.forwardFnMap[routeName];\n const forwardToStr = config.forwardMap[routeName];\n\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n if (forwardToFn !== undefined) {\n route.forwardTo = forwardToFn;\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n } else if (forwardToStr !== undefined) {\n route.forwardTo = forwardToStr;\n }\n\n if (routeName in config.defaultParams) {\n route.defaultParams = config.defaultParams[routeName];\n }\n\n if (routeName in config.decoders) {\n route.decodeParams = config.decoders[routeName];\n }\n\n if (routeName in config.encoders) {\n route.encodeParams = config.encoders[routeName];\n }\n\n const [canDeactivateFactories, canActivateFactories] = factories;\n\n if (routeName in canActivateFactories) {\n route.canActivate = canActivateFactories[routeName];\n }\n\n if (routeName in canDeactivateFactories) {\n route.canDeactivate = canDeactivateFactories[routeName];\n }\n\n if (routeDef.children) {\n route.children = routeDef.children.map((child) =>\n enrichRoute(child, `${routeName}.${child.name}`, config, factories),\n );\n }\n\n return route;\n}\n\n// ============================================================================\n// CRUD operations\n// ============================================================================\n\n/**\n * Adds one or more routes to the router.\n * Input already validated by facade.\n */\nfunction addRoutes<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n store: RoutesStore<Dependencies>,\n routes: Route<Dependencies>[],\n parentName?: string,\n): void {\n if (parentName) {\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion\n const parentDef = findDefinition(store.definitions, parentName)!;\n\n parentDef.children ??= [];\n\n for (const route of routes) {\n parentDef.children.push(sanitizeRoute(route));\n }\n } else {\n for (const route of routes) {\n store.definitions.push(sanitizeRoute(route));\n }\n }\n\n registerAllRouteHandlers(\n routes,\n store.config,\n store.routeCustomFields,\n store.pendingCanActivate,\n store.pendingCanDeactivate,\n store.depsStore,\n parentName ?? \"\",\n );\n\n store.treeOperations.commitTreeChanges(store);\n}\n\n/**\n * Atomically replaces all routes with a new set.\n * Follows RFC 6-step semantics for HMR support.\n */\nfunction replaceRoutes<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n store: RoutesStore<Dependencies>,\n routes: Route<Dependencies>[],\n ctx: RouterInternals<Dependencies>,\n currentPath: string | undefined,\n previousTransition: TransitionMeta | undefined,\n): void {\n // Step 2: Clear route data (WITHOUT tree rebuild)\n clearRouteData(store);\n\n // Step 3: Clear definition lifecycle handlers (preserve external guards)\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- guaranteed set after wiring\n store.lifecycleNamespace!.clearDefinitionGuards();\n\n // Step 4: Register new routes\n for (const route of routes) {\n store.definitions.push(sanitizeRoute(route));\n }\n\n registerAllRouteHandlers(\n routes,\n store.config,\n store.routeCustomFields,\n store.pendingCanActivate,\n store.pendingCanDeactivate,\n store.depsStore,\n \"\",\n );\n\n // Step 5: One tree rebuild\n store.treeOperations.commitTreeChanges(store);\n\n // Step 6: Revalidate state (preserve transition from previous state)\n if (currentPath !== undefined) {\n const revalidated = ctx.matchPath(currentPath, ctx.getOptions());\n\n if (revalidated) {\n ctx.setState({\n ...revalidated,\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- previousTransition is guaranteed defined: currentPath is only set when getState() returned a state, which always has transition\n transition: previousTransition!,\n });\n } else {\n ctx.clearState();\n }\n }\n}\n\n/**\n * Removes a route and all its children.\n *\n * @returns true if removed, false if not found\n */\nfunction removeRoute<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(store: RoutesStore<Dependencies>, name: string): boolean {\n const wasRemoved = removeFromDefinitions(store.definitions, name);\n\n if (!wasRemoved) {\n return false;\n }\n\n clearRouteConfigurations(\n name,\n store.config,\n store.routeCustomFields,\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion\n store.lifecycleNamespace!,\n );\n\n store.treeOperations.commitTreeChanges(store);\n\n return true;\n}\n\n/**\n * Updates a route's configuration in place.\n */\nfunction updateRouteConfig<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n store: RoutesStore<Dependencies>,\n name: string,\n updates: {\n forwardTo?: string | ForwardToCallback<Dependencies> | null | undefined;\n defaultParams?: Params | null | undefined;\n decodeParams?: ((params: Params) => Params) | null | undefined;\n encodeParams?: ((params: Params) => Params) | null | undefined;\n },\n): void {\n if (updates.forwardTo !== undefined) {\n store.resolvedForwardMap = updateForwardTo(\n name,\n updates.forwardTo,\n store.config,\n (config) => refreshForwardMap(config),\n );\n }\n\n if (updates.defaultParams !== undefined) {\n if (updates.defaultParams === null) {\n delete store.config.defaultParams[name];\n } else {\n store.config.defaultParams[name] = updates.defaultParams;\n }\n }\n\n if (updates.decodeParams !== undefined) {\n if (updates.decodeParams === null) {\n delete store.config.decoders[name];\n } else {\n const decoder = updates.decodeParams;\n\n store.config.decoders[name] = (params: Params): Params =>\n (decoder(params) as Params | undefined) ?? params;\n }\n }\n\n if (updates.encodeParams !== undefined) {\n if (updates.encodeParams === null) {\n delete store.config.encoders[name];\n } else {\n const encoder = updates.encodeParams;\n\n store.config.encoders[name] = (params: Params): Params =>\n (encoder(params) as Params | undefined) ?? params;\n }\n }\n}\n\n/**\n * Gets a route by name with all its configuration.\n */\nfunction getRoute<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n store: RoutesStore<Dependencies>,\n name: string,\n): Route<Dependencies> | undefined {\n const segments = store.matcher.getSegmentsByName(name);\n\n if (!segments) {\n return undefined;\n }\n\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- segments is non-empty (checked above)\n const targetNode = segments.at(-1)! as RouteTree;\n const definition = store.treeOperations.nodeToDefinition(targetNode);\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion\n const factories = store.lifecycleNamespace!.getFactories();\n\n return enrichRoute(definition, name, store.config, factories);\n}\n\n// ============================================================================\n// API factory\n// ============================================================================\n\nexport function getRoutesApi<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(router: Router<Dependencies>): RoutesApi<Dependencies> {\n const ctx = getInternals(router);\n\n const store = ctx.routeGetStore();\n\n const interceptableAdd = createInterceptable(\n \"add\",\n (routeArray: Route<Dependencies>[], options?: { parent?: string }) => {\n addRoutes(store, routeArray, options?.parent);\n },\n ctx.interceptors,\n );\n\n return {\n add: (routes, options) => {\n throwIfDisposed(ctx.isDisposed);\n\n const routeArray = Array.isArray(routes) ? routes : [routes];\n const parentName = options?.parent;\n\n guardRouteStructure(routeArray, ctx.validator);\n\n if (parentName !== undefined) {\n ctx.validator?.routes.validateParentOption(parentName, store.tree);\n }\n\n ctx.validator?.routes.throwIfInternalRouteInArray(routeArray, \"addRoute\");\n ctx.validator?.routes.validateAddRouteArgs(routeArray);\n ctx.validator?.routes.validateRoutes(routeArray, store);\n\n interceptableAdd(\n routeArray,\n parentName === undefined ? undefined : { parent: parentName },\n );\n },\n\n remove: (name) => {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.routes.validateRemoveRouteArgs(name);\n ctx.validator?.routes.throwIfInternalRoute(name, \"removeRoute\");\n\n const canRemove = validateRemoveRoute(\n name,\n ctx.getStateName(),\n ctx.isTransitioning(),\n );\n\n if (!canRemove) {\n return;\n }\n\n const wasRemoved = removeRoute(store, name);\n\n if (!wasRemoved) {\n logger.warn(\n \"router.removeRoute\",\n `Route \"${name}\" not found. No changes made.`,\n );\n }\n },\n\n update: (name, updates) => {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.routes.validateUpdateRouteBasicArgs(name, updates);\n ctx.validator?.routes.throwIfInternalRoute(name, \"updateRoute\");\n\n const {\n forwardTo,\n defaultParams,\n decodeParams,\n encodeParams,\n canActivate,\n canDeactivate,\n } = updates;\n\n ctx.validator?.routes.validateUpdateRoutePropertyTypes(name, updates);\n\n /* v8 ignore next 6 -- @preserve: race condition guard, mirrors Router.updateRoute() same-path guard tested via Router.ts unit tests */\n if (ctx.isTransitioning()) {\n logger.error(\n \"router.updateRoute\",\n `Updating route \"${name}\" while navigation is in progress. This may cause unexpected behavior.`,\n );\n }\n\n ctx.validator?.routes.validateUpdateRoute(name, updates, store);\n\n updateRouteConfig(store, name, {\n forwardTo,\n defaultParams,\n decodeParams,\n encodeParams,\n });\n\n if (canActivate !== undefined) {\n if (canActivate === null) {\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- guaranteed set after wiring\n store.lifecycleNamespace!.clearCanActivate(name);\n } else {\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- guaranteed set after wiring\n store.lifecycleNamespace!.addCanActivate(name, canActivate, true);\n }\n }\n\n if (canDeactivate !== undefined) {\n if (canDeactivate === null) {\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- guaranteed set after wiring\n store.lifecycleNamespace!.clearCanDeactivate(name);\n } else {\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- guaranteed set after wiring\n store.lifecycleNamespace!.addCanDeactivate(name, canDeactivate, true);\n }\n }\n },\n\n clear: () => {\n throwIfDisposed(ctx.isDisposed);\n\n const canClear = validateClearRoutes(ctx.isTransitioning());\n\n /* v8 ignore next 3 -- @preserve: race condition guard, mirrors Router.clearRoutes() same-path guard tested via validateClearRoutes unit tests */\n if (!canClear) {\n return;\n }\n\n store.treeOperations.resetStore(store);\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- guaranteed set after wiring\n store.lifecycleNamespace!.clearAll();\n ctx.clearState();\n },\n\n has: (name) => {\n ctx.validator?.routes.validateRouteName(name, \"hasRoute\");\n\n return store.matcher.hasRoute(name);\n },\n\n get: (name) => {\n ctx.validator?.routes.validateRouteName(name, \"getRoute\");\n\n return getRoute(store, name);\n },\n\n replace: (routes) => {\n throwIfDisposed(ctx.isDisposed);\n\n const routeArray = Array.isArray(routes) ? routes : [routes];\n\n const canReplace = validateClearRoutes(ctx.isTransitioning());\n\n if (!canReplace) {\n return;\n }\n\n guardRouteStructure(routeArray, ctx.validator);\n\n ctx.validator?.routes.throwIfInternalRouteInArray(\n routeArray,\n \"replaceRoutes\",\n );\n ctx.validator?.routes.validateAddRouteArgs(routeArray);\n ctx.validator?.routes.validateRoutes(routeArray, store);\n\n const currentState = router.getState();\n\n replaceRoutes(\n store,\n routeArray,\n ctx,\n currentState?.path,\n currentState?.transition,\n );\n },\n };\n}\n","import { throwIfDisposed } from \"./helpers\";\nimport { getInternals } from \"../internals\";\n\nimport type { DependenciesApi } from \"./types\";\nimport type { DependenciesStore } from \"../namespaces\";\nimport type { RouterValidator } from \"../types/RouterValidator\";\nimport type { DefaultDependencies, Router } from \"@real-router/types\";\n\n// =============================================================================\n// Module-private CRUD functions\n// =============================================================================\n\nfunction setDependency(\n store: DependenciesStore,\n dependencyName: string,\n dependencyValue: unknown,\n validator?: RouterValidator | null,\n): boolean {\n // undefined = \"don't set\" (feature for conditional setting)\n if (dependencyValue === undefined) {\n return false;\n }\n\n const isNewKey = !Object.hasOwn(store.dependencies, dependencyName);\n\n if (isNewKey) {\n // Only check limit when adding new keys (overwrites don't increase count)\n validator?.dependencies.validateDependencyCount(store, \"setDependency\");\n } else {\n const oldValue = (store.dependencies as Record<string, unknown>)[\n dependencyName\n ];\n const isChanging = oldValue !== dependencyValue;\n // Special case for NaN idempotency (NaN !== NaN is always true)\n const bothAreNaN = Number.isNaN(oldValue) && Number.isNaN(dependencyValue);\n\n if (isChanging && !bothAreNaN) {\n validator?.dependencies.warnOverwrite(dependencyName, \"setDependency\");\n }\n }\n\n (store.dependencies as Record<string, unknown>)[dependencyName] =\n dependencyValue;\n\n return true;\n}\n\nfunction setMultipleDependencies(\n store: DependenciesStore,\n deps: Record<string, unknown>,\n validator?: RouterValidator | null,\n): void {\n const overwrittenKeys: string[] = [];\n\n for (const key in deps) {\n if (deps[key] !== undefined) {\n if (Object.hasOwn(store.dependencies, key)) {\n overwrittenKeys.push(key);\n } else {\n validator?.dependencies.validateDependencyCount(\n store,\n \"setDependencies\",\n );\n }\n\n (store.dependencies as Record<string, unknown>)[key] = deps[key];\n }\n }\n\n if (overwrittenKeys.length > 0) {\n validator?.dependencies.warnBatchOverwrite(\n overwrittenKeys,\n \"setDependencies\",\n );\n }\n}\n\n// =============================================================================\n// Public API factory\n// =============================================================================\n\nexport function getDependenciesApi<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(router: Router<Dependencies>): DependenciesApi<Dependencies> {\n const ctx = getInternals(router);\n\n return {\n get: (name) => {\n ctx.validator?.dependencies.validateDependencyName(name, \"getDependency\");\n\n const store = ctx.dependenciesGetStore();\n const value = (store.dependencies as Record<string, unknown>)[\n name as string\n ];\n\n ctx.validator?.dependencies.validateDependencyExists(\n name as string,\n store,\n );\n\n return value as Dependencies[typeof name];\n },\n getAll: () => ({ ...ctx.dependenciesGetStore().dependencies }),\n set: (name, value) => {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.dependencies.validateSetDependencyArgs(\n name,\n value,\n \"setDependency\",\n );\n\n setDependency(\n ctx.dependenciesGetStore(),\n name as string,\n value,\n ctx.validator,\n );\n },\n setAll: (deps) => {\n throwIfDisposed(ctx.isDisposed);\n\n const store = ctx.dependenciesGetStore();\n\n ctx.validator?.dependencies.validateDependenciesObject(\n deps,\n \"setDependencies\",\n );\n ctx.validator?.dependencies.validateDependencyLimit(store, store.limits);\n\n setMultipleDependencies(\n store,\n deps as Record<string, unknown>,\n ctx.validator,\n );\n },\n remove: (name) => {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.dependencies.validateDependencyName(\n name,\n \"removeDependency\",\n );\n\n const store = ctx.dependenciesGetStore();\n\n if (!Object.hasOwn(store.dependencies, name as string)) {\n ctx.validator?.dependencies.warnRemoveNonExistent(name);\n }\n\n delete (store.dependencies as Record<string, unknown>)[name as string];\n },\n reset: () => {\n throwIfDisposed(ctx.isDisposed);\n const store = ctx.dependenciesGetStore();\n\n store.dependencies = Object.create(null) as Partial<Dependencies>;\n },\n has: (name) => {\n ctx.validator?.dependencies.validateDependencyName(name, \"hasDependency\");\n\n return Object.hasOwn(\n ctx.dependenciesGetStore().dependencies,\n name as string,\n );\n },\n };\n}\n","import { throwIfDisposed } from \"./helpers\";\nimport { getInternals } from \"../internals\";\n\nimport type { LifecycleApi } from \"./types\";\nimport type { DefaultDependencies, Router } from \"@real-router/types\";\n\nexport function getLifecycleApi<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(router: Router<Dependencies>): LifecycleApi<Dependencies> {\n const ctx = getInternals(router);\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- guaranteed set after wiring\n const lifecycleNamespace = ctx.routeGetStore().lifecycleNamespace!;\n\n return {\n addActivateGuard(name, handler) {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.routes.validateRouteName(name, \"addActivateGuard\");\n ctx.validator?.lifecycle.validateHandler(handler, \"addActivateGuard\");\n\n const activateCount = lifecycleNamespace.getHandlerCount(\"activate\");\n\n ctx.validator?.lifecycle.validateHandlerLimit(\n activateCount,\n ctx.dependenciesGetStore().limits,\n \"canActivate\",\n );\n\n lifecycleNamespace.addCanActivate(name, handler);\n },\n\n addDeactivateGuard(name, handler) {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.routes.validateRouteName(name, \"addDeactivateGuard\");\n ctx.validator?.lifecycle.validateHandler(handler, \"addDeactivateGuard\");\n\n const deactivateCount = lifecycleNamespace.getHandlerCount(\"deactivate\");\n\n ctx.validator?.lifecycle.validateHandlerLimit(\n deactivateCount,\n ctx.dependenciesGetStore().limits,\n \"canDeactivate\",\n );\n\n lifecycleNamespace.addCanDeactivate(name, handler);\n },\n\n removeActivateGuard(name) {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.routes.validateRouteName(name, \"removeActivateGuard\");\n\n lifecycleNamespace.clearCanActivate(name);\n },\n\n removeDeactivateGuard(name) {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.routes.validateRouteName(name, \"removeDeactivateGuard\");\n\n lifecycleNamespace.clearCanDeactivate(name);\n },\n };\n}\n","import { routeTreeToDefinitions } from \"route-tree\";\n\nimport { errorCodes } from \"../constants\";\nimport { getInternals } from \"../internals\";\nimport { Router as RouterClass } from \"../Router\";\nimport { RouterError } from \"../RouterError\";\nimport { getLifecycleApi } from \"./getLifecycleApi\";\n\nimport type { Route } from \"../types\";\nimport type { DefaultDependencies, Router } from \"@real-router/types\";\n\nexport function cloneRouter<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n router: Router<Dependencies>,\n dependencies?: Dependencies,\n): RouterClass<Dependencies> {\n const ctx = getInternals(router);\n\n if (ctx.isDisposed()) {\n throw new RouterError(errorCodes.ROUTER_DISPOSED);\n }\n\n ctx.validator?.dependencies.validateCloneArgs(dependencies);\n\n // Get source store directly\n const sourceStore = ctx.routeGetStore();\n const routes = routeTreeToDefinitions(sourceStore.tree);\n const routeConfig = sourceStore.config;\n const resolvedForwardMap = sourceStore.resolvedForwardMap;\n const routeCustomFields = sourceStore.routeCustomFields;\n\n const options = ctx.cloneOptions();\n const sourceDeps = ctx.cloneDependencies();\n const [canDeactivateFactories, canActivateFactories] =\n ctx.getLifecycleFactories();\n const pluginFactories = ctx.getPluginFactories();\n\n const mergedDeps = {\n ...sourceDeps,\n ...dependencies,\n } as Dependencies;\n\n const newRouter = new RouterClass<Dependencies>(\n routes as Route<Dependencies>[],\n options,\n mergedDeps,\n );\n\n const lifecycle = getLifecycleApi(newRouter);\n\n for (const [name, handler] of Object.entries(canDeactivateFactories)) {\n lifecycle.addDeactivateGuard(name, handler);\n }\n\n for (const [name, handler] of Object.entries(canActivateFactories)) {\n lifecycle.addActivateGuard(name, handler);\n }\n\n if (pluginFactories.length > 0) {\n newRouter.usePlugin(...pluginFactories);\n }\n\n const newCtx = getInternals(newRouter);\n const newStore = newCtx.routeGetStore();\n\n // Apply cloned config directly to new store\n Object.assign(newStore.config.decoders, routeConfig.decoders);\n Object.assign(newStore.config.encoders, routeConfig.encoders);\n Object.assign(newStore.config.defaultParams, routeConfig.defaultParams);\n Object.assign(newStore.config.forwardMap, routeConfig.forwardMap);\n Object.assign(newStore.config.forwardFnMap, routeConfig.forwardFnMap);\n Object.assign(newStore.resolvedForwardMap, resolvedForwardMap);\n Object.assign(newStore.routeCustomFields, routeCustomFields);\n\n return newRouter;\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"api.mjs","names":[],"sources":["../../src/namespaces/RoutesNamespace/routeGuards.ts","../../src/api/getRoutesApi.ts","../../src/api/getDependenciesApi.ts"],"sourcesContent":["import { logger } from \"@real-router/logger\";\n\n/**\n * Validates removeRoute constraints.\n * Returns false if removal should be blocked (route is active).\n * Logs warnings for edge cases.\n *\n * @param name - Route name to remove\n * @param currentStateName - Current active route name (or undefined)\n * @param isNavigating - Whether navigation is in progress\n * @returns true if removal can proceed, false if blocked\n */\nexport function validateRemoveRoute(\n name: string,\n currentStateName: string | undefined,\n isNavigating: boolean,\n): boolean {\n if (currentStateName) {\n const isExactMatch = currentStateName === name;\n const isParentOfCurrent = currentStateName.startsWith(`${name}.`);\n\n if (isExactMatch || isParentOfCurrent) {\n const suffix = isExactMatch ? \"\" : ` (current: \"${currentStateName}\")`;\n\n logger.warn(\n \"router.removeRoute\",\n `Cannot remove route \"${name}\" — it is currently active${suffix}. Navigate away first.`,\n );\n\n return false;\n }\n }\n\n if (isNavigating) {\n logger.warn(\n \"router.removeRoute\",\n `Route \"${name}\" removed while navigation is in progress. This may cause unexpected behavior.`,\n );\n }\n\n return true;\n}\n\n/**\n * Validates clearRoutes operation.\n * Returns false if operation should be blocked (navigation in progress).\n *\n * @param isNavigating - Whether navigation is in progress\n * @returns true if clearRoutes can proceed, false if blocked\n */\nexport function validateClearRoutes(isNavigating: boolean): boolean {\n if (isNavigating) {\n logger.error(\n \"router.clearRoutes\",\n \"Cannot clear routes while navigation is in progress. Wait for navigation to complete.\",\n );\n\n return false;\n }\n\n return true;\n}\n","import { logger } from \"@real-router/logger\";\n\nimport { throwIfDisposed } from \"./helpers\";\nimport { guardRouteStructure } from \"../guards\";\nimport { createInterceptable, getInternals } from \"../internals\";\nimport {\n clearConfigEntries,\n removeFromDefinitions,\n sanitizeRoute,\n} from \"../namespaces/RoutesNamespace/helpers\";\nimport {\n validateClearRoutes,\n validateRemoveRoute,\n} from \"../namespaces/RoutesNamespace/routeGuards\";\nimport {\n clearRouteData,\n refreshForwardMap,\n registerAllRouteHandlers,\n} from \"../namespaces/RoutesNamespace/routesStore\";\n\nimport type { RoutesApi } from \"./types\";\nimport type { RouterInternals } from \"../internals\";\nimport type { RouteLifecycleNamespace, RouteConfig } from \"../namespaces\";\nimport type { RoutesStore } from \"../namespaces/RoutesNamespace\";\nimport type { GuardFnFactory, Route } from \"../types\";\nimport type {\n DefaultDependencies,\n ForwardToCallback,\n Params,\n Router,\n TransitionMeta,\n} from \"@real-router/types\";\nimport type { RouteDefinition, RouteTree } from \"route-tree\";\n\n// ============================================================================\n// Helpers\n// ============================================================================\n\n/**\n * Recursively finds a route definition by its full dotted name.\n */\nfunction findDefinition(\n definitions: RouteDefinition[],\n fullName: string,\n parentPrefix = \"\",\n): RouteDefinition | undefined {\n for (const def of definitions) {\n const currentFullName = parentPrefix\n ? `${parentPrefix}.${def.name}`\n : def.name;\n\n if (currentFullName === fullName) {\n return def;\n }\n\n if (def.children && fullName.startsWith(`${currentFullName}.`)) {\n return findDefinition(def.children, fullName, currentFullName);\n }\n }\n\n /* v8 ignore next -- @preserve: defensive return, callers validate route exists before calling */\n return undefined;\n}\n\n/**\n * Clears all config entries and lifecycle handlers for a removed route\n * (and all its descendants).\n */\nfunction clearRouteConfigurations<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n routeName: string,\n config: RouteConfig,\n routeCustomFields: Record<string, Record<string, unknown>>,\n lifecycleNamespace: RouteLifecycleNamespace<Dependencies>,\n): void {\n const shouldClear = (name: string): boolean =>\n name === routeName || name.startsWith(`${routeName}.`);\n\n clearConfigEntries(config.decoders, shouldClear);\n clearConfigEntries(config.encoders, shouldClear);\n clearConfigEntries(config.defaultParams, shouldClear);\n clearConfigEntries(config.forwardMap, shouldClear);\n clearConfigEntries(config.forwardFnMap, shouldClear);\n clearConfigEntries(routeCustomFields, shouldClear);\n\n // Clear forwardMap entries pointing TO the deleted route (or its descendants)\n clearConfigEntries(config.forwardMap, (key) =>\n shouldClear(config.forwardMap[key]),\n );\n\n // Clear lifecycle handlers\n const [canDeactivateFactories, canActivateFactories] =\n lifecycleNamespace.getFactories();\n\n for (const name of Object.keys(canActivateFactories)) {\n if (shouldClear(name)) {\n lifecycleNamespace.clearCanActivate(name);\n }\n }\n\n for (const name of Object.keys(canDeactivateFactories)) {\n if (shouldClear(name)) {\n lifecycleNamespace.clearCanDeactivate(name);\n }\n }\n}\n\n/**\n * Updates forwardTo for a route in config and returns the refreshed resolved\n * forward map (REPLACE semantics — caller must call ctx.setResolvedForwardMap).\n */\nfunction updateForwardTo<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n name: string,\n forwardTo: string | ForwardToCallback<Dependencies> | null,\n config: RouteConfig,\n refreshForwardMapFn: (config: RouteConfig) => Record<string, string>,\n): Record<string, string> {\n if (forwardTo === null) {\n delete config.forwardMap[name];\n delete config.forwardFnMap[name];\n } else if (typeof forwardTo === \"string\") {\n delete config.forwardFnMap[name];\n config.forwardMap[name] = forwardTo;\n } else {\n delete config.forwardMap[name];\n config.forwardFnMap[name] = forwardTo;\n }\n\n return refreshForwardMapFn(config);\n}\n\n/**\n * Builds a full Route object from a bare RouteDefinition by re-attaching\n * config entries and lifecycle factories.\n *\n * RECURSIVE — call with the factories tuple obtained ONCE from\n * `lifecycleNamespace.getFactories()` and pass it through to children.\n */\nfunction enrichRoute<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n routeDef: RouteDefinition,\n routeName: string,\n config: RouteConfig,\n factories: [\n Record<string, GuardFnFactory<Dependencies>>,\n Record<string, GuardFnFactory<Dependencies>>,\n ],\n): Route<Dependencies> {\n const route: Route<Dependencies> = {\n name: routeDef.name,\n path: routeDef.path,\n };\n\n const forwardToFn = config.forwardFnMap[routeName];\n const forwardToStr = config.forwardMap[routeName];\n\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n if (forwardToFn !== undefined) {\n route.forwardTo = forwardToFn;\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n } else if (forwardToStr !== undefined) {\n route.forwardTo = forwardToStr;\n }\n\n if (routeName in config.defaultParams) {\n route.defaultParams = config.defaultParams[routeName];\n }\n\n if (routeName in config.decoders) {\n route.decodeParams = config.decoders[routeName];\n }\n\n if (routeName in config.encoders) {\n route.encodeParams = config.encoders[routeName];\n }\n\n const [canDeactivateFactories, canActivateFactories] = factories;\n\n if (routeName in canActivateFactories) {\n route.canActivate = canActivateFactories[routeName];\n }\n\n if (routeName in canDeactivateFactories) {\n route.canDeactivate = canDeactivateFactories[routeName];\n }\n\n if (routeDef.children) {\n route.children = routeDef.children.map((child) =>\n enrichRoute(child, `${routeName}.${child.name}`, config, factories),\n );\n }\n\n return route;\n}\n\n// ============================================================================\n// CRUD operations\n// ============================================================================\n\n/**\n * Adds one or more routes to the router.\n * Input already validated by facade.\n */\nfunction addRoutes<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n store: RoutesStore<Dependencies>,\n routes: Route<Dependencies>[],\n parentName?: string,\n): void {\n if (parentName) {\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion\n const parentDef = findDefinition(store.definitions, parentName)!;\n\n parentDef.children ??= [];\n\n for (const route of routes) {\n parentDef.children.push(sanitizeRoute(route));\n }\n } else {\n for (const route of routes) {\n store.definitions.push(sanitizeRoute(route));\n }\n }\n\n registerAllRouteHandlers(\n routes,\n store.config,\n store.routeCustomFields,\n store.pendingCanActivate,\n store.pendingCanDeactivate,\n store.depsStore,\n parentName ?? \"\",\n );\n\n store.treeOperations.commitTreeChanges(store);\n}\n\n/**\n * Atomically replaces all routes with a new set.\n * Follows RFC 6-step semantics for HMR support.\n */\nfunction replaceRoutes<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n store: RoutesStore<Dependencies>,\n routes: Route<Dependencies>[],\n ctx: RouterInternals<Dependencies>,\n currentPath: string | undefined,\n previousTransition: TransitionMeta | undefined,\n): void {\n // Step 2: Clear route data (WITHOUT tree rebuild)\n clearRouteData(store);\n\n // Step 3: Clear definition lifecycle handlers (preserve external guards)\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- guaranteed set after wiring\n store.lifecycleNamespace!.clearDefinitionGuards();\n\n // Step 4: Register new routes\n for (const route of routes) {\n store.definitions.push(sanitizeRoute(route));\n }\n\n registerAllRouteHandlers(\n routes,\n store.config,\n store.routeCustomFields,\n store.pendingCanActivate,\n store.pendingCanDeactivate,\n store.depsStore,\n \"\",\n );\n\n // Step 5: One tree rebuild\n store.treeOperations.commitTreeChanges(store);\n\n // Step 6: Revalidate state (preserve transition from previous state)\n if (currentPath !== undefined) {\n const revalidated = ctx.matchPath(currentPath, ctx.getOptions());\n\n if (revalidated) {\n ctx.setState({\n ...revalidated,\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- previousTransition is guaranteed defined: currentPath is only set when getState() returned a state, which always has transition\n transition: previousTransition!,\n });\n } else {\n ctx.clearState();\n }\n }\n}\n\n/**\n * Removes a route and all its children.\n *\n * @returns true if removed, false if not found\n */\nfunction removeRoute<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(store: RoutesStore<Dependencies>, name: string): boolean {\n const wasRemoved = removeFromDefinitions(store.definitions, name);\n\n if (!wasRemoved) {\n return false;\n }\n\n clearRouteConfigurations(\n name,\n store.config,\n store.routeCustomFields,\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion\n store.lifecycleNamespace!,\n );\n\n store.treeOperations.commitTreeChanges(store);\n\n return true;\n}\n\n/**\n * Updates a route's configuration in place.\n */\nfunction updateRouteConfig<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n store: RoutesStore<Dependencies>,\n name: string,\n updates: {\n forwardTo?: string | ForwardToCallback<Dependencies> | null | undefined;\n defaultParams?: Params | null | undefined;\n decodeParams?: ((params: Params) => Params) | null | undefined;\n encodeParams?: ((params: Params) => Params) | null | undefined;\n },\n): void {\n if (updates.forwardTo !== undefined) {\n store.resolvedForwardMap = updateForwardTo(\n name,\n updates.forwardTo,\n store.config,\n (config) => refreshForwardMap(config),\n );\n }\n\n if (updates.defaultParams !== undefined) {\n if (updates.defaultParams === null) {\n delete store.config.defaultParams[name];\n } else {\n store.config.defaultParams[name] = updates.defaultParams;\n }\n }\n\n if (updates.decodeParams !== undefined) {\n if (updates.decodeParams === null) {\n delete store.config.decoders[name];\n } else {\n const decoder = updates.decodeParams;\n\n store.config.decoders[name] = (params: Params): Params =>\n (decoder(params) as Params | undefined) ?? params;\n }\n }\n\n if (updates.encodeParams !== undefined) {\n if (updates.encodeParams === null) {\n delete store.config.encoders[name];\n } else {\n const encoder = updates.encodeParams;\n\n store.config.encoders[name] = (params: Params): Params =>\n (encoder(params) as Params | undefined) ?? params;\n }\n }\n}\n\n/**\n * Gets a route by name with all its configuration.\n */\nfunction getRoute<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n store: RoutesStore<Dependencies>,\n name: string,\n): Route<Dependencies> | undefined {\n const segments = store.matcher.getSegmentsByName(name);\n\n if (!segments) {\n return undefined;\n }\n\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- segments is non-empty (checked above)\n const targetNode = segments.at(-1)! as RouteTree;\n const definition = store.treeOperations.nodeToDefinition(targetNode);\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion\n const factories = store.lifecycleNamespace!.getFactories();\n\n return enrichRoute(definition, name, store.config, factories);\n}\n\n// ============================================================================\n// API factory\n// ============================================================================\n\nexport function getRoutesApi<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(router: Router<Dependencies>): RoutesApi<Dependencies> {\n const ctx = getInternals(router);\n\n const store = ctx.routeGetStore();\n\n const interceptableAdd = createInterceptable(\n \"add\",\n (routeArray: Route<Dependencies>[], options?: { parent?: string }) => {\n addRoutes(store, routeArray, options?.parent);\n },\n ctx.interceptors,\n );\n\n return {\n add: (routes, options) => {\n throwIfDisposed(ctx.isDisposed);\n\n const routeArray = Array.isArray(routes) ? routes : [routes];\n const parentName = options?.parent;\n\n guardRouteStructure(routeArray, ctx.validator);\n\n if (parentName !== undefined) {\n ctx.validator?.routes.validateParentOption(parentName, store.tree);\n }\n\n ctx.validator?.routes.throwIfInternalRouteInArray(routeArray, \"addRoute\");\n ctx.validator?.routes.validateAddRouteArgs(routeArray);\n ctx.validator?.routes.validateRoutes(routeArray, store);\n\n interceptableAdd(\n routeArray,\n parentName === undefined ? undefined : { parent: parentName },\n );\n },\n\n remove: (name) => {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.routes.validateRemoveRouteArgs(name);\n ctx.validator?.routes.throwIfInternalRoute(name, \"removeRoute\");\n\n const canRemove = validateRemoveRoute(\n name,\n ctx.getStateName(),\n ctx.isTransitioning(),\n );\n\n if (!canRemove) {\n return;\n }\n\n const wasRemoved = removeRoute(store, name);\n\n if (!wasRemoved) {\n logger.warn(\n \"router.removeRoute\",\n `Route \"${name}\" not found. No changes made.`,\n );\n }\n },\n\n update: (name, updates) => {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.routes.validateUpdateRouteBasicArgs(name, updates);\n ctx.validator?.routes.throwIfInternalRoute(name, \"updateRoute\");\n\n const {\n forwardTo,\n defaultParams,\n decodeParams,\n encodeParams,\n canActivate,\n canDeactivate,\n } = updates;\n\n ctx.validator?.routes.validateUpdateRoutePropertyTypes(name, updates);\n\n /* v8 ignore next 6 -- @preserve: race condition guard, mirrors Router.updateRoute() same-path guard tested via Router.ts unit tests */\n if (ctx.isTransitioning()) {\n logger.error(\n \"router.updateRoute\",\n `Updating route \"${name}\" while navigation is in progress. This may cause unexpected behavior.`,\n );\n }\n\n ctx.validator?.routes.validateUpdateRoute(name, updates, store);\n\n updateRouteConfig(store, name, {\n forwardTo,\n defaultParams,\n decodeParams,\n encodeParams,\n });\n\n if (canActivate !== undefined) {\n if (canActivate === null) {\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- guaranteed set after wiring\n store.lifecycleNamespace!.clearCanActivate(name);\n } else {\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- guaranteed set after wiring\n store.lifecycleNamespace!.addCanActivate(name, canActivate, true);\n }\n }\n\n if (canDeactivate !== undefined) {\n if (canDeactivate === null) {\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- guaranteed set after wiring\n store.lifecycleNamespace!.clearCanDeactivate(name);\n } else {\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- guaranteed set after wiring\n store.lifecycleNamespace!.addCanDeactivate(name, canDeactivate, true);\n }\n }\n },\n\n clear: () => {\n throwIfDisposed(ctx.isDisposed);\n\n const canClear = validateClearRoutes(ctx.isTransitioning());\n\n /* v8 ignore next 3 -- @preserve: race condition guard, mirrors Router.clearRoutes() same-path guard tested via validateClearRoutes unit tests */\n if (!canClear) {\n return;\n }\n\n store.treeOperations.resetStore(store);\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- guaranteed set after wiring\n store.lifecycleNamespace!.clearAll();\n ctx.clearState();\n },\n\n has: (name) => {\n ctx.validator?.routes.validateRouteName(name, \"hasRoute\");\n\n return store.matcher.hasRoute(name);\n },\n\n get: (name) => {\n ctx.validator?.routes.validateRouteName(name, \"getRoute\");\n\n return getRoute(store, name);\n },\n\n replace: (routes) => {\n throwIfDisposed(ctx.isDisposed);\n\n const routeArray = Array.isArray(routes) ? routes : [routes];\n\n const canReplace = validateClearRoutes(ctx.isTransitioning());\n\n if (!canReplace) {\n return;\n }\n\n guardRouteStructure(routeArray, ctx.validator);\n\n ctx.validator?.routes.throwIfInternalRouteInArray(\n routeArray,\n \"replaceRoutes\",\n );\n ctx.validator?.routes.validateAddRouteArgs(routeArray);\n ctx.validator?.routes.validateRoutes(routeArray, store);\n\n const currentState = router.getState();\n\n replaceRoutes(\n store,\n routeArray,\n ctx,\n currentState?.path,\n currentState?.transition,\n );\n },\n };\n}\n","import { throwIfDisposed } from \"./helpers\";\nimport { getInternals } from \"../internals\";\n\nimport type { DependenciesApi } from \"./types\";\nimport type { DependenciesStore } from \"../namespaces\";\nimport type { RouterValidator } from \"../types/RouterValidator\";\nimport type { DefaultDependencies, Router } from \"@real-router/types\";\n\n// =============================================================================\n// Module-private CRUD functions\n// =============================================================================\n\nfunction setDependency(\n store: DependenciesStore,\n dependencyName: string,\n dependencyValue: unknown,\n validator?: RouterValidator | null,\n): boolean {\n // undefined = \"don't set\" (feature for conditional setting)\n if (dependencyValue === undefined) {\n return false;\n }\n\n const isNewKey = !Object.hasOwn(store.dependencies, dependencyName);\n\n if (isNewKey) {\n // Only check limit when adding new keys (overwrites don't increase count)\n validator?.dependencies.validateDependencyCount(store, \"setDependency\");\n } else {\n const oldValue = (store.dependencies as Record<string, unknown>)[\n dependencyName\n ];\n const isChanging = oldValue !== dependencyValue;\n // Special case for NaN idempotency (NaN !== NaN is always true)\n const bothAreNaN = Number.isNaN(oldValue) && Number.isNaN(dependencyValue);\n\n if (isChanging && !bothAreNaN) {\n validator?.dependencies.warnOverwrite(dependencyName, \"setDependency\");\n }\n }\n\n (store.dependencies as Record<string, unknown>)[dependencyName] =\n dependencyValue;\n\n return true;\n}\n\nfunction setMultipleDependencies(\n store: DependenciesStore,\n deps: Record<string, unknown>,\n validator?: RouterValidator | null,\n): void {\n const overwrittenKeys: string[] = [];\n\n for (const key in deps) {\n if (deps[key] !== undefined) {\n if (Object.hasOwn(store.dependencies, key)) {\n overwrittenKeys.push(key);\n } else {\n validator?.dependencies.validateDependencyCount(\n store,\n \"setDependencies\",\n );\n }\n\n (store.dependencies as Record<string, unknown>)[key] = deps[key];\n }\n }\n\n if (overwrittenKeys.length > 0) {\n validator?.dependencies.warnBatchOverwrite(\n overwrittenKeys,\n \"setDependencies\",\n );\n }\n}\n\n// =============================================================================\n// Public API factory\n// =============================================================================\n\nexport function getDependenciesApi<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(router: Router<Dependencies>): DependenciesApi<Dependencies> {\n const ctx = getInternals(router);\n\n return {\n get: (name) => {\n ctx.validator?.dependencies.validateDependencyName(name, \"getDependency\");\n\n const store = ctx.dependenciesGetStore();\n const value = (store.dependencies as Record<string, unknown>)[\n name as string\n ];\n\n ctx.validator?.dependencies.validateDependencyExists(\n name as string,\n store,\n );\n\n return value as Dependencies[typeof name];\n },\n getAll: () => ({ ...ctx.dependenciesGetStore().dependencies }),\n set: (name, value) => {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.dependencies.validateSetDependencyArgs(\n name,\n value,\n \"setDependency\",\n );\n\n setDependency(\n ctx.dependenciesGetStore(),\n name as string,\n value,\n ctx.validator,\n );\n },\n setAll: (deps) => {\n throwIfDisposed(ctx.isDisposed);\n\n const store = ctx.dependenciesGetStore();\n\n ctx.validator?.dependencies.validateDependenciesObject(\n deps,\n \"setDependencies\",\n );\n ctx.validator?.dependencies.validateDependencyLimit(store, store.limits);\n\n setMultipleDependencies(\n store,\n deps as Record<string, unknown>,\n ctx.validator,\n );\n },\n remove: (name) => {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.dependencies.validateDependencyName(\n name,\n \"removeDependency\",\n );\n\n const store = ctx.dependenciesGetStore();\n\n if (!Object.hasOwn(store.dependencies, name as string)) {\n ctx.validator?.dependencies.warnRemoveNonExistent(name);\n }\n\n delete (store.dependencies as Record<string, unknown>)[name as string];\n },\n reset: () => {\n throwIfDisposed(ctx.isDisposed);\n const store = ctx.dependenciesGetStore();\n\n store.dependencies = Object.create(null) as Partial<Dependencies>;\n },\n has: (name) => {\n ctx.validator?.dependencies.validateDependencyName(name, \"hasDependency\");\n\n return Object.hasOwn(\n ctx.dependenciesGetStore().dependencies,\n name as string,\n );\n },\n };\n}\n"],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ import{m as e,n as t,t as n,u as r}from"./Router-DRM2Fd06.mjs";import{r as i}from"./internals-C59msvHY.mjs";function a(n){if(n())throw new t(e.ROUTER_DISPOSED)}const o=new WeakMap;function s(n){let r=o.get(n);if(r)return r;let s=i(n),c={makeState:(e,t,n,r)=>(s.validator?.state.validateMakeStateArgs(e,t,n),s.makeState(e,t,n,r?.params)),buildState:(e,t)=>{s.validator?.routes.validateStateBuilderArgs(e,t,`buildState`);let{name:n,params:r}=s.forwardState(e,t);return s.buildStateResolved(n,r)},forwardState:(e,t)=>(s.validator?.routes.validateStateBuilderArgs(e,t,`forwardState`),s.forwardState(e,t)),matchPath:e=>(s.validator?.routes.validateMatchPathArgs(e),s.matchPath(e,s.getOptions())),navigateToState:(e,t)=>(a(s.isDisposed),s.validator?.navigation.validateNavigateToStateArgs(e),t!==void 0&&s.validator?.navigation.validateNavigationOptions(t,`navigateToState`),s.navigateToState(e,t)),setRootPath:e=>{a(s.isDisposed),s.validator?.routes.validateSetRootPathArgs(e),s.setRootPath(e)},getRootPath:s.getRootPath,addEventListener:(e,t)=>(a(s.isDisposed),s.validator?.eventBus.validateListenerArgs(e,t),s.addEventListener(e,t)),buildNavigationState:(e,t={})=>{s.validator?.routes.validateStateBuilderArgs(e,t,`buildNavigationState`);let{name:n,params:r}=s.forwardState(e,t),i=s.buildStateResolved(n,r);if(i)return s.makeState(i.name,i.params,s.buildPath(i.name,i.params),i.meta)},getOptions:s.getOptions,getTree:s.getTree,addInterceptor:(e,t)=>{a(s.isDisposed),s.validator?.plugins.validateAddInterceptorArgs(e,t);let n=s.interceptors.get(e);return n||(n=[],s.interceptors.set(e,n)),n.push(t),()=>{let e=n.indexOf(t);e!==-1&&n.splice(e,1)}},getRouteConfig:e=>{let t=s.routeGetStore();if(t.matcher.hasRoute(e))return t.routeCustomFields[e]},extendRouter:r=>{a(s.isDisposed);let i=Object.keys(r);for(let r of i)if(r in n)throw new t(e.PLUGIN_CONFLICT,{message:`Cannot extend router: property "${r}" already exists`});for(let e of i)n[e]=r[e];let o={keys:i};s.routerExtensions.push(o);let c=!1;return()=>{if(c)return;c=!0;for(let e of o.keys)delete n[e];let e=s.routerExtensions.indexOf(o);e!==-1&&s.routerExtensions.splice(e,1)}},emitTransitionError:e=>{a(s.isDisposed),s.emitTransitionError(e)},claimContextNamespace:(n=>{if(a(s.isDisposed),s.contextClaimRecords.has(n))throw new t(e.CONTEXT_NAMESPACE_ALREADY_CLAIMED,{message:`Cannot claim context namespace: "${n}" is already claimed by another plugin`});return s.contextClaimRecords.add(n),{write(e,t){e.context[n]=t},release(){s.contextClaimRecords.delete(n)}}})};return o.set(n,c),c}function c(e){let t=i(e),n=t.routeGetStore().lifecycleNamespace;return{addActivateGuard(e,r){a(t.isDisposed),t.validator?.routes.validateRouteName(e,`addActivateGuard`),t.validator?.lifecycle.validateHandler(r,`addActivateGuard`);let i=n.getHandlerCount(`activate`);t.validator?.lifecycle.validateHandlerLimit(i,t.dependenciesGetStore().limits,`canActivate`),n.addCanActivate(e,r)},addDeactivateGuard(e,r){a(t.isDisposed),t.validator?.routes.validateRouteName(e,`addDeactivateGuard`),t.validator?.lifecycle.validateHandler(r,`addDeactivateGuard`);let i=n.getHandlerCount(`deactivate`);t.validator?.lifecycle.validateHandlerLimit(i,t.dependenciesGetStore().limits,`canDeactivate`),n.addCanDeactivate(e,r)},removeActivateGuard(e){a(t.isDisposed),t.validator?.routes.validateRouteName(e,`removeActivateGuard`),n.clearCanActivate(e)},removeDeactivateGuard(e){a(t.isDisposed),t.validator?.routes.validateRouteName(e,`removeDeactivateGuard`),n.clearCanDeactivate(e)}}}function l(a,o){let s=i(a);if(s.isDisposed())throw new t(e.ROUTER_DISPOSED);s.validator?.dependencies.validateCloneArgs(o);let l=s.routeGetStore(),u=r(l.tree),d=l.config,f=l.resolvedForwardMap,p=l.routeCustomFields,m=s.cloneOptions(),h=s.cloneDependencies(),[g,_]=s.getLifecycleFactories(),v=s.getPluginFactories(),y=new n(u,m,{...h,...o}),b=c(y);for(let[e,t]of Object.entries(g))b.addDeactivateGuard(e,t);for(let[e,t]of Object.entries(_))b.addActivateGuard(e,t);v.length>0&&y.usePlugin(...v);let x=i(y).routeGetStore();return Object.assign(x.config.decoders,d.decoders),Object.assign(x.config.encoders,d.encoders),Object.assign(x.config.defaultParams,d.defaultParams),Object.assign(x.config.forwardMap,d.forwardMap),Object.assign(x.config.forwardFnMap,d.forwardFnMap),Object.assign(x.resolvedForwardMap,f),Object.assign(x.routeCustomFields,p),y}export{a as i,c as n,s as r,l as t};
2
+ //# sourceMappingURL=cloneRouter-DdGGwYdL.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cloneRouter-DdGGwYdL.mjs","names":["routeTreeToDefinitions","RouterClass"],"sources":["../../src/api/helpers.ts","../../src/api/getPluginApi.ts","../../src/api/getLifecycleApi.ts","../../src/api/cloneRouter.ts"],"sourcesContent":["// packages/core/src/api/helpers.ts\n\nimport { errorCodes } from \"../constants\";\nimport { RouterError } from \"../RouterError\";\n\nexport function throwIfDisposed(isDisposed: () => boolean): void {\n if (isDisposed()) {\n throw new RouterError(errorCodes.ROUTER_DISPOSED);\n }\n}\n","import { throwIfDisposed } from \"./helpers\";\nimport { errorCodes } from \"../constants\";\nimport { getInternals } from \"../internals\";\nimport { RouterError } from \"../RouterError\";\n\nimport type { PluginApi } from \"./types\";\nimport type {\n ContextNamespaceClaim,\n DefaultDependencies,\n Params,\n Router,\n State,\n} from \"@real-router/types\";\n\n// Cache the assembled PluginApi per router — mirrors getNavigator() (#525):\n// avoids re-allocating the closure-bag on each call (plugins call this once\n// at init, but tests + nested plugins poll it), and gives spy/stub helpers\n// a stable object identity to attach to (e.g. spying on\n// `getPluginApi(router).navigateToState` to inject errors in popstate\n// recovery tests).\nconst cache = new WeakMap<object, PluginApi>();\n\nexport function getPluginApi<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(router: Router<Dependencies>): PluginApi {\n const cached = cache.get(router);\n\n if (cached) {\n return cached;\n }\n\n const ctx = getInternals(router);\n const api: PluginApi = {\n makeState: (name, params, path, meta) => {\n ctx.validator?.state.validateMakeStateArgs(name, params, path);\n\n return ctx.makeState(\n name,\n params,\n path,\n meta?.params as\n | Record<string, Record<string, \"url\" | \"query\">>\n | undefined,\n );\n },\n buildState: (routeName, routeParams) => {\n ctx.validator?.routes.validateStateBuilderArgs(\n routeName,\n routeParams,\n \"buildState\",\n );\n\n const { name, params } = ctx.forwardState(routeName, routeParams);\n\n return ctx.buildStateResolved(name, params);\n },\n forwardState: <P extends Params = Params>(\n routeName: string,\n routeParams: P,\n ) => {\n ctx.validator?.routes.validateStateBuilderArgs(\n routeName,\n routeParams,\n \"forwardState\",\n );\n\n return ctx.forwardState(routeName, routeParams);\n },\n matchPath: (path) => {\n ctx.validator?.routes.validateMatchPathArgs(path);\n\n return ctx.matchPath(path, ctx.getOptions());\n },\n navigateToState: (state, options) => {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.navigation.validateNavigateToStateArgs(state);\n\n if (options !== undefined) {\n ctx.validator?.navigation.validateNavigationOptions(\n options,\n \"navigateToState\",\n );\n }\n\n return ctx.navigateToState(state, options);\n },\n setRootPath: (rootPath) => {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.routes.validateSetRootPathArgs(rootPath);\n\n ctx.setRootPath(rootPath);\n },\n getRootPath: ctx.getRootPath,\n addEventListener: (eventName, cb) => {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.eventBus.validateListenerArgs(eventName, cb);\n\n return ctx.addEventListener(eventName, cb);\n },\n buildNavigationState: (name, params = {}) => {\n ctx.validator?.routes.validateStateBuilderArgs(\n name,\n params,\n \"buildNavigationState\",\n );\n\n const { name: resolvedName, params: resolvedParams } = ctx.forwardState(\n name,\n params,\n );\n const routeInfo = ctx.buildStateResolved(resolvedName, resolvedParams);\n\n if (!routeInfo) {\n return;\n }\n\n return ctx.makeState(\n routeInfo.name,\n routeInfo.params,\n ctx.buildPath(routeInfo.name, routeInfo.params),\n routeInfo.meta,\n );\n },\n getOptions: ctx.getOptions,\n getTree: ctx.getTree,\n addInterceptor: (method, fn) => {\n throwIfDisposed(ctx.isDisposed);\n ctx.validator?.plugins.validateAddInterceptorArgs(method, fn);\n let list = ctx.interceptors.get(method);\n\n if (!list) {\n list = [];\n ctx.interceptors.set(method, list);\n }\n\n list.push(fn);\n\n return () => {\n const index = list.indexOf(fn);\n\n if (index !== -1) {\n list.splice(index, 1);\n }\n };\n },\n getRouteConfig: (name) => {\n const store = ctx.routeGetStore();\n\n if (!store.matcher.hasRoute(name)) {\n return;\n }\n\n return store.routeCustomFields[name];\n },\n extendRouter: (extensions: Record<string, unknown>) => {\n throwIfDisposed(ctx.isDisposed);\n\n const keys = Object.keys(extensions);\n\n for (const key of keys) {\n if (key in router) {\n throw new RouterError(errorCodes.PLUGIN_CONFLICT, {\n message: `Cannot extend router: property \"${key}\" already exists`,\n });\n }\n }\n\n for (const key of keys) {\n (router as Record<string, unknown>)[key] = extensions[key];\n }\n\n const extensionRecord = { keys };\n\n ctx.routerExtensions.push(extensionRecord);\n\n let removed = false;\n\n return () => {\n if (removed) {\n return;\n }\n\n removed = true;\n\n for (const key of extensionRecord.keys) {\n delete (router as Record<string, unknown>)[key];\n }\n\n const idx = ctx.routerExtensions.indexOf(extensionRecord);\n\n if (idx !== -1) {\n ctx.routerExtensions.splice(idx, 1);\n }\n };\n },\n emitTransitionError: (error) => {\n throwIfDisposed(ctx.isDisposed);\n ctx.emitTransitionError(error);\n },\n claimContextNamespace: ((namespace: string) => {\n throwIfDisposed(ctx.isDisposed);\n\n if (ctx.contextClaimRecords.has(namespace)) {\n throw new RouterError(errorCodes.CONTEXT_NAMESPACE_ALREADY_CLAIMED, {\n message: `Cannot claim context namespace: \"${namespace}\" is already claimed by another plugin`,\n });\n }\n\n ctx.contextClaimRecords.add(namespace);\n\n return {\n write(state: State, value: unknown) {\n (state.context as Record<string, unknown>)[namespace] = value;\n },\n release() {\n ctx.contextClaimRecords.delete(namespace);\n },\n } satisfies ContextNamespaceClaim;\n }) as PluginApi[\"claimContextNamespace\"],\n };\n\n cache.set(router, api);\n\n return api;\n}\n","import { throwIfDisposed } from \"./helpers\";\nimport { getInternals } from \"../internals\";\n\nimport type { LifecycleApi } from \"./types\";\nimport type { DefaultDependencies, Router } from \"@real-router/types\";\n\nexport function getLifecycleApi<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(router: Router<Dependencies>): LifecycleApi<Dependencies> {\n const ctx = getInternals(router);\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- guaranteed set after wiring\n const lifecycleNamespace = ctx.routeGetStore().lifecycleNamespace!;\n\n return {\n addActivateGuard(name, handler) {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.routes.validateRouteName(name, \"addActivateGuard\");\n ctx.validator?.lifecycle.validateHandler(handler, \"addActivateGuard\");\n\n const activateCount = lifecycleNamespace.getHandlerCount(\"activate\");\n\n ctx.validator?.lifecycle.validateHandlerLimit(\n activateCount,\n ctx.dependenciesGetStore().limits,\n \"canActivate\",\n );\n\n lifecycleNamespace.addCanActivate(name, handler);\n },\n\n addDeactivateGuard(name, handler) {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.routes.validateRouteName(name, \"addDeactivateGuard\");\n ctx.validator?.lifecycle.validateHandler(handler, \"addDeactivateGuard\");\n\n const deactivateCount = lifecycleNamespace.getHandlerCount(\"deactivate\");\n\n ctx.validator?.lifecycle.validateHandlerLimit(\n deactivateCount,\n ctx.dependenciesGetStore().limits,\n \"canDeactivate\",\n );\n\n lifecycleNamespace.addCanDeactivate(name, handler);\n },\n\n removeActivateGuard(name) {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.routes.validateRouteName(name, \"removeActivateGuard\");\n\n lifecycleNamespace.clearCanActivate(name);\n },\n\n removeDeactivateGuard(name) {\n throwIfDisposed(ctx.isDisposed);\n\n ctx.validator?.routes.validateRouteName(name, \"removeDeactivateGuard\");\n\n lifecycleNamespace.clearCanDeactivate(name);\n },\n };\n}\n","import { routeTreeToDefinitions } from \"route-tree\";\n\nimport { errorCodes } from \"../constants\";\nimport { getInternals } from \"../internals\";\nimport { Router as RouterClass } from \"../Router\";\nimport { RouterError } from \"../RouterError\";\nimport { getLifecycleApi } from \"./getLifecycleApi\";\n\nimport type { Route } from \"../types\";\nimport type { DefaultDependencies, Router } from \"@real-router/types\";\n\nexport function cloneRouter<\n Dependencies extends DefaultDependencies = DefaultDependencies,\n>(\n router: Router<Dependencies>,\n dependencies?: Dependencies,\n): RouterClass<Dependencies> {\n const ctx = getInternals(router);\n\n if (ctx.isDisposed()) {\n throw new RouterError(errorCodes.ROUTER_DISPOSED);\n }\n\n ctx.validator?.dependencies.validateCloneArgs(dependencies);\n\n // Get source store directly\n const sourceStore = ctx.routeGetStore();\n const routes = routeTreeToDefinitions(sourceStore.tree);\n const routeConfig = sourceStore.config;\n const resolvedForwardMap = sourceStore.resolvedForwardMap;\n const routeCustomFields = sourceStore.routeCustomFields;\n\n const options = ctx.cloneOptions();\n const sourceDeps = ctx.cloneDependencies();\n const [canDeactivateFactories, canActivateFactories] =\n ctx.getLifecycleFactories();\n const pluginFactories = ctx.getPluginFactories();\n\n const mergedDeps = {\n ...sourceDeps,\n ...dependencies,\n } as Dependencies;\n\n const newRouter = new RouterClass<Dependencies>(\n routes as Route<Dependencies>[],\n options,\n mergedDeps,\n );\n\n const lifecycle = getLifecycleApi(newRouter);\n\n for (const [name, handler] of Object.entries(canDeactivateFactories)) {\n lifecycle.addDeactivateGuard(name, handler);\n }\n\n for (const [name, handler] of Object.entries(canActivateFactories)) {\n lifecycle.addActivateGuard(name, handler);\n }\n\n if (pluginFactories.length > 0) {\n newRouter.usePlugin(...pluginFactories);\n }\n\n const newCtx = getInternals(newRouter);\n const newStore = newCtx.routeGetStore();\n\n // Apply cloned config directly to new store\n Object.assign(newStore.config.decoders, routeConfig.decoders);\n Object.assign(newStore.config.encoders, routeConfig.encoders);\n Object.assign(newStore.config.defaultParams, routeConfig.defaultParams);\n Object.assign(newStore.config.forwardMap, routeConfig.forwardMap);\n Object.assign(newStore.config.forwardFnMap, routeConfig.forwardFnMap);\n Object.assign(newStore.resolvedForwardMap, resolvedForwardMap);\n Object.assign(newStore.routeCustomFields, routeCustomFields);\n\n return newRouter;\n}\n"],"mappings":"4GAKA,SAAgB,EAAgB,EAAiC,CAC/D,GAAI,GAAY,CACd,MAAM,IAAI,EAAY,EAAW,gBAAgB,CCarD,MAAM,EAAQ,IAAI,QAElB,SAAgB,EAEd,EAAyC,CACzC,IAAM,EAAS,EAAM,IAAI,EAAO,CAEhC,GAAI,EACF,OAAO,EAGT,IAAM,EAAM,EAAa,EAAO,CAC1B,EAAiB,CACrB,WAAY,EAAM,EAAQ,EAAM,KAC9B,EAAI,WAAW,MAAM,sBAAsB,EAAM,EAAQ,EAAK,CAEvD,EAAI,UACT,EACA,EACA,EACA,GAAM,OAGP,EAEH,YAAa,EAAW,IAAgB,CACtC,EAAI,WAAW,OAAO,yBACpB,EACA,EACA,aACD,CAED,GAAM,CAAE,OAAM,UAAW,EAAI,aAAa,EAAW,EAAY,CAEjE,OAAO,EAAI,mBAAmB,EAAM,EAAO,EAE7C,cACE,EACA,KAEA,EAAI,WAAW,OAAO,yBACpB,EACA,EACA,eACD,CAEM,EAAI,aAAa,EAAW,EAAY,EAEjD,UAAY,IACV,EAAI,WAAW,OAAO,sBAAsB,EAAK,CAE1C,EAAI,UAAU,EAAM,EAAI,YAAY,CAAC,EAE9C,iBAAkB,EAAO,KACvB,EAAgB,EAAI,WAAW,CAE/B,EAAI,WAAW,WAAW,4BAA4B,EAAM,CAExD,IAAY,IAAA,IACd,EAAI,WAAW,WAAW,0BACxB,EACA,kBACD,CAGI,EAAI,gBAAgB,EAAO,EAAQ,EAE5C,YAAc,GAAa,CACzB,EAAgB,EAAI,WAAW,CAE/B,EAAI,WAAW,OAAO,wBAAwB,EAAS,CAEvD,EAAI,YAAY,EAAS,EAE3B,YAAa,EAAI,YACjB,kBAAmB,EAAW,KAC5B,EAAgB,EAAI,WAAW,CAE/B,EAAI,WAAW,SAAS,qBAAqB,EAAW,EAAG,CAEpD,EAAI,iBAAiB,EAAW,EAAG,EAE5C,sBAAuB,EAAM,EAAS,EAAE,GAAK,CAC3C,EAAI,WAAW,OAAO,yBACpB,EACA,EACA,uBACD,CAED,GAAM,CAAE,KAAM,EAAc,OAAQ,GAAmB,EAAI,aACzD,EACA,EACD,CACK,EAAY,EAAI,mBAAmB,EAAc,EAAe,CAEjE,KAIL,OAAO,EAAI,UACT,EAAU,KACV,EAAU,OACV,EAAI,UAAU,EAAU,KAAM,EAAU,OAAO,CAC/C,EAAU,KACX,EAEH,WAAY,EAAI,WAChB,QAAS,EAAI,QACb,gBAAiB,EAAQ,IAAO,CAC9B,EAAgB,EAAI,WAAW,CAC/B,EAAI,WAAW,QAAQ,2BAA2B,EAAQ,EAAG,CAC7D,IAAI,EAAO,EAAI,aAAa,IAAI,EAAO,CASvC,OAPK,IACH,EAAO,EAAE,CACT,EAAI,aAAa,IAAI,EAAQ,EAAK,EAGpC,EAAK,KAAK,EAAG,KAEA,CACX,IAAM,EAAQ,EAAK,QAAQ,EAAG,CAE1B,IAAU,IACZ,EAAK,OAAO,EAAO,EAAE,GAI3B,eAAiB,GAAS,CACxB,IAAM,EAAQ,EAAI,eAAe,CAE5B,KAAM,QAAQ,SAAS,EAAK,CAIjC,OAAO,EAAM,kBAAkB,IAEjC,aAAe,GAAwC,CACrD,EAAgB,EAAI,WAAW,CAE/B,IAAM,EAAO,OAAO,KAAK,EAAW,CAEpC,IAAK,IAAM,KAAO,EAChB,GAAI,KAAO,EACT,MAAM,IAAI,EAAY,EAAW,gBAAiB,CAChD,QAAS,mCAAmC,EAAI,kBACjD,CAAC,CAIN,IAAK,IAAM,KAAO,EACf,EAAmC,GAAO,EAAW,GAGxD,IAAM,EAAkB,CAAE,OAAM,CAEhC,EAAI,iBAAiB,KAAK,EAAgB,CAE1C,IAAI,EAAU,GAEd,UAAa,CACX,GAAI,EACF,OAGF,EAAU,GAEV,IAAK,IAAM,KAAO,EAAgB,KAChC,OAAQ,EAAmC,GAG7C,IAAM,EAAM,EAAI,iBAAiB,QAAQ,EAAgB,CAErD,IAAQ,IACV,EAAI,iBAAiB,OAAO,EAAK,EAAE,GAIzC,oBAAsB,GAAU,CAC9B,EAAgB,EAAI,WAAW,CAC/B,EAAI,oBAAoB,EAAM,EAEhC,uBAAyB,GAAsB,CAG7C,GAFA,EAAgB,EAAI,WAAW,CAE3B,EAAI,oBAAoB,IAAI,EAAU,CACxC,MAAM,IAAI,EAAY,EAAW,kCAAmC,CAClE,QAAS,oCAAoC,EAAU,wCACxD,CAAC,CAKJ,OAFA,EAAI,oBAAoB,IAAI,EAAU,CAE/B,CACL,MAAM,EAAc,EAAgB,CACjC,EAAM,QAAoC,GAAa,GAE1D,SAAU,CACR,EAAI,oBAAoB,OAAO,EAAU,EAE5C,GAEJ,CAID,OAFA,EAAM,IAAI,EAAQ,EAAI,CAEf,EC5NT,SAAgB,EAEd,EAA0D,CAC1D,IAAM,EAAM,EAAa,EAAO,CAE1B,EAAqB,EAAI,eAAe,CAAC,mBAE/C,MAAO,CACL,iBAAiB,EAAM,EAAS,CAC9B,EAAgB,EAAI,WAAW,CAE/B,EAAI,WAAW,OAAO,kBAAkB,EAAM,mBAAmB,CACjE,EAAI,WAAW,UAAU,gBAAgB,EAAS,mBAAmB,CAErE,IAAM,EAAgB,EAAmB,gBAAgB,WAAW,CAEpE,EAAI,WAAW,UAAU,qBACvB,EACA,EAAI,sBAAsB,CAAC,OAC3B,cACD,CAED,EAAmB,eAAe,EAAM,EAAQ,EAGlD,mBAAmB,EAAM,EAAS,CAChC,EAAgB,EAAI,WAAW,CAE/B,EAAI,WAAW,OAAO,kBAAkB,EAAM,qBAAqB,CACnE,EAAI,WAAW,UAAU,gBAAgB,EAAS,qBAAqB,CAEvE,IAAM,EAAkB,EAAmB,gBAAgB,aAAa,CAExE,EAAI,WAAW,UAAU,qBACvB,EACA,EAAI,sBAAsB,CAAC,OAC3B,gBACD,CAED,EAAmB,iBAAiB,EAAM,EAAQ,EAGpD,oBAAoB,EAAM,CACxB,EAAgB,EAAI,WAAW,CAE/B,EAAI,WAAW,OAAO,kBAAkB,EAAM,sBAAsB,CAEpE,EAAmB,iBAAiB,EAAK,EAG3C,sBAAsB,EAAM,CAC1B,EAAgB,EAAI,WAAW,CAE/B,EAAI,WAAW,OAAO,kBAAkB,EAAM,wBAAwB,CAEtE,EAAmB,mBAAmB,EAAK,EAE9C,CCpDH,SAAgB,EAGd,EACA,EAC2B,CAC3B,IAAM,EAAM,EAAa,EAAO,CAEhC,GAAI,EAAI,YAAY,CAClB,MAAM,IAAI,EAAY,EAAW,gBAAgB,CAGnD,EAAI,WAAW,aAAa,kBAAkB,EAAa,CAG3D,IAAM,EAAc,EAAI,eAAe,CACjC,EAASA,EAAuB,EAAY,KAAK,CACjD,EAAc,EAAY,OAC1B,EAAqB,EAAY,mBACjC,EAAoB,EAAY,kBAEhC,EAAU,EAAI,cAAc,CAC5B,EAAa,EAAI,mBAAmB,CACpC,CAAC,EAAwB,GAC7B,EAAI,uBAAuB,CACvB,EAAkB,EAAI,oBAAoB,CAO1C,EAAY,IAAIC,EACpB,EACA,EACA,CAPA,GAAG,EACH,GAAG,EAMO,CACX,CAEK,EAAY,EAAgB,EAAU,CAE5C,IAAK,GAAM,CAAC,EAAM,KAAY,OAAO,QAAQ,EAAuB,CAClE,EAAU,mBAAmB,EAAM,EAAQ,CAG7C,IAAK,GAAM,CAAC,EAAM,KAAY,OAAO,QAAQ,EAAqB,CAChE,EAAU,iBAAiB,EAAM,EAAQ,CAGvC,EAAgB,OAAS,GAC3B,EAAU,UAAU,GAAG,EAAgB,CAIzC,IAAM,EADS,EAAa,EACL,CAAC,eAAe,CAWvC,OARA,OAAO,OAAO,EAAS,OAAO,SAAU,EAAY,SAAS,CAC7D,OAAO,OAAO,EAAS,OAAO,SAAU,EAAY,SAAS,CAC7D,OAAO,OAAO,EAAS,OAAO,cAAe,EAAY,cAAc,CACvE,OAAO,OAAO,EAAS,OAAO,WAAY,EAAY,WAAW,CACjE,OAAO,OAAO,EAAS,OAAO,aAAc,EAAY,aAAa,CACrE,OAAO,OAAO,EAAS,mBAAoB,EAAmB,CAC9D,OAAO,OAAO,EAAS,kBAAmB,EAAkB,CAErD"}