@sigx/lynx-navigation 0.4.0 → 0.4.2

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 (187) hide show
  1. package/dist/components/Drawer.js +74 -0
  2. package/dist/components/Drawer.js.map +1 -0
  3. package/dist/components/EdgeBackHandle.js +144 -0
  4. package/dist/components/EdgeBackHandle.js.map +1 -0
  5. package/dist/components/EntryScope.d.ts +1 -1
  6. package/dist/components/EntryScope.d.ts.map +1 -1
  7. package/dist/components/EntryScope.js +39 -0
  8. package/dist/components/EntryScope.js.map +1 -0
  9. package/dist/components/Header.js +103 -0
  10. package/dist/components/Header.js.map +1 -0
  11. package/dist/components/Layer.d.ts +2 -2
  12. package/dist/components/Layer.d.ts.map +1 -1
  13. package/dist/components/Layer.js +66 -0
  14. package/dist/components/Layer.js.map +1 -0
  15. package/dist/components/Link.d.ts +2 -2
  16. package/dist/components/Link.d.ts.map +1 -1
  17. package/dist/components/Link.js +51 -0
  18. package/dist/components/Link.js.map +1 -0
  19. package/dist/components/NavigationRoot.d.ts +2 -2
  20. package/dist/components/NavigationRoot.d.ts.map +1 -1
  21. package/dist/components/NavigationRoot.js +67 -0
  22. package/dist/components/NavigationRoot.js.map +1 -0
  23. package/dist/components/Screen.js +98 -0
  24. package/dist/components/Screen.js.map +1 -0
  25. package/dist/components/Stack.js +257 -0
  26. package/dist/components/Stack.js.map +1 -0
  27. package/dist/components/TabBar.d.ts +1 -1
  28. package/dist/components/TabBar.d.ts.map +1 -1
  29. package/dist/components/TabBar.js +63 -0
  30. package/dist/components/TabBar.js.map +1 -0
  31. package/dist/components/Tabs.d.ts +8 -3
  32. package/dist/components/Tabs.d.ts.map +1 -1
  33. package/dist/components/Tabs.js +168 -0
  34. package/dist/components/Tabs.js.map +1 -0
  35. package/dist/define-routes.d.ts +1 -1
  36. package/dist/define-routes.d.ts.map +1 -1
  37. package/{src/define-routes.d.ts → dist/define-routes.js} +4 -2
  38. package/dist/define-routes.js.map +1 -0
  39. package/dist/hooks/use-focus.js +87 -0
  40. package/dist/hooks/use-focus.js.map +1 -0
  41. package/dist/hooks/use-hardware-back.js +84 -0
  42. package/dist/hooks/use-hardware-back.js.map +1 -0
  43. package/dist/hooks/use-linking-nav.d.ts +3 -3
  44. package/dist/hooks/use-linking-nav.d.ts.map +1 -1
  45. package/dist/hooks/use-linking-nav.js +109 -0
  46. package/dist/hooks/use-linking-nav.js.map +1 -0
  47. package/dist/hooks/use-nav-internal.d.ts +2 -2
  48. package/dist/hooks/use-nav-internal.d.ts.map +1 -1
  49. package/dist/hooks/use-nav-internal.js +55 -0
  50. package/dist/hooks/use-nav-internal.js.map +1 -0
  51. package/dist/hooks/use-nav-serializer.d.ts +1 -1
  52. package/dist/hooks/use-nav-serializer.d.ts.map +1 -1
  53. package/dist/hooks/use-nav-serializer.js +181 -0
  54. package/dist/hooks/use-nav-serializer.js.map +1 -0
  55. package/dist/hooks/use-nav.d.ts +2 -2
  56. package/dist/hooks/use-nav.d.ts.map +1 -1
  57. package/dist/hooks/use-nav.js +11 -0
  58. package/dist/hooks/use-nav.js.map +1 -0
  59. package/dist/hooks/use-params.d.ts +1 -1
  60. package/dist/hooks/use-params.d.ts.map +1 -1
  61. package/{src/hooks/use-params.d.ts → dist/hooks/use-params.js} +6 -2
  62. package/dist/hooks/use-params.js.map +1 -0
  63. package/dist/hooks/use-screen-chrome.d.ts +1 -1
  64. package/dist/hooks/use-screen-chrome.d.ts.map +1 -1
  65. package/dist/hooks/use-screen-chrome.js +102 -0
  66. package/dist/hooks/use-screen-chrome.js.map +1 -0
  67. package/dist/hooks/use-screen-options.d.ts +1 -1
  68. package/dist/hooks/use-screen-options.d.ts.map +1 -1
  69. package/dist/hooks/use-screen-options.js +43 -0
  70. package/dist/hooks/use-screen-options.js.map +1 -0
  71. package/dist/hooks/use-search.d.ts +1 -1
  72. package/dist/hooks/use-search.d.ts.map +1 -1
  73. package/{src/hooks/use-search.d.ts → dist/hooks/use-search.js} +6 -2
  74. package/dist/hooks/use-search.js.map +1 -0
  75. package/dist/href.d.ts +2 -2
  76. package/dist/href.d.ts.map +1 -1
  77. package/dist/href.js +57 -0
  78. package/dist/href.js.map +1 -0
  79. package/dist/index.d.ts +33 -33
  80. package/dist/index.d.ts.map +1 -1
  81. package/dist/index.js +30 -1160
  82. package/dist/index.js.map +1 -1
  83. package/dist/internal/layer-plan.d.ts +1 -1
  84. package/dist/internal/layer-plan.d.ts.map +1 -1
  85. package/dist/internal/layer-plan.js +102 -0
  86. package/dist/internal/layer-plan.js.map +1 -0
  87. package/dist/internal/screen-registry.d.ts +1 -1
  88. package/dist/internal/screen-registry.d.ts.map +1 -1
  89. package/{src/internal/screen-registry.d.ts → dist/internal/screen-registry.js} +32 -21
  90. package/dist/internal/screen-registry.js.map +1 -0
  91. package/{src/internal/screen-width.d.ts → dist/internal/screen-width.js} +17 -2
  92. package/dist/internal/screen-width.js.map +1 -0
  93. package/dist/navigator/core.d.ts +3 -3
  94. package/dist/navigator/core.d.ts.map +1 -1
  95. package/dist/navigator/core.js +394 -0
  96. package/dist/navigator/core.js.map +1 -0
  97. package/dist/register.d.ts +1 -1
  98. package/dist/register.d.ts.map +1 -1
  99. package/dist/register.js +2 -0
  100. package/dist/register.js.map +1 -0
  101. package/dist/types.js +9 -0
  102. package/dist/types.js.map +1 -0
  103. package/dist/url/build.js +30 -0
  104. package/dist/url/build.js.map +1 -0
  105. package/dist/url/compile.js +83 -0
  106. package/dist/url/compile.js.map +1 -0
  107. package/dist/url/format.js +102 -0
  108. package/dist/url/format.js.map +1 -0
  109. package/dist/url/index.d.ts +6 -6
  110. package/dist/url/index.d.ts.map +1 -1
  111. package/dist/url/index.js +13 -0
  112. package/dist/url/index.js.map +1 -0
  113. package/dist/url/parse.d.ts +1 -1
  114. package/dist/url/parse.d.ts.map +1 -1
  115. package/dist/url/parse.js +94 -0
  116. package/dist/url/parse.js.map +1 -0
  117. package/dist/url/registry.d.ts +2 -2
  118. package/dist/url/registry.d.ts.map +1 -1
  119. package/{src/url/registry.d.ts → dist/url/registry.js} +28 -12
  120. package/dist/url/registry.js.map +1 -0
  121. package/dist/url/validate.d.ts +1 -1
  122. package/dist/url/validate.d.ts.map +1 -1
  123. package/dist/url/validate.js +37 -0
  124. package/dist/url/validate.js.map +1 -0
  125. package/package.json +16 -13
  126. package/src/components/EdgeBackHandle.tsx +2 -2
  127. package/src/components/EntryScope.tsx +3 -3
  128. package/src/components/Header.tsx +3 -3
  129. package/src/components/Layer.tsx +3 -3
  130. package/src/components/Link.tsx +4 -4
  131. package/src/components/NavigationRoot.tsx +6 -6
  132. package/src/components/Screen.tsx +3 -3
  133. package/src/components/Stack.tsx +8 -8
  134. package/src/components/TabBar.tsx +1 -1
  135. package/src/components/Tabs.tsx +8 -3
  136. package/src/define-routes.ts +1 -1
  137. package/src/hooks/use-focus.ts +2 -2
  138. package/src/hooks/use-hardware-back.ts +1 -1
  139. package/src/hooks/use-linking-nav.ts +4 -4
  140. package/src/hooks/use-nav-internal.ts +2 -2
  141. package/src/hooks/use-nav-serializer.ts +3 -3
  142. package/src/hooks/use-nav.ts +2 -2
  143. package/src/hooks/use-params.ts +2 -2
  144. package/src/hooks/use-screen-chrome.ts +3 -3
  145. package/src/hooks/use-screen-options.ts +3 -3
  146. package/src/hooks/use-search.ts +2 -2
  147. package/src/href.ts +6 -6
  148. package/src/index.ts +33 -33
  149. package/src/internal/layer-plan.ts +2 -2
  150. package/src/internal/screen-registry.ts +1 -1
  151. package/src/navigator/core.ts +3 -3
  152. package/src/register.ts +1 -1
  153. package/src/url/build.ts +2 -2
  154. package/src/url/index.ts +6 -6
  155. package/src/url/parse.ts +6 -6
  156. package/src/url/registry.ts +3 -3
  157. package/src/url/validate.ts +1 -1
  158. package/src/components/Drawer.d.ts +0 -55
  159. package/src/components/EdgeBackHandle.d.ts +0 -1
  160. package/src/components/EntryScope.d.ts +0 -25
  161. package/src/components/Header.d.ts +0 -6
  162. package/src/components/Layer.d.ts +0 -33
  163. package/src/components/Link.d.ts +0 -60
  164. package/src/components/NavigationRoot.d.ts +0 -36
  165. package/src/components/Screen.d.ts +0 -97
  166. package/src/components/Stack.d.ts +0 -90
  167. package/src/components/TabBar.d.ts +0 -38
  168. package/src/components/Tabs.d.ts +0 -109
  169. package/src/hooks/use-focus.d.ts +0 -45
  170. package/src/hooks/use-hardware-back.d.ts +0 -37
  171. package/src/hooks/use-linking-nav.d.ts +0 -91
  172. package/src/hooks/use-nav-internal.d.ts +0 -91
  173. package/src/hooks/use-nav-serializer.d.ts +0 -82
  174. package/src/hooks/use-nav.d.ts +0 -111
  175. package/src/hooks/use-screen-chrome.d.ts +0 -18
  176. package/src/hooks/use-screen-options.d.ts +0 -2
  177. package/src/href.d.ts +0 -54
  178. package/src/index.d.ts +0 -39
  179. package/src/internal/layer-plan.d.ts +0 -68
  180. package/src/navigator/core.d.ts +0 -96
  181. package/src/register.d.ts +0 -37
  182. package/src/types.d.ts +0 -217
  183. package/src/url/build.d.ts +0 -15
  184. package/src/url/compile.d.ts +0 -34
  185. package/src/url/format.d.ts +0 -28
  186. package/src/url/parse.d.ts +0 -20
  187. package/src/url/validate.d.ts +0 -23
package/src/types.d.ts DELETED
@@ -1,217 +0,0 @@
1
- /**
2
- * Core types for @sigx/lynx-navigation.
3
- *
4
- * The type machinery here is the differentiating DX: route names, params, and
5
- * search are all inferred end-to-end from the user's `defineRoutes` call so
6
- * `nav.push('profile', { id: 42 })` is a TS error if `id` is typed as string.
7
- */
8
- /**
9
- * Minimal Standard Schema spec subset — see https://standardschema.dev.
10
- * Inlined so we don't depend on `@standard-schema/spec` for the type spike.
11
- * Compatible with Zod, Valibot, ArkType, etc.
12
- */
13
- export interface StandardSchemaV1<Input = unknown, Output = Input> {
14
- readonly '~standard': {
15
- readonly version: 1;
16
- readonly vendor: string;
17
- readonly types?: {
18
- readonly input: Input;
19
- readonly output: Output;
20
- };
21
- };
22
- }
23
- /**
24
- * Infer the validated output type of a Standard Schema, falling back to
25
- * `unknown` for non-schema values.
26
- */
27
- export type InferOutput<S> = S extends StandardSchemaV1<unknown, infer O> ? O : unknown;
28
- /** Empty record — what `ParamsOf` returns when a route declares no schema. */
29
- export type EmptyParams = Record<string, never>;
30
- /**
31
- * How a route entry is presented on the stack.
32
- * `card` is the default push; `modal`/`fullScreen` slide up; `transparent-modal`
33
- * preserves the underlying screen visible (e.g. for popovers).
34
- */
35
- export type Presentation = 'card' | 'modal' | 'fullScreen' | 'transparent-modal';
36
- /**
37
- * A route definition entry.
38
- *
39
- * Users construct this via `defineRoutes({...})`. The `params` and `search`
40
- * schemas drive runtime validation AND TS inference for `useParams`,
41
- * `useSearch`, `nav.push`, `<Link>`, etc.
42
- *
43
- * `component` accepts an eager component factory or a lazy import — both shapes
44
- * resolve through sigx's `<Suspense>` boundary at render time.
45
- */
46
- export interface RouteDefinition<Params extends StandardSchemaV1 | undefined = StandardSchemaV1 | undefined, Search extends StandardSchemaV1 | undefined = StandardSchemaV1 | undefined> {
47
- /** Component factory or lazy importer. */
48
- component: ComponentLike;
49
- /**
50
- * Fallback shown while a lazy `component` is loading.
51
- *
52
- * Set this only on routes whose `component` was created with `lazy(...)`.
53
- * The fallback is rendered inside a `<Suspense>` boundary wrapping the
54
- * screen mount, so the user sees this UI while the screen's chunk is
55
- * being fetched. When omitted, lazy routes still work — the caller is
56
- * responsible for placing its own `<Suspense>` boundary (e.g. above the
57
- * `<NavigationRoot>` or inside the screen component).
58
- *
59
- * Accepts a component factory (`MyLoadingScreen`) or a function returning
60
- * JSX (`() => <Spinner />`). Eager routes ignore this field.
61
- */
62
- fallback?: ComponentLike | (() => unknown);
63
- /** Standard-Schema validator for path params. Optional. */
64
- params?: Params;
65
- /** Standard-Schema validator for query/search params. Optional. */
66
- search?: Search;
67
- /** Optional URL pattern for deep-link serialization (e.g. `/users/:id`). */
68
- path?: string;
69
- /** Default presentation when this route is pushed. */
70
- presentation?: Presentation;
71
- /** Nested routes — share the URL/path namespace and may inherit options. */
72
- children?: Record<string, RouteDefinition>;
73
- }
74
- /**
75
- * The component shape we accept on a route. Kept structural so we don't pull
76
- * `ComponentFactory` from sigx at type level (avoids a hard dep on sigx purely
77
- * for types in the spike). Refined to a real ComponentFactory in Phase 0.1
78
- * runtime work.
79
- */
80
- export type ComponentLike = ((...args: any[]) => unknown) | (() => Promise<{
81
- default: (...args: any[]) => unknown;
82
- }>);
83
- /**
84
- * Map of route definitions, as returned by `defineRoutes`. Keys are route
85
- * names; values are typed RouteDefinitions.
86
- */
87
- export type RouteMap = Record<string, RouteDefinition>;
88
- /**
89
- * Extract params type from a single RouteDefinition.
90
- * Falls back to `EmptyParams` when the route declares no schema.
91
- *
92
- * We use a structural `params: infer S` match (without an `extends
93
- * StandardSchemaV1` constraint on `S`) because TS conditional types treat the
94
- * generic-defaulted `StandardSchemaV1<unknown, unknown>` as invariant in this
95
- * position — a schema typed `StandardSchemaV1<{id:string}>` does not match
96
- * `extends StandardSchemaV1` reliably under `<const T>` inference. `InferOutput`
97
- * gracefully handles non-schema `S` by returning `unknown`.
98
- */
99
- export type ParamsOf<R> = R extends {
100
- params: infer S;
101
- } ? InferOutput<S> : EmptyParams;
102
- /**
103
- * Extract search type from a single RouteDefinition.
104
- * Falls back to `EmptyParams` when the route declares no schema.
105
- */
106
- export type SearchOf<R> = R extends {
107
- search: infer S;
108
- } ? InferOutput<S> : EmptyParams;
109
- /**
110
- * Whether a route requires a `params` argument when calling `nav.push` etc.
111
- * True iff the route definition has a `params` field.
112
- */
113
- export type RouteRequiresParams<R> = R extends {
114
- params: object;
115
- } ? true : false;
116
- /**
117
- * Per-entry state stored on the stack signal.
118
- *
119
- * `key` is unique per entry — needed because the same route can appear more
120
- * than once (e.g. profile A → message → profile A again). Focus state and
121
- * scroll position are keyed by `key`, not by route name.
122
- */
123
- export interface StackEntry<R extends string = string, P = unknown, S = unknown> {
124
- readonly key: string;
125
- readonly route: R;
126
- readonly params: P;
127
- readonly search: S;
128
- /** User state — survives suspend/restore. */
129
- state: unknown;
130
- readonly presentation: Presentation;
131
- }
132
- /** Options accepted by `nav.push` / `nav.replace`. */
133
- export interface PushOptions {
134
- /** Override the route's default presentation for this navigation. */
135
- presentation?: Presentation;
136
- /** User state to attach to the new entry. Survives suspend/restore. */
137
- state?: unknown;
138
- /**
139
- * Skip the slide animation (instant swap). Defaults to true on platforms
140
- * where `useAnimatedStyle` isn't available (test renderer); defaults to
141
- * false on real Lynx. Tests can force `false` to keep assertions
142
- * deterministic.
143
- */
144
- animated?: boolean;
145
- }
146
- /** Options accepted by `nav.pop`. */
147
- export interface PopOptions {
148
- /** Skip the slide animation (instant swap). See `PushOptions.animated`. */
149
- animated?: boolean;
150
- }
151
- /**
152
- * Direction of an in-flight transition.
153
- * - `push`: a new entry is animating in (progress 0 → 1).
154
- * - `pop`: the current top is animating out (progress 0 → 1, then committed).
155
- */
156
- export type TransitionKind = 'push' | 'pop';
157
- /** Role of a screen during a transition — determines its transform formula. */
158
- export type TransitionRole = 'top' | 'underneath';
159
- /**
160
- * Snapshot of an in-flight transition. Stored on the navigator state so the
161
- * `<Stack>` component knows to render two entries (`topEntry` above
162
- * `underneathEntry`) and bind their transforms to `progress`.
163
- *
164
- * `progress` is a `SharedValue<number>` (re-exported as `unknown` here to
165
- * avoid a hard dep on `@sigx/lynx`'s SharedValue type at the contract level —
166
- * the runtime `<Stack>` casts as needed). The value runs 0 → 1 in both push
167
- * and pop, with the role/kind pair determining the visual direction.
168
- */
169
- export interface TransitionState {
170
- readonly kind: TransitionKind;
171
- readonly topEntry: StackEntry;
172
- readonly underneathEntry: StackEntry;
173
- /** Animation progress signal — typed loosely; cast at the runtime boundary. */
174
- readonly progress: unknown;
175
- }
176
- /**
177
- * Per-screen display options written by `<Screen>` into its entry's registry.
178
- *
179
- * Read by persistent navigator chrome (the `<HeaderBar>` shipped in the
180
- * `header` slice; `<TabBar>` later). All fields are optional — consumers
181
- * apply sensible defaults (headerShown defaults to true, gestureEnabled to
182
- * true, title falls back to the route name).
183
- *
184
- * `title` accepts a function so the header can be derived from reactive
185
- * state (e.g. a user's display name signal). Plain strings are wrapped in
186
- * a thunk by consumers when read.
187
- */
188
- export interface ScreenOptions {
189
- /** Header title. Either a static string or a getter (re-tracked each render). */
190
- title?: string | (() => string);
191
- /** When false, the navigator's header is hidden for this screen. Default true. */
192
- headerShown?: boolean;
193
- /** When false, the iOS edge-swipe-back gesture is disabled for this screen. Default true. */
194
- gestureEnabled?: boolean;
195
- }
196
- /**
197
- * Slot fills written by `<Screen.Header>` / `<Screen.HeaderLeft>` /
198
- * `<Screen.HeaderRight>` / `<Screen.TabBarItem>`.
199
- *
200
- * Each fill is the rendered output of that sub-component's `default` slot,
201
- * captured as a thunk so the navigator's persistent chrome can call it at
202
- * render time. `tabBarItem` is a scoped slot — the consumer passes
203
- * `{ active }` so the same screen's tab-bar item can style itself
204
- * differently when focused vs. not.
205
- */
206
- export interface ScreenSlotFills {
207
- /** Full header replacement. When set, takes precedence over title + headerLeft/Right. */
208
- header?: () => unknown;
209
- /** Left-side header content (typically back arrow override). */
210
- headerLeft?: () => unknown;
211
- /** Right-side header content (typically action buttons). */
212
- headerRight?: () => unknown;
213
- /** Tab-bar item — scoped slot receives `{ active }` indicating focus. */
214
- tabBarItem?: (ctx: {
215
- active: boolean;
216
- }) => unknown;
217
- }
@@ -1,15 +0,0 @@
1
- /**
2
- * Typed → URL: build the `url` field of an Href from a route's params/search.
3
- *
4
- * Mirror of parse.ts. Used by `hrefFor()` after schema validation succeeds.
5
- */
6
- /**
7
- * Build the URL form of a route + params + search, or `null` if the route
8
- * declares no `path` template (typed navigation still works — only deep-link
9
- * serialization is unavailable).
10
- *
11
- * Params must already be valid for the route's schema (callers run this after
12
- * `validateSync`). Search values are stringified as-is — schema-validated
13
- * inputs survive round-tripping because `parseHref` re-runs the same schema.
14
- */
15
- export declare function buildUrl(routeName: string, params: Record<string, unknown> | undefined, search: Record<string, unknown> | undefined): string | null;
@@ -1,34 +0,0 @@
1
- /**
2
- * Path template compiler.
3
- *
4
- * Turns a route's `path` (e.g. `/users/:id/posts/:postId`) into a compiled
5
- * object that can both match a URL pathname against it and format a typed
6
- * params object back into a URL.
7
- *
8
- * Supported syntax (intentionally minimal for v1):
9
- * - Literal segments: `/users`, `/users/me`
10
- * - Named params: `:id` (matches `[^/]+`)
11
- * - Trailing slashes tolerated on match
12
- *
13
- * Out of scope for v1 (future-compatible — additions won't break v1 paths):
14
- * - Wildcards `*`
15
- * - Optional params `:id?`
16
- * - Typed/constrained params `:id<number>` or `:id(\\d+)`
17
- */
18
- /** Result of compiling a path template — used by parse + format. */
19
- export interface CompiledPath {
20
- readonly source: string;
21
- readonly paramNames: readonly string[];
22
- /** Regex that matches a URL pathname. Captures are param values in order. */
23
- readonly regex: RegExp;
24
- /**
25
- * Render a URL pathname for this template given param values. Each value
26
- * is `encodeURIComponent`-encoded. Throws if a required `:name` is missing.
27
- */
28
- format(params: Record<string, string | number>): string;
29
- }
30
- /**
31
- * Compile a path template. Throws on malformed input (duplicate param names,
32
- * unexpected `:` syntax). Pure — safe to memoize.
33
- */
34
- export declare function compilePath(template: string): CompiledPath;
@@ -1,28 +0,0 @@
1
- /**
2
- * Format helpers: typed params/search → URL string.
3
- *
4
- * Used by `hrefFor()` to render the `url` field of an Href.
5
- */
6
- /**
7
- * Serialize an object as a `key=value&key=value` querystring.
8
- *
9
- * Keys are sorted to make the output deterministic (useful for tests and
10
- * persistence diffs). `undefined`/`null` values are skipped. Non-primitive
11
- * values are JSON-stringified on the way out — `parseSearch` returns the
12
- * raw string and leaves any JSON decoding to the route's `search` schema
13
- * (e.g. a Zod `transform`), so the round-trip is intentionally one-way at
14
- * this layer.
15
- *
16
- * Returns `''` (empty string) when there are no entries — callers join with
17
- * `?` only when the result is non-empty.
18
- */
19
- export declare function formatSearch(search: Record<string, unknown> | undefined): string;
20
- /**
21
- * Parse a `key=value&key=value` querystring into a string-keyed bag. Values
22
- * are decoded but kept as strings — typed coercion happens in the route's
23
- * `search` schema (e.g. Zod's `z.coerce.number()`).
24
- *
25
- * Multiple occurrences of the same key produce an array. Schemas that don't
26
- * expect arrays will reject this — that's the right failure mode.
27
- */
28
- export declare function parseSearch(query: string): Record<string, string | string[]>;
@@ -1,20 +0,0 @@
1
- /**
2
- * URL → typed Href parser.
3
- *
4
- * Walks every registered route with a `path`, tries to match its compiled
5
- * regex against the URL's pathname, and on a hit validates the extracted
6
- * params + search through the route's Standard Schema. First match wins;
7
- * iteration order follows `Object.keys` of the registered routes map.
8
- *
9
- * Validation failures return `null` rather than throwing — deep-link handlers
10
- * fall back to the initial route on a bad URL instead of crashing the app.
11
- */
12
- import type { Href } from '../href';
13
- /**
14
- * Parse a URL string against the active route registry.
15
- *
16
- * Accepts both absolute URLs (`myapp://host/users/42?tab=about`) and
17
- * pathname-only forms (`/users/42?tab=about`). Returns `null` if no route's
18
- * `path` matches the URL or if schema validation rejects the extracted bits.
19
- */
20
- export declare function parseHrefImpl(url: string): Href | null;
@@ -1,23 +0,0 @@
1
- /**
2
- * Standard Schema validation helper (sync only).
3
- *
4
- * `hrefFor` and `parseHref` run on hot paths (link rendering, deep-link
5
- * resolution) so we restrict to sync validators. Zod/Valibot/ArkType are all
6
- * sync, which covers the common case. Async validators throw a clear error.
7
- */
8
- import type { StandardSchemaV1 } from '../types';
9
- /** Outcome of a sync validation call — discriminated for explicit handling. */
10
- export type ValidateOutcome = {
11
- readonly ok: true;
12
- readonly value: unknown;
13
- } | {
14
- readonly ok: false;
15
- readonly issues: ReadonlyArray<string>;
16
- };
17
- /**
18
- * Run a Standard Schema's `validate` synchronously. When the schema lacks a
19
- * `validate` function (e.g. our test `fakeSchema`), passthrough — assume the
20
- * input is already in the correct shape. This is a deliberate ergonomic
21
- * choice so the type-spike fixtures stay terse.
22
- */
23
- export declare function validateSync(schema: StandardSchemaV1 | undefined, input: unknown): ValidateOutcome;