Zum Inhalt springen
    WingoUI
    KomponentenVorlagenDokuPreiseKI-AgentenBlogChangelog
    1. Startseite
    2. Blog
    3. Praxis: Screens und Apps
    4. React 404 Seite: 5 Fehlerseiten für den Next.js App Router
    Read in English
    1. Blog
    2. Praxis: Screens und Apps
    3. React 404 Seite: 5 Fehlerseiten für den Next.js App Router
    Praxis: Screens und Apps
    Praxis: Screens und Apps

    React 404 Seite: 5 Fehlerseiten für den Next.js App Router

    SR
    Serban Rusu · Gründer von Wingo UI
    16. Okt. 2026 · 12 Min. Lesezeit

    Auf dieser Seite

    0%
    1. Was sollte eine React 404 Seite leisten?
    2. Welche Fehlerseiten braucht eine Next.js App?
    3. Wie installiere ich eine Vorlage für eine React 404 Seite?
    4. Wie baue ich eine Next.js 404 Seite?
      1. Wann ist eine komplette 404-Seite zu viel?
    5. Wie zeige ich eine 500-Seite mit Retry?
    6. Wie baue ich eine React Wartungsseite?
    7. Wie bekommt meine PWA eine Offline-Seite?
    8. Wie zeige ich eine Seite für fehlenden Zugriff an?
    9. Wie sieht das fertige Setup aus?
    10. Häufige Fragen
      1. Wie erstelle ich eine 404-Seite im Next.js App Router?
      2. Liefert die Next.js not found page einen 404-Statuscode?
      3. Wie baue ich eine 404-Seite mit React Router?
      4. Welchen Statuscode sollte eine Wartungsseite liefern?
      5. Wie zeige ich in einer PWA eine Offline-Seite an?

    Kurz gesagt

    Eine gute React 404 Seite sagt, was schiefging, bietet eine Suche und ein paar naheliegende Ziele an und antwortet mit einem echten 404-Status (oder zumindest noindex), damit Suchmaschinen die URL verwerfen. Im Next.js App Router übernimmt not-found.tsx den 404, error.tsx und global-error.tsx den 500, forbidden.tsx den 403, proxy.ts liefert die Wartungsseite mit einem 503 aus und ein Service Worker die Offline-Seite. Der Error Pages Block von Wingo UI (Pro) rendert alle fünf Screens über einen einzigen variant-Prop.

    Veröffentlicht am 16. Okt. 2026

    Die meisten Vorlagen für eine React 404 Seite bestehen aus einer großen Zahl, einer traurigen Illustration und einem Button „Go home“. Damit ist einer der fünf Fehler-Screens abgedeckt, auf die eine echte App trifft, und den Statuscode überlässt sie dem, was der Server gerade schickt. Dieses Tutorial baut eine React 404 Seite, die Leuten hilft, ans Ziel zu kommen, und danach die vier Screens daneben: eine 500-Seite mit Retry, eine Wartungsseite mit Countdown, eine Offline-Seite für deine PWA und eine Seite für fehlenden Zugriff, über die man Zugriff anfragen kann. Alles wird im Next.js App Router verdrahtet, mit den Dateikonventionen von Next.js 16.3. Wir bauen Wingo UI, und der Code nutzt unseren Block Error Pages. Wir sind also nicht neutral; die Verdrahtung funktioniert mit jeder Komponente.

    Was sollte eine React 404 Seite leisten?

    Sie bringt die Person auf eine funktionierende Seite und hält die tote URL aus der Suche heraus. Vier Dinge entscheiden, ob jemand den Weg zurückfindet:

    • Sag in klaren Worten, was passiert ist. „Diese Seite gibt es nicht oder sie wurde verschoben“, nicht „Error 404“.
    • Biete den nächsten Schritt an. Ein Suchfeld, die drei oder vier Seiten, die Leute am häufigsten suchen, und einen Weg zurück dorthin, wo sie herkamen.
    • Liefere den richtigen Status. Google markiert eine Seite, die mit 200 antwortet, aber eine Fehlermeldung zeigt, in der Search Console als Soft 404 (opens in a new tab). Die Not-found-Oberfläche braucht einen 404, oder zumindest ein noindex.
    • Setz den Fokus nach einer clientseitigen Navigation auf den Titel, damit jemand mit Screenreader hört, dass sich die Seite geändert hat. Beim ersten Laden lässt du das, denn da beginnt der Browser ohnehin oben. Der Error Pages Block hält sich über seinen Prop autoFocusTitle an diese Regel (standardmäßig an).

    Dieselbe Checkliste gilt für die anderen vier Fehler-Screens, jeweils mit einem anderen nächsten Schritt.

    Welche Fehlerseiten braucht eine Next.js App?

    Fünf: nicht gefunden, Serverfehler, Wartung, offline und kein Zugriff. Jede hat ihren eigenen Einstiegspunkt im App Router:

    ScreenEinstiegspunkt im App RouterStatusWas die Person tun kann
    Nicht gefundenapp/not-found.tsx, notFound()404 (200 + noindex beim Streaming)Suchen, eine vorgeschlagene Seite öffnen, zurückgehen
    Serverfehlerapp/error.tsx, app/global-error.tsx500Erneut versuchen, eine Fehler-ID für den Support kopieren
    Wartungproxy.ts leitet den Traffic auf /maintenance503 + Retry-AfterSehen, wann sie endet, die Statusseite prüfen
    OfflineEin Fallback im Service Worker, useOfflinekeiner (kein Netz)Auf den automatischen Retry warten, gespeicherte Seiten öffnen
    Kein Zugriffapp/forbidden.tsx, forbidden()403Zugriff anfragen, Konto wechseln

    Die Fakten in dieser Tabelle stammen aus der Doku von Next.js 16.3, die in node_modules/next/dist/docs mitkommt, gelesen am 16. Oktober 2026. forbidden.tsx und useOffline sind dort noch experimentell.

    Wie installiere ich eine Vorlage für eine React 404 Seite?

    Installier den Error Pages Block mit der CLI:

    bash
    npx wingo-ui@latest add error-pages

    Das kopiert components/blocks/error-pages.tsx mit seiner Datendatei und den Teilen, aus denen er besteht (Alert, Countdown, Tracker, Dialog, Suchfeld und ein paar mehr), dazu die npm-Pakete, die sie brauchen, darunter motion, lucide-react, react-hook-form und zod. Error Pages gehört zu Wingo UI Pro.

    Die Standardwerte des Blocks sind Demo-Inhalte: ein Acme-CRM-Logo, support@acme.com, Beispiel-Admins, ein Beispiel-Stacktrace. Gib einmal deine eigenen mit, in einem kleinen Client-Wrapper, der ihm auch den Link von Next.js übergibt:

    tsx
    // components/app-error-page.tsx
    "use client"
    import Link from "next/link"
    import { ErrorPage, type ErrorPageProps } from "@/components/blocks/error-pages"
    export function AppErrorPage(props: ErrorPageProps) {
    return (
    <ErrorPage
    linkComponent={Link}
    logo={<span className="font-semibold">Northwind</span>}
    supportHref="mailto:help@northwind.app"
    statusHref=""
    {...props}
    />
    )
    }

    statusHref="" blendet die Links zur Statusseite aus, bis du eine hast. Server-Dateien wie not-found.tsx können diesen Wrapper direkt rendern, solange jeder Prop, den sie übergeben, reine Daten, JSX (Icons gehen) oder eine Server Action ist. Funktionen, die in einer Server-Datei definiert sind, lassen sich nicht an den Client-Wrapper übergeben.

    Wie baue ich eine Next.js 404 Seite?

    Leg app/not-found.tsx an. Diese Datei ist die Next.js not found page: Sie rendert für jede URL, zu der keine Route passt, und für jedes Segment, das notFound() aufruft:

    tsx
    // app/not-found.tsx
    import { BarChart3, FileText, LayoutDashboard, LifeBuoy } from "lucide-react"
    import { AppErrorPage } from "@/components/app-error-page"
    const suggestions = [
    { label: "Dashboard", href: "/dashboard", icon: <LayoutDashboard />, description: "Der Tag auf einen Blick" },
    { label: "Rechnungen", href: "/invoices", icon: <FileText />, description: "Gesendet, bezahlt und überfällig" },
    { label: "Berichte", href: "/reports", icon: <BarChart3 />, description: "Umsatz nach Monat" },
    { label: "Hilfe-Center", href: "/help", icon: <LifeBuoy />, description: "Anleitungen und Antworten" },
    ]
    export default function NotFound() {
    return <AppErrorPage variant="404" suggestions={suggestions} />
    }

    Das Suchfeld navigiert standardmäßig mit Enter zu /search?q=. Übergib onSearch aus einer Client-Komponente, um woandershin zu leiten, oder showSearch={false}, wenn du keine Suche hast. „Go back“ nutzt history.back(), wenn es einen Verlauf gibt, und fällt auf den Link zur Startseite zurück, wenn der Tab keinen Verlauf hat, etwa weil der Link in einem neuen Tab geöffnet wurde.

    Drück /, um die Suche zu fokussieren, tipp eine Anfrage und drück Enter, oder fahr über die Vorschlagskarten: Jede ist ein einfacher Link
    $ npx wingo-ui@latest add error-pages
    ProDoku: Error Pages

    Für einen fehlenden Datensatz rufst du notFound() in der Seite auf, die ihn lädt:

    tsx
    // app/invoices/[id]/page.tsx
    import { notFound } from "next/navigation"
    import { getInvoice } from "@/lib/invoices"
    export default async function InvoicePage({ params }: { params: Promise<{ id: string }> }) {
    const { id } = await params
    const invoice = await getInvoice(id)
    if (!invoice) notFound()
    return <InvoiceView invoice={invoice} />
    }

    Zwei Details zum Status, die die Doku ausdrücklich nennt. notFound() liefert einen 404, solange die Antwort noch nicht gestreamt wird. Hat eine loading.tsx-Boundary die Shell schon gesendet, bleibt der Status 200, und Next.js fügt stattdessen <meta name="robots" content="noindex"> ein. Brauchst du den echten 404 für deine Analytics, prüf, ob der Datensatz existiert, bevor irgendetwas gestreamt wird. Und wenn eine App mehrere Root-Layouts hat, gibt dir das experimentelle global-not-found.tsx (hinter experimental.globalNotFound) einen einzigen 404, der ganz ohne Layout rendert.

    Wann ist eine komplette 404-Seite zu viel?

    Wenn die URL stimmt und nur die Daten leer sind. Eine Suche ohne Treffer, eine gefilterte Tabelle mit null Zeilen oder ein neues Konto ohne Rechnungen sollten mit 200 und einem Empty State innerhalb der Seite antworten, nie mit einem 404. Der kostenlose Empty State deckt diesen Fall mit seinen Presets no-results, empty, no-permission und offline ab, und live kündigt ihn Screenreadern an, wenn sich die Ergebnisse ändern:

    tsx
    // app/invoices/invoice-list-empty.tsx
    "use client"
    import { Button } from "@/components/ui/button"
    import { EmptyState } from "@/components/ui/empty-state"
    export function InvoiceListEmpty({ query, clearFilters }: { query: string; clearFilters: () => void }) {
    return (
    <EmptyState
    preset="no-results"
    live
    title={`Keine Rechnungen zu "${query}"`}
    description="Versuch einen anderen Kundennamen oder setz die Filter zurück."
    actions={<Button variant="outline" onClick={clearFilters}>Filter zurücksetzen</Button>}
    />
    )
    }

    Wie zeige ich eine 500-Seite mit Retry?

    Leg app/error.tsx an und verbinde seinen Prop retry mit dem Button „Try again“. Die Datei packt jedes Segment in eine React Error Boundary, also muss sie eine Client-Komponente sein. Seit Next.js 16.3 ist der Prop retry stabil. Er lädt die Daten des Segments neu und rendert es neu, anders als das ältere reset(), das nur neu rendert, ohne neu zu laden. Ein Segment, dessen Datenabruf fehlschlug, zeigt mit reset() also wieder denselben Fehler:

    tsx
    // app/error.tsx
    "use client"
    import { usePathname } from "next/navigation"
    import { useEffect } from "react"
    import { AppErrorPage } from "@/components/app-error-page"
    export default function Error({ error, retry }: { error: Error & { digest?: string }; retry: () => void }) {
    const pathname = usePathname()
    useEffect(() => {
    console.error(error)
    }, [error])
    return (
    <AppErrorPage
    variant="500"
    errorId={error.digest ?? ""}
    error={error}
    errorPath={pathname}
    showDetails={process.env.NODE_ENV === "development"}
    onRetry={retry}
    />
    )
    }

    error.digest ist der Hash, den Next.js auch ins Server-Log schreibt. Damit eignet er sich gut als ID, die Leute dem Support nennen können: Der Block kopiert ihn mit einem Klick. Fehler, die im Browser geworfen werden, haben keinen Digest, und errorId="" blendet die Zeile mit der ID aus. In Produktion kommen Fehler aus Server Components mit einer generischen Meldung beim Client an, und den Stacktrace brauchen Besucher ohnehin nicht. Deshalb erscheinen die technischen Details hier nur in der Entwicklungsumgebung.

    Drück Try again: Der erste Versuch scheitert und zeigt, wann, der zweite klappt. Öffne Technical details, um Pfad und Stacktrace zu sehen
    $ npx wingo-ui@latest add error-pages
    ProDoku: Error Pages

    error.tsx fängt keine Fehler im Root-Layout ab. Dafür ergänzt du app/global-error.tsx. Diese Datei ersetzt das ganze Dokument, rendert also ihr eigenes <html> und <body> und importiert deine Styles:

    tsx
    // app/global-error.tsx
    "use client"
    import "./globals.css"
    import { AppErrorPage } from "@/components/app-error-page"
    export default function GlobalError({ error, retry }: { error: Error & { digest?: string }; retry: () => void }) {
    return (
    <html lang="de">
    <body className="bg-background text-foreground">
    <AppErrorPage variant="500" errorId={error.digest ?? ""} showDetails={false} onRetry={retry} />
    </body>
    </html>
    )
    }

    Sie liegt außerdem außerhalb jedes Theme-Providers. Ein klassenbasierter Dark Mode erreicht sie also nicht: Diese Seite rendert mit deinen hellen Tokens, solange du die Klasse nicht selbst setzt.

    Innerhalb einer App-Shell übergibst du layout="inline" an eine beliebige Variante, zum Beispiel aus einem verschachtelten app/(app)/error.tsx. Die Seite lässt dann ihr eigenes Logo und ihren Footer weg und füllt den Hauptbereich der Shell. Scheitert ein Bericht, bleibt die Sidebar deiner Admin Shell also drumherum stehen.

    Wie baue ich eine React Wartungsseite?

    Liefer sie mit einem 503-Status aus und sag den Leuten, wann sie endet. Eine typische React Wartungsseite ist ein statisches „Wir sind bald zurück“, das mit 200 antwortet, und macht damit beides falsch. Googles Doku zu HTTP-Statuscodes (opens in a new tab) (aktualisiert am 4. Februar 2026) beschreibt, dass 5xx-Antworten die Crawler bremsen, dass Inhalte von diesen URLs ignoriert werden und dass indexierte URLs zunächst erhalten bleiben und erst verschwinden, wenn die Fehler anhalten. Eine Wartungsseite mit 200 bekommt keinen dieser Schutzmechanismen.

    Die Seite selbst ist eine ganz normale Route:

    tsx
    // app/maintenance/page.tsx
    import { connection } from "next/server"
    import { AppErrorPage } from "@/components/app-error-page"
    export default async function Maintenance() {
    // die env zur Anfragezeit lesen, nicht beim Build
    await connection()
    return (
    <AppErrorPage
    variant="maintenance"
    // ein ISO-Datum wie 2026-10-18T04:00:00Z
    until={process.env.MAINTENANCE_UNTIL}
    showStatus={false}
    showSubscribe={false}
    />
    )
    }

    until steuert einen live laufenden Countdown. Erreicht er null, meldet die Seite, dass die Wartung vorbei ist, und der Haupt-Button wird zu „Reload“. Dabei gibt es zwei Fallstricke. Ohne connection() wird die Seite vorgerendert und behält den Wert, den MAINTENANCE_UNTIL beim Build hatte. Und fehlt die Variable, fällt until auf das Beispieldatum des Blocks zurück, das in der Vergangenheit liegt. Die Seite öffnet dann mit „Maintenance is over“. showStatus und showSubscribe sind aus, weil ihre Standardwerte Beispieldaten sind: Schalte sie ein, sobald du deine eigene statusHistory (ein Tracker über 30 Tage) und eine Server Action für onSubscribe übergibst. Für eine vollständige öffentliche Uptime-Seite ist die Vorlage Status Page der separate Screen, auf den statusHref zeigen sollte.

    Um jede Anfrage dorthin zu schicken, nimm proxy.ts (die Datei, die in Next.js 16 middleware.ts ersetzt hat). Verlass dich für den Status nicht auf NextResponse.rewrite(): Im Router von 16.3 reicht ein Rewrite die Header des Proxys weiter, aber die Zielseite rendert die Antwort, und eine normale Seite antwortet mit 200. Für einen echten 503 holst du die gerenderte Seite per fetch und gibst sie mit deinem eigenen Status zurück:

    ts
    // proxy.ts
    import type { NextRequest } from "next/server"
    export async function proxy(request: NextRequest) {
    if (process.env.MAINTENANCE !== "on") return
    const page = await fetch(new URL("/maintenance", request.url))
    return new Response(page.body, {
    status: 503,
    headers: { "Content-Type": "text/html; charset=utf-8", "Retry-After": "3600" },
    })
    }
    export const config = {
    // die Wartungsseite selbst, ihre Assets und robots.txt bleiben erreichbar
    matcher: ["/((?!maintenance|_next/static|_next/image|favicon.ico|robots.txt).*)"],
    }

    Halt /maintenance aus dem Matcher heraus, sonst ruft der fetch wieder den Proxy auf. Retry-After nimmt Sekunden oder ein HTTP-Datum; setz es auf das Ende des Wartungsfensters. Clientseitige Navigationen bekommen dasselbe HTML mit einem 503, also weicht der Router auf ein vollständiges Neuladen der Seite aus, und genau das willst du während der Wartung.

    Wie bekommt meine PWA eine Offline-Seite?

    Leg eine /offline-Route in einem Service Worker in den Cache und liefere sie aus, wenn das Laden einer Seite fehlschlägt. Das deckt vollständige Seitenaufrufe ab; Anfragen in einer App, die schon offen ist, brauchen eine andere Lösung.

    Innerhalb der App scheitert eine Soft Navigation, ein Prefetch oder eine Server Action, weil das Netz weg ist. Next.js 16.3 hat dafür eine experimentelle Antwort: Mit experimental.useOffline werden diese Anfragen wiederholt, sobald die Verbindung zurück ist, und der Hook useOffline() aus next/offline liefert true, damit eine Komponente ein Banner zeigen kann. Ohne das Flag liefert der Hook immer false. Eine Fehlerseite braucht es dafür nicht.

    Ein vollständiger Seitenaufruf ohne Netz. Der Browser hat kein HTML, das er zeigen könnte, also hilft nur ein Service Worker. Leg bei seiner Installation eine Offline-Route in den Cache und liefere sie aus, wenn eine Navigation scheitert:

    js
    // public/sw.js
    const CACHE = "offline-v1"
    self.addEventListener("install", (event) => {
    event.waitUntil(caches.open(CACHE).then((cache) => cache.add("/offline")))
    self.skipWaiting()
    })
    self.addEventListener("activate", (event) => event.waitUntil(self.clients.claim()))
    self.addEventListener("fetch", (event) => {
    if (event.request.mode !== "navigate") return
    event.respondWith(fetch(event.request).catch(() => caches.match("/offline")))
    })

    Registrier ihn einmal aus einer Client-Komponente im Root-Layout:

    tsx
    // app/register-sw.tsx
    "use client"
    import { useEffect } from "react"
    export function RegisterServiceWorker() {
    useEffect(() => {
    if ("serviceWorker" in navigator) navigator.serviceWorker.register("/sw.js")
    }, [])
    return null
    }

    Die Offline-Route prüft die Verbindung nach ihrem eigenen Zeitplan. Die HEAD-Anfrage ist keine Navigation, also lässt der Service Worker sie zum Netz durch:

    tsx
    // app/offline/offline-view.tsx
    "use client"
    import { AppErrorPage } from "@/components/app-error-page"
    async function ping() {
    const res = await fetch(window.location.href, { method: "HEAD", cache: "no-store" })
    if (!res.ok) throw new Error("Immer noch offline")
    }
    export function OfflineView() {
    return <AppErrorPage variant="offline" retryInterval={10} onRetry={ping} offlinePages={[]} />
    }

    Render <OfflineView /> aus app/offline/page.tsx. Das ist die PWA Offline Seite, die Leute nach einem Neuladen ohne Empfang sehen, weiterhin unter der URL, die sie aufgerufen haben. Sie prüft alle 10 Sekunden erneut und zeigt dabei einen Fortschrittsbalken. Löst der Browser online aus, prüft sie sofort, und sobald eine Prüfung klappt, lädt sie die ursprüngliche URL neu. offlinePages={[]} blendet die Liste „saved on this device“ aus, bis du wirklich Seiten cachst.

    Einen Haken hat der minimale Worker oben: Er cacht nur das HTML von /offline. Die CSS- und JavaScript-Chunks unter /_next/static liegen nicht im Cache, also erscheint die Seite ohne Netz ungestylt, und die Retry-Schleife startet nie. Leg diese Dateien ebenfalls vorab in den Cache. Serwist (opens in a new tab), die Option, auf die der PWA-Guide von Next.js verweist, baut diese Precache-Liste aus deinem Build-Output. Wenn du die App zu einer PWA machst, kümmert sich unser Beitrag zum React PWA Install Prompt um die Installation.

    Wie zeige ich eine Seite für fehlenden Zugriff an?

    Liefer einen 403, der sagt, wer Zugriff gewähren kann. Für eine angemeldete Person ohne die passende Rolle verschleiert ein 404, dass es die Seite gibt, und eine Weiterleitung zur Anmeldung endet in einer Schleife. Schalte experimental.authInterrupts in next.config.ts ein, ruf forbidden() aus next/navigation dort auf, wo du die Rolle prüfst (Next.js ergänzt bei dieser Antwort ein noindex-Tag), und leg app/forbidden.tsx an. Der Status funktioniert wie bei notFound(): Einen echten 403 bekommst du nur, wenn die Prüfung läuft, bevor das Streaming der Antwort beginnt.

    tsx
    // app/forbidden.tsx
    import { AppErrorPage } from "@/components/app-error-page"
    import { getSession, getWorkspaceAdmins } from "@/lib/auth"
    import { requestAccess, switchAccount } from "./access-actions"
    export default async function Forbidden() {
    const session = await getSession()
    const admins = await getWorkspaceAdmins()
    return (
    <AppErrorPage
    variant="forbidden"
    resource="Finanzberichte"
    admins={admins}
    account={session ? { name: session.user.name, email: session.user.email } : null}
    onRequestAccess={requestAccess}
    onSwitchAccount={switchAccount}
    />
    )
    }

    getSession, getWorkspaceAdmins und die beiden Server Actions schreibst du selbst. requestAccess bekommt { adminId, reason }. Ein abgelehntes Promise zeigt seine Meldung im Dialog, der sich auf Smartphones als Bottom Sheet öffnet. Ein Fallstrick in Produktion: Next.js ersetzt die Meldung eines Fehlers, der in einer Server Action geworfen wird, durch eine generische. „Du hast schon eine offene Anfrage“ würde den Dialog also nicht erreichen. Lass die Action stattdessen { error } zurückgeben und übergib onRequestAccess aus einer kleinen Client-Komponente, die sie aufruft und new Error(result.error) wirft. Nach einer erfolgreichen Anfrage wird der Button zu einem deaktivierten „Request sent“ mit der Uhrzeit.

    Drück Request access und dann Send request, ohne etwas auszufüllen, um beide Fehler zu sehen. Wähl einen Admin, schreib einen Grund und schick die Anfrage erneut
    $ npx wingo-ui@latest add error-pages
    ProDoku: Error Pages

    Wie sieht das fertige Setup aus?

    Sechs Routendateien, ein Proxy, ein Service Worker und ein Wrapper um einen Block:

    text
    app/
    not-found.tsx 404 für unbekannte URLs und notFound()
    error.tsx 500 pro Segment, retry()
    global-error.tsx 500, wenn das Root-Layout scheitert
    forbidden.tsx 403 aus forbidden()
    maintenance/page.tsx von proxy.ts mit einem 503 ausgeliefert
    offline/page.tsx von public/sw.js gecacht
    register-sw.tsx registriert den Service Worker
    components/
    app-error-page.tsx dein Logo, deine Support-Adresse und Link
    proxy.ts 503, solange MAINTENANCE=on
    public/sw.js Offline-Fallback für Seitenaufrufe

    Die passende Shell für die Inline-Varianten baut unser Tutorial zum Next.js Admin Dashboard, und weitere komplette Screens findest du in der Kategorie Praxis: Screens und Apps.

    Fang mit dem kostenlosen Empty State für Sackgassen innerhalb einer Seite an, und nimm den Block Error Pages dazu, wenn du alle fünf vollständigen Screens willst: npx wingo-ui@latest add error-pages.

    Komponenten in diesem Artikel

    • Error Pages

      React error pages in one block: 404 not found, 500 server error, maintenance, offline and no permission, full page or inside an app shell.

      Pro
    • Empty State

      A React empty state for lists, tables, searches and pages with nothing to show yet: an icon tile, a title, a description and actions.

      Free

    Häufige Fragen

    Wie erstelle ich eine 404-Seite im Next.js App Router?

    Leg app/not-found.tsx an. Die Datei rendert für jede URL ohne passende Route und immer dann, wenn eine Server Component notFound() aus next/navigation aufruft, und Next.js ergänzt automatisch ein noindex-Meta-Tag.

    Liefert die Next.js not found page einen 404-Statuscode?

    Sie liefert 404, wenn die Antwort nicht gestreamt wird. Hat eine loading.tsx-Boundary das Streaming schon gestartet, bevor notFound() lief, bleibt der Status 200, aber Next.js fügt ein noindex-Meta-Tag ein, damit die URL trotzdem nicht im Index landet.

    Wie baue ich eine 404-Seite mit React Router?

    Leg eine Catch-all-Route mit path="*" an, die deine Not-found-Komponente rendert. In einer Single Page App antwortet der Server trotzdem für jeden Pfad mit 200, also stell den Host so ein, dass er für Pfade außerhalb deiner Routenliste 404 liefert, wenn dir Suchtraffic wichtig ist.

    Welchen Statuscode sollte eine Wartungsseite liefern?

    503 Service Unavailable, mit einem Retry-After-Header, der sagt, wann es weitergeht. Google dokumentiert, dass 5xx-Antworten seine Crawler bremsen, ihr Inhalt verworfen wird und indexierte URLs zunächst erhalten bleiben; eine Wartungsseite mit 200 bekommt keinen dieser Schutzmechanismen.

    Wie zeige ich in einer PWA eine Offline-Seite an?

    Leg beim Installieren des Service Workers eine /offline-Route in den Cache und liefere sie aus, wenn eine Navigation fehlschlägt. Für eine App, die schon offen ist, wiederholt die experimentelle Option useOffline in Next.js 16.3 fehlgeschlagene Navigationen, Prefetches und Server Actions, sobald die Verbindung wieder da ist, und der Hook useOffline aus next/offline meldet den Zustand.

    • Fehlerseiten
    • Next.js
    • App Router
    • PWA
    • React

    Teilen

    SR

    Über den Autor

    Serban Rusu

    Gründer von Wingo UI

    Serban Rusu hat Wingo UI gegründet. Er baut die Komponenten, die CLI und den MCP-Server und schreibt über React-UIs für Smartphones und KI-Agents.

    Mehr von Serban
    Weiterlesen

    Ähnliche Artikel

    Alle Artikel
    Komponenten-Guides

    React Empty State: Erste Nutzung, keine Treffer, Fehler

    Bau eine React Empty State Komponente für erste Nutzung, keine Treffer und Fehler, mit Texten, die sagen, was passiert ist, und einer Aktion, die weiterhilft.

    SRSerban Rusu·19. Okt. 2026·9 Min. Lesezeit
    Komponenten-Guides

    React Skeleton Loader: echte Formen, kein Layout Shift

    Bau einen React Skeleton Loader in der Form des echten Inhalts, nimm einen Spinner, wo ein Skeleton nicht passt, und tausch die Daten ohne Layout Shift ein.

    SRSerban Rusu·19. Okt. 2026·9 Min. Lesezeit
    Praxis: Screens und Apps

    Next.js Blog Template: Markdown, Live-Demos und JSON-LD

    So haben wir ein Next.js Blog Template auf Markdown gebaut: zod-Frontmatter, Live-Demos, Sticky-Inhaltsverzeichnis, JSON-LD, Feeds und ein strenger Validator.

    SRSerban Rusu·16. Okt. 2026·10 Min. Lesezeit
    Newsletter

    Neue Artikel per E-Mail

    Neue Guides, Tutorials und Vergleiche aus dem Wingo UI Blog, sobald sie erscheinen. Die meisten Artikel sind auf Englisch.

    Kein Spam. Du kannst dich jederzeit abmelden.

    WingoUI

    Animierte, konfigurierbare, mobile-first React-Komponenten und Blöcke. Kopier den Quellcode, pass ihn an und lass deinen Coding-Agenten damit bauen.

    Produkt

    • Komponenten
    • Vorlagen
    • Preise
    • KI-Agenten
    • Theme-Generator

    Ressourcen

    • Doku
    • Blog
    • Changelog
    • Changelog-RSS
    • llms.txt

    Rechtliches

    • AGB
    • Datenschutz
    • Rückerstattung
    • Lizenz
    • Impressum

    Komponenten-Kategorien

    • Buttons & Actions
    • Inputs
    • Forms
    • Navigation
    • Overlays
    • Feedback
    • Data Display
    • Tables & Lists
    • Charts & Stats
    • Layout
    • Media
    • AI Kit
    • Text & Effects
    • Mobile
    • Commerce
    • Marketing Sections
    • Blocks
    • Hooks & Utilities

    © 2026 Wingo UI

    Wingo UI