router-core

Angular's router is solid, but reading its state means subscribing to observables, and every navigation flashes to loading. These helpers hand you router state as signals, drive titles and menus straight from your Routes, preload lazy chunks before the click, and hold the old view on screen until the new one is ready.

@mmstack/router-corenpm

npm install @mmstack/router-core

Nothing here replaces the router. Your Routes config, guards, and resolvers stay exactly as they are. Every helper is opt-in, so you can pull in the reactive url signal on a Tuesday and never touch the rest, or wire up the transition outlet the week after. Pick what solves a problem you actually have.

#Start here

Each row is a thing you might be trying to do and where to go for it. If you are new, the reactive state helpers are the gentlest entry point; the transition outlet is the one people remember.

You want toReach for
Read the current URL or a query param as a signalurl, queryParam
Recompute per navigation, even same-URL reloadsnavigationEndTick
Preload a lazy route's chunk on hover or visibilitymmLink, PreloadStrategy
Preload imperatively, from an effect or a shortcutinjectTriggerPreload
Fetch a route's data at the resolve phase, before the component createRouteData, injectRouteData
Hold the old view on screen until the new one's data settles mm-transition-outlet
Stabilize a persisted resource so it never flashes mid-navigation holdThroughNavigation
Set the document title, breadcrumbs, or nav menus from routes createTitle, createBreadcrumb, createNavItems

#Built for any resource

The transition outlet and route-level data both build on the transition-scope primitive from @mmstack/primitives. That primitive tracks readiness, not fetching, so @mmstack/router-core never imports a resource library. Your factory is the one and only place a resource gets named.

In practice that means you reach for @mmstack/resource's queryResource, Angular's own httpResource, or anything that hands back a ResourceRef, and the router pieces work the same way regardless. You are not locked into a data layer to use the routing layer.