Framework
Version
Integrationen

Fehler "Nicht gefunden" (Not Found Errors)

⚠️ Diese Seite behandelt die neueren Funktionen notFound und die API notFoundComponent zur Behandlung von Fehlern "Nicht gefunden". Die Route NotFoundRoute ist veraltet und wird in einer zukünftigen Version entfernt. Siehe Migration von NotFoundRoute für weitere Informationen.

Übersicht

Es gibt 2 Anwendungsfälle für Fehler "Nicht gefunden" in TanStack Router

  • Nicht übereinstimmende Pfade von Routen: Wenn ein Pfad keinem bekannten Routenmuster entspricht ODER wenn er teilweise mit einer Route übereinstimmt, aber zusätzliche Pfadsegmente aufweist
    • Der Router löst automatisch einen Fehler "Nicht gefunden" aus, wenn ein Pfad keinem bekannten Routenmuster entspricht
    • Wenn der notFoundMode des Routers auf fuzzy gesetzt ist, behandelt die nächstgelegene übergeordnete Route mit einer notFoundComponent den Fehler. Wenn der notFoundMode des Routers auf root gesetzt ist, behandelt die Stammroute den Fehler.
    • Beispiele
      • Versuch, auf /users zuzugreifen, wenn keine /users-Route vorhanden ist
      • Versuch, auf /posts/1/edit zuzugreifen, wenn der Routenbaum nur /posts/$postId behandelt
  • Fehlende Ressourcen: Wenn eine Ressource nicht gefunden werden kann, z. B. ein Beitrag mit einer bestimmten ID oder beliebige asynchrone Daten, die nicht verfügbar oder nicht vorhanden sind
    • Sie, der Entwickler, müssen einen Fehler "Nicht gefunden" auslösen, wenn eine Ressource nicht gefunden werden kann. Dies kann in den Funktionen beforeLoad oder loader mithilfe des notFound-Dienstprogramms geschehen.
    • Wird von der nächstgelegenen übergeordneten Route mit einer notFoundComponent behandelt (wenn notFound innerhalb von loader aufgerufen wird) oder von der Stammroute.
    • Beispiele
      • Versuch, auf /posts/1 zuzugreifen, wenn der Beitrag mit ID 1 nicht existiert
      • Versuch, auf /docs/path/to/document zuzugreifen, wenn das Dokument nicht existiert

Im Grunde sind beide Fälle über dieselbe notFound-Funktion und dieselbe notFoundComponent-API implementiert.

Die Option notFoundMode

Wenn TanStack Router auf einen Pfadnamen stößt, der keinem bekannten Routenmuster entspricht ODER teilweise mit einem Routenmuster übereinstimmt, aber zusätzliche nachfolgende Pfadnamen-Segmente aufweist, löst er automatisch einen Fehler "Nicht gefunden" aus.

Abhängig von der Option notFoundMode behandelt der Router diese automatischen Fehler unterschiedlich:

  • "fuzzy"-Modus (Standard): Der Router findet intelligent die nächstgelegene passende Route und zeigt die notFoundComponent an.
  • "root"-Modus: Alle Fehler "Nicht gefunden" werden von der notFoundComponent der Stammroute behandelt, unabhängig von der nächstgelegenen passenden Route.

notFoundMode: 'fuzzy'

Standardmäßig ist der notFoundMode des Routers auf fuzzy gesetzt, was bedeutet, dass der Router versucht, die nächstgelegene passende Route mit Kindern/(einer Outlet) und einer konfigurierten "Nicht gefunden"-Komponente zu verwenden, wenn ein Pfadname keiner bekannten Route entspricht.

❓ Warum ist das der Standard? Fuzzy-Matching zur möglichst weitgehenden Beibehaltung des übergeordneten Layouts für den Benutzer gibt ihm mehr Kontext, um zu einem nützlichen Ort zu navigieren, basierend darauf, wo er anzukommen glaubte.

Die nächstgelegene geeignete Route wird anhand der folgenden Kriterien gefunden

  • Die Route muss Kinder und damit eine Outlet zur Anzeige der notFoundComponent haben
  • Die Route muss eine konfigurierte notFoundComponent haben oder der Router muss eine defaultNotFoundComponent konfiguriert haben

Betrachten Sie zum Beispiel den folgenden Routenbaum

  • __root__ (hat eine konfigurierte notFoundComponent)
    • posts (hat eine konfigurierte notFoundComponent)
      • $postId (hat eine konfigurierte notFoundComponent)

Wenn der Pfad /posts/1/edit angegeben wird, wird die folgende Komponentenstruktur gerendert

  • <Root>
    • <Posts>
      • <Posts.notFoundComponent>

Die notFoundComponent der Route posts wird gerendert, da sie die nächstgelegene geeignete übergeordnete Route mit Kindern (und damit einer Outlet) und einer konfigurierten notFoundComponent ist.

notFoundMode: 'root'

Wenn notFoundMode auf root gesetzt ist, werden alle Fehler "Nicht gefunden" von der notFoundComponent der Stammroute behandelt, anstatt von der nächstgelegenen fuzzy-gematchten Route nach oben zu blubbern.

Betrachten Sie zum Beispiel den folgenden Routenbaum

  • __root__ (hat eine konfigurierte notFoundComponent)
    • posts (hat eine konfigurierte notFoundComponent)
      • $postId (hat eine konfigurierte notFoundComponent)

Wenn der Pfad /posts/1/edit angegeben wird, wird die folgende Komponentenstruktur gerendert

  • <Root>
    • <Root.notFoundComponent>

Die notFoundComponent der Route __root__ wird gerendert, da der notFoundMode auf root gesetzt ist.

Konfigurieren einer notFoundComponent für eine Route

Um beide Arten von Fehlern "Nicht gefunden" zu behandeln, können Sie einer Route eine notFoundComponent zuweisen. Diese Komponente wird gerendert, wenn ein Fehler "Nicht gefunden" ausgelöst wird.

Zum Beispiel das Konfigurieren einer notFoundComponent für eine Route /settings, um nicht existierende Einstellungsseiten zu behandeln

tsx
export const Route = createFileRoute('/settings')({
  component: () => {
    return (
      <div>
        <p>Settings page</p>
        <Outlet />
      </div>
    )
  },
  notFoundComponent: () => {
    return <p>This setting page doesn't exist!</p>
  },
})
export const Route = createFileRoute('/settings')({
  component: () => {
    return (
      <div>
        <p>Settings page</p>
        <Outlet />
      </div>
    )
  },
  notFoundComponent: () => {
    return <p>This setting page doesn't exist!</p>
  },
})

Oder das Konfigurieren einer notFoundComponent für eine Route /posts/$postId, um nicht existierende Beiträge zu behandeln

tsx
export const Route = createFileRoute('/posts/$postId')({
  loader: async ({ params: { postId } }) => {
    const post = await getPost(postId)
    if (!post) throw notFound()
    return { post }
  },
  component: ({ post }) => {
    return (
      <div>
        <h1>{post.title}</h1>
        <p>{post.body}</p>
      </div>
    )
  },
  notFoundComponent: () => {
    return <p>Post not found!</p>
  },
})
export const Route = createFileRoute('/posts/$postId')({
  loader: async ({ params: { postId } }) => {
    const post = await getPost(postId)
    if (!post) throw notFound()
    return { post }
  },
  component: ({ post }) => {
    return (
      <div>
        <h1>{post.title}</h1>
        <p>{post.body}</p>
      </div>
    )
  },
  notFoundComponent: () => {
    return <p>Post not found!</p>
  },
})

Standardmäßige Routerweite Fehlerbehandlung "Nicht gefunden"

Sie möchten möglicherweise eine Standard-Komponente für "Nicht gefunden" für jede Route in Ihrer App mit untergeordneten Routen bereitstellen.

Warum nur Routen mit Kindern? Leaf-Routen (Routen ohne Kinder) rendern niemals eine Outlet und können daher keine Fehler "Nicht gefunden" behandeln.

Um dies zu tun, übergeben Sie eine defaultNotFoundComponent an die Funktion createRouter

tsx
const router = createRouter({
  defaultNotFoundComponent: () => {
    return (
      <div>
        <p>Not found!</p>
        <Link to="/">Go home</Link>
      </div>
    )
  },
})
const router = createRouter({
  defaultNotFoundComponent: () => {
    return (
      <div>
        <p>Not found!</p>
        <Link to="/">Go home</Link>
      </div>
    )
  },
})

Eigene notFound Fehler auslösen

Sie können Fehler "Nicht gefunden" manuell in Loader-Methoden und Komponenten mit der Funktion notFound auslösen. Dies ist nützlich, wenn Sie signalisieren müssen, dass eine Ressource nicht gefunden werden kann.

Die Funktion notFound funktioniert ähnlich wie die Funktion redirect. Um einen Fehler "Nicht gefunden" zu verursachen, können Sie notFound() auslösen.

tsx
export const Route = createFileRoute('/posts/$postId')({
  loader: async ({ params: { postId } }) => {
    // Returns `null` if the post doesn't exist
    const post = await getPost(postId)
    if (!post) {
      throw notFound()
      // Alternatively, you can make the notFound function throw:
      // notFound({ throw: true })
    }
    // Post is guaranteed to be defined here because we threw an error
    return { post }
  },
})
export const Route = createFileRoute('/posts/$postId')({
  loader: async ({ params: { postId } }) => {
    // Returns `null` if the post doesn't exist
    const post = await getPost(postId)
    if (!post) {
      throw notFound()
      // Alternatively, you can make the notFound function throw:
      // notFound({ throw: true })
    }
    // Post is guaranteed to be defined here because we threw an error
    return { post }
  },
})

Der Fehler "Nicht gefunden" wird von derselben oder der nächstgelegenen übergeordneten Route behandelt, die entweder eine Routenoption notFoundComponent oder die Router-Option defaultNotFoundComponent konfiguriert hat.

Wenn weder die Route noch eine geeignete übergeordnete Route gefunden wird, um den Fehler zu behandeln, wird die Stammroute ihn mit der extrem einfachen (und bewusst unerwünschten) Standard-Komponente für "Nicht gefunden" von TanStack Router behandeln, die einfach <div>Not Found</div> rendert. Es wird dringend empfohlen, entweder mindestens eine notFoundComponent an die Stammroute anzuhängen oder eine Router-weite defaultNotFoundComponent zu konfigurieren, um Fehler "Nicht gefunden" zu behandeln.

Festlegen, welche Routen Fehler "Nicht gefunden" behandeln

Manchmal möchten Sie möglicherweise auf einer bestimmten übergeordneten Route einen Fehler "Nicht gefunden" auslösen und die normale Weiterleitung der Komponente für "Nicht gefunden" umgehen. Um dies zu tun, übergeben Sie eine Routen-ID an die Option route in der Funktion notFound.

tsx
// _pathlessLayout.tsx
export const Route = createFileRoute('/_pathlessLayout')({
  // This will render
  notFoundComponent: () => {
    return <p>Not found (in _pathlessLayout)</p>
  },
  component: () => {
    return (
      <div>
        <p>This is a pathless layout route!</p>
        <Outlet />
      </div>
    )
  },
})

// _pathlessLayout/route-a.tsx
export const Route = createFileRoute('/_pathless/route-a')({
  loader: async () => {
    // This will make LayoutRoute handle the not-found error
    throw notFound({ routeId: '/_pathlessLayout' })
    //                      ^^^^^^^^^ This will autocomplete from the registered router
  },
  // This WILL NOT render
  notFoundComponent: () => {
    return <p>Not found (in _pathlessLayout/route-a)</p>
  },
})
// _pathlessLayout.tsx
export const Route = createFileRoute('/_pathlessLayout')({
  // This will render
  notFoundComponent: () => {
    return <p>Not found (in _pathlessLayout)</p>
  },
  component: () => {
    return (
      <div>
        <p>This is a pathless layout route!</p>
        <Outlet />
      </div>
    )
  },
})

// _pathlessLayout/route-a.tsx
export const Route = createFileRoute('/_pathless/route-a')({
  loader: async () => {
    // This will make LayoutRoute handle the not-found error
    throw notFound({ routeId: '/_pathlessLayout' })
    //                      ^^^^^^^^^ This will autocomplete from the registered router
  },
  // This WILL NOT render
  notFoundComponent: () => {
    return <p>Not found (in _pathlessLayout/route-a)</p>
  },
})

Manuelles Anzielen der Stammroute

Sie können auch die Stammroute ansprechen, indem Sie die exportierte Variable rootRouteId an die Eigenschaft route der Funktion notFound übergeben.

tsx
import { rootRouteId } from '@tanstack/react-router'

export const Route = createFileRoute('/posts/$postId')({
  loader: async ({ params: { postId } }) => {
    const post = await getPost(postId)
    if (!post) throw notFound({ routeId: rootRouteId })
    return { post }
  },
})
import { rootRouteId } from '@tanstack/react-router'

export const Route = createFileRoute('/posts/$postId')({
  loader: async ({ params: { postId } }) => {
    const post = await getPost(postId)
    if (!post) throw notFound({ routeId: rootRouteId })
    return { post }
  },
})

Auslösen von Fehlern "Nicht gefunden" in Komponenten

Sie können Fehler "Nicht gefunden" auch in Komponenten auslösen. Es wird jedoch empfohlen, Fehler "Nicht gefunden" in Loader-Methoden anstelle von Komponenten auszulösen, um die Loader-Daten korrekt zu typisieren und Flackern zu verhindern.

TanStack Router stellt eine CatchNotFound-Komponente ähnlich wie CatchBoundary bereit, die verwendet werden kann, um Fehler "Nicht gefunden" in Komponenten abzufangen und die Benutzeroberfläche entsprechend anzuzeigen.

Datenladen innerhalb von notFoundComponent

notFoundComponent ist ein Sonderfall beim Datenladen. SomeRoute.useLoaderData ist möglicherweise nicht definiert, abhängig davon, auf welche Route Sie zugreifen und wo der Fehler "Nicht gefunden" ausgelöst wird. Jedoch geben Route.useParams, Route.useSearch, Route.useRouteContext usw. einen definierten Wert zurück.

Wenn Sie unvollständige Loader-Daten an notFoundComponent übergeben müssen, übergeben Sie die Daten über die Option data in der Funktion notFound und validieren Sie sie in notFoundComponent.

tsx
export const Route = createFileRoute('/posts/$postId')({
  loader: async ({ params: { postId } }) => {
    const post = await getPost(postId)
    if (!post)
      throw notFound({
        // Forward some data to the notFoundComponent
        // data: someIncompleteLoaderData
      })
    return { post }
  },
  // `data: unknown` is passed to the component via the `data` option when calling `notFound`
  notFoundComponent: ({ data }) => {
    // ❌ useLoaderData is not valid here: const { post } = Route.useLoaderData()

    // ✅:
    const { postId } = Route.useParams()
    const search = Route.useSearch()
    const context = Route.useRouteContext()

    return <p>Post with id {postId} not found!</p>
  },
})
export const Route = createFileRoute('/posts/$postId')({
  loader: async ({ params: { postId } }) => {
    const post = await getPost(postId)
    if (!post)
      throw notFound({
        // Forward some data to the notFoundComponent
        // data: someIncompleteLoaderData
      })
    return { post }
  },
  // `data: unknown` is passed to the component via the `data` option when calling `notFound`
  notFoundComponent: ({ data }) => {
    // ❌ useLoaderData is not valid here: const { post } = Route.useLoaderData()

    // ✅:
    const { postId } = Route.useParams()
    const search = Route.useSearch()
    const context = Route.useRouteContext()

    return <p>Post with id {postId} not found!</p>
  },
})

Verwendung mit SSR

Siehe SSR-Anleitung für weitere Informationen.

Migration von NotFoundRoute

Die API NotFoundRoute ist zugunsten von notFoundComponent veraltet. Die API NotFoundRoute wird in einer zukünftigen Version entfernt.

Die Funktion notFound und notFoundComponent funktionieren nicht, wenn NotFoundRoute verwendet wird.

Die Hauptunterschiede sind

  • NotFoundRoute ist eine Route, die eine <Outlet> auf ihrer übergeordneten Route zur Darstellung benötigt. notFoundComponent ist eine Komponente, die an jede Route angehängt werden kann.
  • Bei Verwendung von NotFoundRoute können Sie keine Layouts verwenden. notFoundComponent kann mit Layouts verwendet werden.
  • Bei Verwendung von notFoundComponent ist das Pfadmatching strikt. Das bedeutet, wenn Sie eine Route unter /post/$postId haben, wird ein Fehler "Nicht gefunden" ausgelöst, wenn Sie versuchen, auf /post/1/2/3 zuzugreifen. Mit NotFoundRoute würde /post/1/2/3 mit der NotFoundRoute übereinstimmen und sie nur rendern, wenn es eine <Outlet> gibt.

Um von NotFoundRoute zu notFoundComponent zu migrieren, müssen Sie nur ein paar Änderungen vornehmen

tsx
// router.tsx
import { createRouter } from '@tanstack/react-router'
import { routeTree } from './routeTree.gen.'
- import { notFoundRoute } from './notFoundRoute'  // [!code --]

export const router = createRouter({
  routeTree,
- notFoundRoute // [!code --]
})

// routes/__root.tsx
import { createRootRoute } from '@tanstack/react-router'

export const Route = createRootRoute({
  // ...
+ notFoundComponent: () => {  // [!code ++]
+   return <p>Not found!</p>  // [!code ++]
+ } // [!code ++]
})
// router.tsx
import { createRouter } from '@tanstack/react-router'
import { routeTree } from './routeTree.gen.'
- import { notFoundRoute } from './notFoundRoute'  // [!code --]

export const router = createRouter({
  routeTree,
- notFoundRoute // [!code --]
})

// routes/__root.tsx
import { createRootRoute } from '@tanstack/react-router'

export const Route = createRootRoute({
  // ...
+ notFoundComponent: () => {  // [!code ++]
+   return <p>Not found!</p>  // [!code ++]
+ } // [!code ++]
})

Wichtige Änderungen

  • Eine notFoundComponent wird zur Stammroute für die globale Fehlerbehandlung "Nicht gefunden" hinzugefügt.
    • Sie können auch eine notFoundComponent zu jeder anderen Route in Ihrem Routenbaum hinzufügen, um Fehler "Nicht gefunden" für diese spezifische Route zu behandeln.
  • Die notFoundComponent unterstützt nicht das Rendern einer <Outlet>.
Unsere Partner
Code Rabbit
Netlify
Neon
Clerk
Convex
Sentry
Bytes abonnieren

Ihre wöchentliche Dosis JavaScript-Nachrichten. Jeden Montag kostenlos an über 100.000 Entwickler geliefert.

Bytes

Kein Spam. Jederzeit kündbar.

Bytes abonnieren

Ihre wöchentliche Dosis JavaScript-Nachrichten. Jeden Montag kostenlos an über 100.000 Entwickler geliefert.

Bytes

Kein Spam. Jederzeit kündbar.