svelte-navigator-lite 2.0.0 → 2.1.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.
package/README.md CHANGED
@@ -19,16 +19,19 @@ Define your routes and guards, then call `createRouter` on mount.
19
19
  import { createRouter, router } from 'svelte-navigator-lite';
20
20
  import { auth } from '$stores/auth.svelte';
21
21
  import AppShell from '$lib/components/AppShell.svelte';
22
+ import { overlayMap } from '$lib/routes';
23
+
24
+ let currentOverlay = $derived(overlayMap[router.route] ?? null);
22
25
 
23
26
  onMount(() => {
24
27
  createRouter({
25
28
  routes: [
26
- { name: 'cal', pattern: '/cal' },
27
- { name: 'cal-date', pattern: '/cal/:mm/:dd/:yyyy' },
28
- { name: 'event', pattern: '/event/:eventId' },
29
- { name: 'edit', pattern: '/event/:eventId/edit' },
30
- { name: 'login', pattern: '/login', guards: ['unauth'] },
31
- { name: 'signup', pattern: '/signup', guards: ['unauth'] },
29
+ { name: 'cal', pattern: '/cal' },
30
+ { name: 'cal-date', pattern: '/cal/:mm/:dd/:yyyy' },
31
+ { name: 'event', pattern: '/event/:eventId', overlay: true },
32
+ { name: 'edit', pattern: '/event/:eventId/edit', overlay: true },
33
+ { name: 'login', pattern: '/login', guards: ['unauth'], overlay: true },
34
+ { name: 'signup', pattern: '/signup', guards: ['unauth'], overlay: true },
32
35
  ],
33
36
  guards: {
34
37
  auth: { condition: () => !auth.isValid(), redirectTo: 'login' },
@@ -40,6 +43,9 @@ Define your routes and guards, then call `createRouter` on mount.
40
43
  </script>
41
44
 
42
45
  <AppShell />
46
+ {#if router.overlay}
47
+ <svelte:component this={currentOverlay} />
48
+ {/if}
43
49
  ```
44
50
 
45
51
  ## Route patterns
@@ -81,14 +87,39 @@ import { router } from 'svelte-navigator-lite';
81
87
  router.route // current route name: string
82
88
  router.params // path params: Record<string, string>
83
89
  router.searchParams // query params: Record<string, string>
90
+ router.overlay // true if the current route has overlay: true
84
91
  router.notFound // true if the URL matched no route and the fallback was used
85
92
 
86
- router.is('cal') // true if current route === 'cal'
93
+ router.is('cal') // true if current route === 'cal'
87
94
  router.matches(['cal', 'event']) // true if current route is in the list
88
95
  ```
89
96
 
90
97
  All properties are reactive — use them in Svelte templates or `$effect` blocks and they update automatically on navigation.
91
98
 
99
+ ## Overlays
100
+
101
+ Mark a route with `overlay: true` to indicate it renders on top of the base layout rather than replacing it. The router exposes `router.overlay` so your root component can conditionally render the overlay without any separate bookkeeping.
102
+
103
+ ```typescript
104
+ routes: [
105
+ { name: 'cal', pattern: '/cal' },
106
+ { name: 'event', pattern: '/event/:eventId', overlay: true },
107
+ { name: 'edit', pattern: '/event/:eventId/edit', overlay: true },
108
+ ]
109
+ ```
110
+
111
+ ```svelte
112
+ <!-- The base layout always renders -->
113
+ <AppShell />
114
+
115
+ <!-- Overlay components mount on top when their route is active -->
116
+ {#if router.overlay}
117
+ <svelte:component this={overlayMap[router.route]} />
118
+ {/if}
119
+ ```
120
+
121
+ `overlay` is purely a metadata flag — the router does not render anything itself. How overlays are displayed (modal, drawer, fullscreen panel, etc.) is entirely up to your components.
122
+
92
123
  ## Guards
93
124
 
94
125
  Guards are defined once in `createRouter` and referenced by name in route definitions.
@@ -96,9 +127,9 @@ Guards are defined once in `createRouter` and referenced by name in route defini
96
127
  ```typescript
97
128
  createRouter({
98
129
  routes: [
99
- { name: 'cal', pattern: '/cal', guards: ['auth'] },
100
- { name: 'login', pattern: '/login', guards: ['unauth'] },
101
- { name: 'verify-email', pattern: '/verify-email', guards: ['unauth'] },
130
+ { name: 'cal', pattern: '/cal', guards: ['auth'] },
131
+ { name: 'login', pattern: '/login', guards: ['unauth'] },
132
+ { name: 'verify-email', pattern: '/verify-email', guards: ['unauth'] },
102
133
  { name: 'login-check', pattern: '/login', guards: ['unauth', 'emailCheck'] },
103
134
  ],
104
135
  guards: {
@@ -150,7 +181,7 @@ await goto('/some/path', { replaceState: true }); // replace instead of push
150
181
 
151
182
  ## Migrating from v1
152
183
 
153
- The `rootPath` + `segments` route definition is replaced by a single `pattern` string, and `routeGuards` inline on each route are replaced by named guards defined once.
184
+ The `rootPath` + `segments` route definition is replaced by a single `pattern` string, `routeGuards` inline on each route are replaced by named guards defined once, and the new `overlay` flag replaces any separate modal-route maps you maintained manually.
154
185
 
155
186
  ```typescript
156
187
  // v1
@@ -161,6 +192,6 @@ The `rootPath` + `segments` route definition is replaced by a single `pattern` s
161
192
  }
162
193
 
163
194
  // v2
164
- { name: 'edit', pattern: '/event/:eventId/edit', guards: ['auth'] }
165
- // with guard defined once in createRouter: auth: { condition: () => !auth.isValid(), redirectTo: 'login' }
195
+ { name: 'edit', pattern: '/event/:eventId/edit', guards: ['auth'], overlay: true }
196
+ // guard defined once: auth: { condition: () => !auth.isValid(), redirectTo: 'login' }
166
197
  ```
package/dist/match.d.ts CHANGED
@@ -5,6 +5,7 @@ type CompiledRoute = {
5
5
  regex: RegExp;
6
6
  paramNames: string[];
7
7
  guards: string[];
8
+ overlay: boolean;
8
9
  };
9
10
  export type RouteMatch = {
10
11
  name: string;
package/dist/match.js CHANGED
@@ -20,6 +20,7 @@ export function compileRoutes(routes) {
20
20
  regex: new RegExp(`^${regexStr}/?$`),
21
21
  paramNames,
22
22
  guards: route.guards ?? [],
23
+ overlay: route.overlay ?? false,
23
24
  };
24
25
  });
25
26
  }
@@ -10,6 +10,7 @@ declare function _createRouter(): {
10
10
  readonly params: Record<string, string>;
11
11
  readonly searchParams: Record<string, string>;
12
12
  readonly notFound: boolean;
13
+ readonly overlay: boolean;
13
14
  is(route: string): boolean;
14
15
  matches(routes: string[]): boolean;
15
16
  parseUrl: (url: string) => void;
@@ -22,6 +23,7 @@ export declare const router: {
22
23
  readonly params: Record<string, string>;
23
24
  readonly searchParams: Record<string, string>;
24
25
  readonly notFound: boolean;
26
+ readonly overlay: boolean;
25
27
  is(route: string): boolean;
26
28
  matches(routes: string[]): boolean;
27
29
  parseUrl: (url: string) => void;
@@ -70,6 +70,7 @@ function _createRouter() {
70
70
  get params() { return state.params; },
71
71
  get searchParams() { return state.searchParams; },
72
72
  get notFound() { return state.notFound; },
73
+ get overlay() { return compiled.find(r => r.name === state.current)?.overlay ?? false; },
73
74
  is(route) { return state.current === route; },
74
75
  matches(routes) { return routes.includes(state.current); },
75
76
  parseUrl,
package/dist/types.d.ts CHANGED
@@ -2,6 +2,7 @@ export type RouteDefinition = {
2
2
  name: string;
3
3
  pattern: string;
4
4
  guards?: string[];
5
+ overlay?: boolean;
5
6
  };
6
7
  export type Guard = {
7
8
  condition: () => boolean;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "svelte-navigator-lite",
3
- "version": "2.0.0",
3
+ "version": "2.1.0",
4
4
  "description": "A lightweight router for Svelte 5",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -12,7 +12,9 @@
12
12
  "types": "./dist/index.d.ts"
13
13
  }
14
14
  },
15
- "files": ["dist"],
15
+ "files": [
16
+ "dist"
17
+ ],
16
18
  "scripts": {
17
19
  "build": "tsc",
18
20
  "dev": "tsc --watch",
@@ -29,10 +31,15 @@
29
31
  "typescript": "^5.0.0",
30
32
  "vitest": "^3.0.0"
31
33
  },
32
- "keywords": ["svelte", "router", "navigation", "svelte5"],
34
+ "keywords": [
35
+ "svelte",
36
+ "router",
37
+ "navigation",
38
+ "svelte5"
39
+ ],
33
40
  "license": "MIT",
34
41
  "repository": {
35
42
  "type": "git",
36
- "url": "https://github.com/jeremyjfleming/svelte-navigator-lite"
43
+ "url": "git+https://github.com/jeremyjfleming/svelte-navigator-lite.git"
37
44
  }
38
45
  }