UNPKG

@furystack/shades

Version:

A lightweight UI framework for FuryStack with JSX support

59 lines 2.41 kB
import { serializeToQueryString } from '@furystack/rest'; import { compileRoute } from '../compile-route.js'; import { LocationService } from '../services/location-service.js'; /** * Builds the resolved URL for a nested navigate call, including path parameters, * serialized query string and hash segment. Exported for callers that need the * URL without side effects (e.g. link rendering helpers). */ export const buildNestedNavigateUrl = (args) => { const { path, params, query, hash } = args; const resolvedPath = params && Object.keys(params).length > 0 ? compileRoute(path, params) : path; const hasQuery = query && Object.keys(query).length > 0; const search = hasQuery ? `?${serializeToQueryString(query)}` : ''; const hashPart = hash ? `#${hash}` : ''; return `${resolvedPath}${search}${hashPart}`; }; /** * Navigates to a route using the LocationService resolved from the given injector. * Compiles parameterized routes (e.g. `/users/:id`), serializes the optional * `query` record with the default `@furystack/rest` serializer, and appends the * optional `hash` segment. * * @param injector - The injector instance to resolve LocationService from * @param args - The navigation arguments */ export const nestedNavigate = (injector, args) => { injector.get(LocationService).navigate(buildNestedNavigateUrl(args)); }; /** * Creates a type-safe navigate function constrained to a specific route tree. * The returned function has the same runtime behavior as {@link nestedNavigate} * but narrows `path` to only accept valid route paths, requires `params` when * the route has parameters, and enforces the route's declared `query` and * `hash` schemas. * * Unlike {@link createNestedRouteLink}, the injector is passed at call time, * not at creation time. * * @typeParam TRoutes - The route tree type (use `typeof yourRoutes`) * @returns A type-safe navigate function * * @example * ```typescript * const appNavigate = createNestedNavigate<typeof appRoutes>() * * appNavigate(injector, { path: '/buttons' }) * appNavigate(injector, { path: '/users/:id', params: { id: '123' } }) * appNavigate(injector, { * path: '/users/:id', * params: { id: '123' }, * query: { tab: 'profile' }, * hash: 'settings', * }) * ``` */ export const createNestedNavigate = () => { return nestedNavigate; }; //# sourceMappingURL=nested-navigate.js.map