Skip to content

Angular ​

headless-prerender works with a client-side Angular app (the default ng build output) when Angular Universal / SSR is not in use.

When you need it ​

index.html bootstraps into <app-root>:

html
<app-root></app-root>
<script src="main.js" type="module"></script>

Non-JS crawlers see an empty <app-root>. The prerender service returns the rendered DOM.

Consider Angular SSR first

Angular has first-class server-side rendering (ng add @angular/ssr). If you can adopt it, that is the better long-term option. Use headless-prerender when SSR is not currently feasible.

Setup ​

  1. Deploy the browser build (dist/<app>/browser) as static files.

  2. Run the service:

    bash
    headless-prerender serve \
      --port 3000 \
      --allow-origin https://www.example.com \
      --cache-ttl 300000
  3. Route bot traffic to it.

Waiting for stability ​

Angular apps often settle quickly, but HTTP calls in ngOnInit or route resolvers may land after network idle. Add settle time:

bash
headless-prerender serve --extra-wait 500

For a deterministic signal, set a flag when the app is stable:

ts
import { ApplicationRef } from "@angular/core";
import { first } from "rxjs/operators";

constructor(appRef: ApplicationRef) {
  appRef.isStable.pipe(first((stable) => stable)).subscribe(() => {
    (window as any).__PRERENDER_READY__ = true;
  });
}

Meta tags ​

Use Angular's Title and Meta services per route:

ts
constructor(private title: Title, private meta: Meta) {}

ngOnInit() {
  this.title.setTitle(this.product.name);
  this.meta.updateTag({ property: "og:title", content: this.product.name });
  this.meta.updateTag({ property: "og:description", content: this.product.summary });
}

The renderer captures the resulting <head>.

404 status codes ​

Render a status-code meta tag on your not-found route and have the proxy read it:

ts
this.meta.updateTag({ name: "prerender-status-code", content: "404" });

Checklist ​

  • [ ] SPA fallback to index.html configured on the host
  • [ ] --allow-origin set
  • [ ] --extra-wait covers resolver / HTTP latency
  • [ ] Title / Meta set per route
  • [ ] 404 routes marked
  • [ ] Caching enabled

Released under the MIT License.