Skip to content

Angular Routing

Routing lets a single-page Angular application show different views for different URLs without a full page reload. This lesson introduces Angular's router and how to wire it into a standalone application.

What Is Angular Routing?

Angular's router (@angular/router) maps URL paths to components, swapping which component renders inside a <router-outlet> as the URL changes, entirely within the browser, without a full page reload.

In modern standalone applications, routing is configured with provideRouter() in the application config, rather than importing RouterModule into an NgModule.

// app.routes.ts
export const routes: Routes = [
  { path: '', component: HomeComponent },
  { path: 'about', component: AboutComponent },
];

// app.config.ts
export const appConfig: ApplicationConfig = {
  providers: [provideRouter(routes)],
};

// app.component.html
<nav>
  <a routerLink="/">Home</a>
  <a routerLink="/about">About</a>
</nav>
<router-outlet></router-outlet>

<router-outlet> marks where the router renders the component matching the current URL.

Basic Router Setup

const routes: Routes = [
  { path: 'path', component: SomeComponent },
];

provideRouter(routes)
<router-outlet></router-outlet>
<a routerLink="/path">Link</a>
  • A Routes array maps URL path strings to components (or lazy-loaded modules/components).
  • provideRouter(routes) registers the router and its configuration for a standalone app.
  • <router-outlet> is the placeholder where the currently matched route's component renders.
  • routerLink is the directive used for internal navigation instead of a plain href.

Angular Routing Cheatsheet

Core APIs and directives for setting up navigation.

API/Directive Example Purpose
Route definition { path: 'users', component: UsersComponent } Map a URL to a component
Router provider provideRouter(routes) Register routing for a standalone app
Outlet <router-outlet></router-outlet> Renders the matched route's component
Link directive <a routerLink="/users"> Client-side navigation link
Active link styling routerLinkActive="active" Applies a class to the active link
Programmatic navigation inject(Router).navigate(['/users']) Navigate from code
Wildcard route { path: '**', component: NotFoundComponent } Catch-all for unmatched URLs

Defining Routes

Each entry in a Routes array describes a path and what should render for it, a component, a redirect, or a lazily loaded chunk. Angular matches routes top to bottom, using the first one that matches the current URL.

export const routes: Routes = [
  { path: '', component: HomeComponent },
  { path: 'users', component: UserListComponent },
  { path: 'users/:id', component: UserDetailComponent },
  { path: '', redirectTo: '/home', pathMatch: 'full' },
  { path: '**', component: NotFoundComponent },
];

The wildcard route (**) should always be last, it matches anything not caught by earlier routes.

Programmatic Navigation

Sometimes navigation needs to happen from code, after a form submits successfully, for example, rather than from a template link. The injectable Router service exposes a navigate() method for this.

export class OrderFormComponent {
  private router = inject(Router);

  onSubmit() {
    this.router.navigate(['/orders', 'confirmation']);
  }
}

Common Mistakes

  • Forgetting to add <router-outlet> anywhere, so routed components have nowhere to render.
  • Using a plain <a href="/users"> instead of routerLink, causing a full page reload and losing SPA state.
  • Placing the wildcard (**) route anywhere but last, causing it to swallow more specific route matches.
  • Forgetting provideRouter(routes) in the application config, leaving routing entirely non-functional.

Key Takeaways

  • The Angular router maps URL paths to components and renders them inside <router-outlet>.
  • provideRouter(routes) wires routing into a standalone application.
  • routerLink and routerLinkActive handle internal navigation and active-state styling declaratively.
  • The injectable Router service supports navigating programmatically from component code.

Pro Tip

Always place a wildcard { path: '**', component: NotFoundComponent } route last in your route configuration; without one, unmatched URLs render a blank router-outlet with no feedback to the user.