Reader Stacks

What Is ng-container in Angular, and When to Use It

A grouping element that never renders to the DOM — useful for applying *ngIf or *ngFor without adding an extra wrapping element that would break your CSS or semantics.

What Is ng-container in Angular, and When to Use It

<ng-container> is a logical grouping element Angular understands at compile time but never actually renders into the DOM — no wrapping <div> or <span> appears in the final HTML. It exists specifically for cases where you need a structural directive (*ngIf, *ngFor) without a real element to attach it to.

The problem it solves

<!-- Adds an unwanted <div> to the DOM just to hold *ngIf -->
<div *ngIf="showDetails">
  <h2>{{ title }}</h2>
  <p>{{ description }}</p>
</div>

<!-- No extra element in the rendered output -->
<ng-container *ngIf="showDetails">
  <h2>{{ title }}</h2>
  <p>{{ description }}</p>
</ng-container>

The difference matters when the extra wrapping element would break CSS selectors relying on direct parent-child relationships (like flex or grid layouts), or when it would be semantically wrong (wrapping <li> elements in a <div> inside a <ul>, for example, which is invalid HTML).

Combining multiple structural directives

Angular doesn't allow two structural directives on the same element (*ngIf and *ngFor can't both go on the same tag) — ng-container is the standard way around that, nesting one inside the other without adding real elements for either:

<ng-container *ngIf="items.length > 0">
  <ng-container *ngFor="let item of items">
    <li>{{ item.name }}</li>
  </ng-container>
</ng-container>

With ng-template and else

<ng-container *ngIf="isLoggedIn; else guestView">
  <p>Welcome back!</p>
</ng-container>
<ng-template #guestView>
  <p>Please log in.</p>
</ng-template>

Modern alternative: the @if/@for control-flow syntax

Angular 17+ introduced a built-in template control-flow syntax (@if, @for) that doesn't require ng-container for most of these cases at all, since @if/@for blocks aren't tied to a host element the way structural directives are. ng-container is still relevant for projects on the older directive-based syntax, or for edge cases the new control-flow syntax doesn't cover directly (like ngSwitch grouping).