Skip to the solution
HardFrontend8 min read

What are Deferrable Views (@defer) and how do they work in Angular 17+?

1.2k views

The problem

Question presented to candidate: "Our product page ships the comments widget and a chart library in the main bundle even though most users never scroll to them. What are deferrable views in Angular, how do the @defer blocks fit together, and what happens at runtime?"

What a strong answer should cover:

  • @defer (v17, stable v18) lazily loads a part of a template and the code of the standalone components, directives and pipes inside it.
  • The companion blocks: @placeholder, @loading, @error, with minimum and after timing options.
  • Triggers: default on idle; on viewport | interaction | hover | timer(...) | immediate, when expr; plus prefetch variants.
  • Runtime states: placeholder, then loading, then complete or error.
  • Requirements and limits: dependencies must be isolated to split; a trigger without a target needs a @placeholder.
  • SSR: the placeholder is server-rendered; hydrate triggers change that.

Clarifying questions expected:

  • "Do we render on the server? That changes what crawlers see inside the block."
  • "Is the heavy code only used in this section, or imported elsewhere too?"

Code / implementation expected: Yes β€” a @defer block with placeholder, loading and error states.

  • performance
  • routing
  • defer

Try it yourself

Sketch your approach before you read the solution. That is what the interview tests.

Stuck? Get a hint.

A short nudge toward the approach. It will not give the answer away.

Solution

The solution is hidden so you can try first

8 min read Β· 9 sections

Read the code

AngularA product page that loads comments on click, with placeholder, loading and error blocks
import { Component } from "@angular/core";

// In a real app this component lives in its own file and is used ONLY inside
// @defer, so the compiler moves it into a separate lazy chunk.
@Component({
  selector: "app-comments",
  template: `<ul><li>Great tea</li><li>Arrived fast</li></ul>`,
})
export class CommentsComponent {}

@Component({
  selector: "app-root",
  imports: [CommentsComponent],
  template: `
    <h3>Product page</h3>
    @defer (on interaction; prefetch on idle) {
      <app-comments />
    } @placeholder (minimum 500ms) {
      <button>Show comments</button>
    } @loading (after 100ms; minimum 300ms) {
      <p>Loading comments...</p>
    } @error {
      <p>Could not load comments.</p>
    }
  `,
})
export class AppComponent {}

Discussion

Other approaches, follow-ups and how it went in real interviews.

Sign in to join the discussion.

No comments yet. Share how you would answer it.

Question 81 of 121 in Angular

Keep your momentum going.

Mark this question solved to track your progress, then take the next one while it is fresh.

All Angular questions
Up nextHard

viewChild() signal queries vs @ViewChild decorator β€” what changed?

Continue