-
Notifications
You must be signed in to change notification settings - Fork 8
Labels
Milestone
Description
Azure Bord:
As a Fusion Framework App Developer
I want my route configuration to include rich metadata (description, path/search param schema) and be statically analyzable at build time
So that the CLI can generate documentation, OpenAPI specs, prerender lists, navigation trees, and links — without loading the app — chatbot agents can understand and use correct tooling to resolve params and search args — and so that every loader has access to the Fusion framework instance.
Acceptance Criteria
Core Functionality
- App team defines routes using a typed DSL (Domain-Specific Language) (
route(),index(),prefix(),layout(), etc.) that compiles to React Router v7RouteObject[] - Each route supports optional metadata:
description,params(path params),search(query params) paramsandsearchschemas include:description, optionaltype(string,number,boolean), andenum(array of allowed values)- Route metadata is extracted during existing
ffc app manifestandffc portal manifestcommands - Routes are added to
AppBuildManifestandPortalManifestBuildSchemaas optionalroutesfield - The manifest contains only:
path,description,params,search— no file paths, no component references - The
<Router>component injects the Fusion framework instance into every loader via React Router'scontext - Loaders access framework via
loader({ context })→context.frameworkwith full TypeScript support - No runtime cost: manifest is generated before bundling (static analysis only)
- Full TypeScript support:
RouteNode,ParamSchema,SearchSchema,ManifestEntry,LoaderContext - Works with React Router v7 (
createBrowserRouter,lazy,handle,loader,action)
DSL API Design
route(path, component, options?)- Define a route with optional metadataindex(component, options?)- Define an index routelayout(component, children, options?)- Define a layout routeprefix(prefix, children)- Group routes with a common prefix- DSL supports nested routes via
childrenarray - DSL supports all React Router features:
lazy,loader,action,errorElement,handle - DSL is backward compatible: existing
RouteObject[]can be gradually migrated
Framework Injection
- Framework instance is injected via React Router's
contextoption increateBrowserRouter - Loader context type:
{ framework: Fusion, params: Record<string, string>, request: Request } - Framework is available in all loaders regardless of route depth
- Framework injection works with nested routers (if any)
- Type-safe loader function:
loader: (args: LoaderArgs) => Promise<Response>whereLoaderArgsincludescontext.framework
Build & Integration
- Route extraction runs during build process (before bundling) as part of manifest generation
- Route extraction does not require app execution or DOM environment
- CLI validates route schemas and reports errors with file locations during manifest generation
- Routes in manifest can be consumed by documentation tools, SSG tools, and other build-time tools
- Routes field is optional - apps without routes still generate valid manifests
- Link generation: Tools can generate links to routes using only the DSL/manifest (no runtime execution or file paths needed)
- Chatbot/AI agent integration: Manifest routes can be used by AI agents to understand route structure and validate params/search args when generating links
Type Safety & Developer Experience
- TypeScript infers route paths from DSL definitions
- Type-safe route generation:
generatePathanduseParamswork with typed routes - IntelliSense support for route metadata (autocomplete descriptions, params, search)
- Compile-time validation of enum values matches route usage
- Clear error messages when route definitions are invalid
Non-Functional Requirements
- Zero runtime overhead: DSL is compile-time only
- Bundle size impact: < 1KB for route DSL utilities
- Build time impact: < 100ms for typical app (50-100 routes)
- Backward compatible: existing apps continue to work without migration
- Migration path: apps can gradually adopt DSL alongside existing routes
Edge Cases & Error Handling
- Handles routes with dynamic segments (
:param,*splat) - Handles optional route segments
- Handles routes with query string parameters
- Handles routes with no metadata (optional feature)
- Handles invalid route definitions with clear error messages
- Handles circular route dependencies
- Handles routes defined in multiple files
Reactions are currently unavailable