Acumatica · Astro

Astro Server Islands — A Field Guide

Server islands let an Astro page cache its static shell aggressively while personalised or dynamic fragments render on the server on demand — static speed without giving up dynamic content.

John Kihiu12 min read

Server islands extend Astro's islands architecture to solve a different problem than client islands: content that must be rendered on the server, per-request, but shouldn't block the rest of an otherwise-static page from serving instantly. A server island renders on-demand while the surrounding page is served from cache or a static build — the personalised or slow-to-compute part streams in afterward rather than forcing the whole page onto the dynamic, per-request rendering path.

The problem server islands solve

Without server islands, a page with one personalised element — a "signed in as X" header, or a recommendation widget that needs a database lookup — forces the entire page into server-rendered (SSR) mode, losing the CDN-cacheable, instantly-served static output for everything else on the page. Server islands let you keep the page static and cacheable while carving out just that one component to render per-request on the server, deferred and streamed in after the initial HTML ships.

ASTRO · SERVER ISLAND USAGE
---
import Avatar from '../components/Avatar.astro';
---

  
    
    

    
    

    
Static footer

How the request actually flows

The initial response ships the static shell immediately with a placeholder where the server island will appear, then the browser makes a follow-up request for that island's rendered output and swaps it in — similar in spirit to a Suspense boundary in React Server Components, but implemented at the Astro component level rather than the framework's rendering tree. The visitor sees the page instantly; the personalised fragment appears a beat later once its request resolves.

Server islands vs. client islands

The two solve different problems and are easy to conflate. A client island (client:load, client:visible, etc.) ships JavaScript to the browser so a component can be interactive after the page loads — it still renders the same HTML for every visitor unless client-side logic changes it. A server island (server:defer) renders different HTML per request on the server, with no client-side JavaScript required for the island itself, though the fetched content can of course include its own client islands if it needs interactivity too.

Server islands need a request-capable deployment target

Server islands require an Astro adapter that supports on-demand rendering (Node, Vercel, Netlify, Cloudflare, etc.) — a pure static-output build has nothing to render the deferred fragment against per request, so this feature only applies once you're running Astro in SSR/hybrid mode, not a fully static export.

Fallback content and loading states

Because the server island's content arrives after the initial page render, you control what shows in the interim with a named slot="fallback" — a skeleton loader, a cached last-known value, or simply nothing if the layout tolerates the gap. Keep the fallback visually stable so the swap doesn't cause a layout shift once the real content streams in; a fixed-height placeholder matching the eventual content's dimensions avoids a Cumulative Layout Shift penalty.

Don't defer content that's needed for SEO

Deferred server island content is not present in the initial HTML response, so search engine crawlers that don't execute the follow-up request may not see it. Keep anything load-bearing for SEO — primary content, headings, canonical metadata — in the static shell, and reserve server islands for genuinely personalised or non-indexable fragments.

FeatureClient islandServer island
Renders whereBrowser, after hydrationServer, per request
Ships JS to browserYesNo (for the island itself)
Personalised per visitorOnly via client-side logicNatively, per request
Needs SSR adapterNoYes

Wrapping up

Server islands are the right tool when one fragment of an otherwise static page genuinely needs per-request, server-side data — a personalised greeting, a live inventory count, a signed-in user's avatar — without paying the cost of moving the whole page to SSR. Keep anything SEO-critical out of the deferred fragment, design a stable fallback to avoid layout shift, and remember this only works once the project is deployed with an adapter that supports on-demand rendering.

John Kihiu
Acumatica ERP Developer · Laravel Engineer

Independent software engineer in Nairobi specialising in Acumatica customisations, Laravel backends, and tax fiscalisation integrations across East and Southern Africa.