Typesense Next.js: Search-UI mit InstantSearch bauen

Eine produktive Suchoberfläche im Next.js App Router braucht drei Bausteine: einen Search-Server, eine UI-Bibliothek und ein sauberes SSR-Pattern. Typesense-Next.js-Setups nutzen dafür den offiziellen typesense-instantsearch-adapter, der die Brücke zu Algolias InstantSearch.js schlägt.

Dieser Leitfaden zeigt die Architektur, die benötigten Pakete, die Adapter-Konfiguration und die typischen Stolperfallen rund um Hydration, SSR und scoped API Keys. Wenn Sie noch keinen Server betreiben, lesen Sie zuerst unseren Leitfaden zum Thema „Typesense installieren“.

Key Takeaways

  • Der typesense-instantsearch-adapter verbindet Typesense mit react-instantsearch
  • Im App Router laufen Server Components und Client Components parallel
  • SSR funktioniert über getServerState
  • Scoped API Keys gehören ins Frontend, niemals der Admin Key
  • Das offizielle Showcase-Repository deckt App Router + SSR vollständig ab
  • Für Headless Commerce ist das Pattern heute ein De-facto-Standard

 

Wie verbindet man Next.js mit Typesense?

Sie verbinden Next.js mit Typesense, indem Sie den typesense-instantsearch-adapter als Search Client konfigurieren und anschließend mit react-instantsearch koppeln.

Die Architektur sieht typischerweise so aus:

Browser
|
v
Next.js App Router
|
v
Typesense Cluster


Im App Router rendert Next.js das Layout serverseitig. Die eigentliche Suchoberfläche läuft als Client Component.

 

Direct-Browser-Pattern

Der Browser spricht Typesense direkt an.

Vorteile:

  • geringere Latenz
  • weniger Serverlast
  • einfachere Architektur

Nachteile:

  • Key-Management wichtig
  • eingeschränkte zentrale Kontrolle

Wichtig: Nur Search-Only-Keys oder Scoped Keys verwenden.

 

Proxy-Pattern via Route Handler

Hier routet ein Next.js Route Handler die Suchanfragen an Typesense weiter.

Vorteile:

  • zentrale Rechteprüfung
  • Rate Limiting
  • Logging
  • einfachere Mandantenlogik

Nachteile:

  • zusätzlicher Netzwerk-Hop
  • etwas höhere Latenz

In B2B-Setups mit Login und Kundengruppen ist dieses Pattern meist robuster.

 

Welche Pakete benötigen Sie?

npm install \
typesense \
typesense-instantsearch-adapter \
react-instantsearch \
react-instantsearch-router-nextjs

Die Aufgaben der Pakete:

Paket Zweck
typesense offizieller API-Client
typesense-instantsearch-adapter Adapter zu InstantSearch
react-instantsearch Search-UI-Komponenten
react-instantsearch-router-nextjs URL-Synchronisation

 

Wie erstellen Sie eine Typesense Collection?

Vor der UI benötigen Sie ein Schema.

import Typesense from "typesense";

const client = new Typesense.Client({
nodes: [
{
host: "search.example.com",
port: 443,
protocol: "https",
},
],
apiKey: process.env.TYPESENSE_ADMIN_KEY!,
});

await client.collections().create({
name: "products",
fields: [
{ name: "title", type: "string" },
{ name: "description", type: "string" },
{ name: "brand", type: "string", facet: true },
{ name: "categories", type: "string[]", facet: true },
{ name: "price", type: "float", facet: true },
{ name: "in_stock", type: "bool", facet: true },
],
default_sorting_field: "price",
});

Felder mit facet: true erscheinen später als Filter.

 

Schema für Produktdaten

Ein typisches Produktschema enthält:

  • Titel
  • Beschreibung
  • Marken
  • Kategorien
  • Preise
  • Lagerbestand

Im B2B kommen häufig hinzu:

  • Kundengruppen
  • Hersteller-IDs
  • Artikelnummern
  • technische Spezifikationen

 

Facettenfelder definieren

Alle filterbaren Felder erhalten facet: true.

Typische Facetten:

  • Marke
  • Kategorie
  • Material
  • Preis
  • Verfügbarkeit

 

Dokumente importieren

Nach dem Schema importieren Sie Dokumente per documents().import().

 

Wie konfigurieren Sie den InstantSearch-Adapter?

Die Adapter-Konfiguration ist das Herzstück der Integration.

"use client";

import TypesenseInstantsearchAdapter from "typesense-instantsearch-adapter";

export const searchClient =
new TypesenseInstantsearchAdapter({
server: {
apiKey:
process.env
.NEXT_PUBLIC_TYPESENSE_SEARCH_KEY!,
nodes: [
{
host:
process.env
.NEXT_PUBLIC_TYPESENSE_HOST!,
port: 443,
protocol: "https",
},
],
cacheSearchResultsForSeconds: 60,
},

additionalSearchParameters: {
query_by:
"title,description,brand,categories",

query_by_weights: "4,2,2,1",

num_typos: 2,
},
}).searchClient;


Server-Verbindung

Die Nodes definieren Host, Port und Protokoll.

 

Search-Only-Key statt Admin-Key

Im Frontend darf ausschließlich ein Search-Only-Key oder Scoped Key verwendet werden.

 

query_by, query_by_weights und num_typos

query_by definiert die durchsuchbaren Felder.

query_by_weights priorisiert wichtige Felder.

num_typos steuert die Tippfehler-Toleranz.

 

Wie bauen Sie die Search-UI mit React InstantSearch?

react-instantsearch liefert fertige Widgets.

"use client";

import {
InstantSearch,
SearchBox,
Hits,
RefinementList,
Pagination,
} from "react-instantsearch";

import { searchClient } from "./search-client";

export function ProductSearch() {
return (
<InstantSearch
searchClient={searchClient}
indexName="products"
>
<SearchBox placeholder="Produkte suchen" />

<div className="grid grid-cols-4 gap-6">
<aside>
<RefinementList attribute="brand" />
<RefinementList attribute="categories" />
</aside>

<main className="col-span-3">
<Hits hitComponent={ProductHit} />
<Pagination />
</main>
</div>
</InstantSearch>
);
}

function ProductHit({
hit,
}: {
hit: {
title: string;
price: number;
};
}) {
return (
<article>
<h3>{hit.title}</h3>
<p>{hit.price.toFixed(2)} EUR</p>
</article>
);
}

SearchBox

Die SearchBox sendet Suchanfragen direkt an Typesense.

 

Hits

Hits rendert die Trefferliste.

 

RefinementList

Facettenfilter werden über RefinementList umgesetzt.

 

Pagination

Pagination ermöglicht große Trefferlisten performant darzustellen.

 

Wie funktioniert SSR im Next.js App Router?

SSR läuft über getServerState.

import { getServerState }
from "react-instantsearch";

import { renderToString }
from "react-dom/server";

import { ProductSearch }
from "./product-search";

export default async function Page() {
const serverState =
await getServerState(
<ProductSearch />,
{ renderToString }
);

return (
<ProductSearch
serverState={serverState}
/>
);
}

Dadurch sehen Suchmaschinen und Nutzer bereits gerenderte Treffer beim ersten Paint.

 

getServerState nutzen

getServerState rendert die Suchoberfläche serverseitig vor.

 

ServerState an die Client Component übergeben

Der State wird an InstantSearchSSRProvider weitergereicht.

 

Hydration-Fehler vermeiden

Server- und Client-State müssen identisch sein.

 

Warum sind Scoped API Keys wichtig?

Der Admin Key darf niemals im Browser landen.

Stattdessen erzeugen Sie pro Nutzer oder Session einen Scoped Key.

import Typesense from "typesense";

const admin = new Typesense.Client({
nodes: [
{
host: "search.example.com",
port: 443,
protocol: "https",
},
],
apiKey:
process.env.TYPESENSE_ADMIN_KEY!,
});

export async function createScopedKey(
tenantId: string
) {
return admin.keys()
.generateScopedSearchKey(
process.env
.TYPESENSE_SEARCH_ONLY_KEY!,
{
filter_by:
`tenant_id:=${tenantId}`,

expires_at:
Math.floor(Date.now() / 1000)
+ 3600,
}
);
}

Admin-Key bleibt serverseitig

Der Admin Key darf niemals öffentlich sichtbar sein.

 

Mandanten- und Kundengruppenfilter

Scoped Keys können Filter enthalten.

 

Ablaufzeit und Rechte begrenzen

Keys können zeitlich begrenzt werden.

 

Wie sieht ein typisches E-Commerce-Setup aus?

Eine typische Architektur:

ERP
|
v
PIM / Middleware
|
v
Typesense
|
v
Next.js Storefront

Die Suche übernimmt:

  • Autocomplete
  • Facetten
  • Filter
  • Preisranges
  • Sortierung
  • Suchvorschläge
  • semantische Suche

 

ERP → PIM → Typesense → Next.js

ERP liefert Stammdaten, PIM reichert an, Typesense indexiert.

 

B2B-Suche mit Kundengruppen und Artikelnummern

B2B-Shops benötigen häufig:

  • Artikelnummernsuche
  • kundenspezifische Sortimente
  • Preislisten
  • Rechteprüfung

 

Facetten, Preisranges und Sortierung

Typische Facetten:

  • Marke
  • Material
  • Norm
  • Hersteller
  • Preis

 

Welche Probleme treten häufig auf?

Hydration Mismatch

Server- und Client-State unterscheiden sich.

CORS-Fehler

Typesense muss den Frontend-Origin erlauben.

Collection oder Feld existiert nicht

Schema und Collection stimmen nicht überein.

Versionskonflikte zwischen Adapter und InstantSearch

Major-Versionen müssen kompatibel sein.

 

Performance-Tipps für produktive Suche

Debouncing

Autocomplete sollte 50–150 ms debounced werden.

Minimum Query Length

Autocomplete erst ab 2–3 Zeichen starten.

Edge-Caching

Top-Queries via CDN cachen.

Facetten bewusst begrenzen

Jede Facette erhöht RAM-Verbrauch.

FAQ

Brauche ich react-instantsearch für Typesense mit Next.js?

Nein, technisch reicht das Typesense SDK. Für produktive Suchoberflächen mit SearchBox, Facetten, Pagination, URL-Sync und SSR ist react-instantsearch mit dem typesense-instantsearch-adapter jedoch meist der schnellere und stabilere Weg.

Funktioniert Typesense mit dem Next.js App Router?

Ja. Im App Router wird die Suchoberfläche als Client Component umgesetzt. Für SSR kann getServerState aus react-instantsearch genutzt werden.

Darf der Typesense Admin-Key im Frontend verwendet werden?

Nein. Der Admin-Key darf niemals im Browser landen. Für Frontends sollten Search-Only-Keys oder Scoped API Keys verwendet werden.

Was ist ein Scoped API Key?

Ein Scoped API Key ist ein eingeschränkter Suchschlüssel. Er kann Filter, Ablaufzeiten und Berechtigungen enthalten, zum Beispiel für Mandanten oder Kundengruppen.

Wie verhindere ich Hydration-Fehler?

Server- und Client-Render müssen dieselbe Adapter-Konfiguration, denselben Index-Namen und dieselben initialen Suchparameter verwenden.

Kann ich mehrere Typesense Collections in einer UI durchsuchen?

Ja. Mit dem <Index>-Widget von react-instantsearch lassen sich mehrere Collections beziehungsweise Indizes parallel durchsuchen.

Ist Typesense für B2B-E-Commerce mit Next.js geeignet?

Ja. Besonders bei Headless-Commerce-Setups mit großen Katalogen, Artikelnummernsuche, Facetten, kundenspezifischen Sortimenten und schnellen Autocomplete-Anfragen ist Typesense gut geeignet.

Brauche ich für Typesense mit Next.js einen Proxy?

Nicht zwingend. Für öffentliche Shops kann der Browser direkt mit einem Search-Only-Key suchen. Für B2B-Portale mit Login, Mandantenlogik oder komplexen Rechten ist ein Proxy über Next.js Route Handler meist besser.