Skip to main content
@mixpeek/search-js is a drop-in React component that connects to any published Mixpeek retriever. It provides a full search UI with keyboard shortcuts, filters, AI answers, and streaming results — no backend code required on your side.
npm install @mixpeek/search-js

Quick Start

1

Set up your search backend

Use the docs search quickstart to provision a complete pipeline in one API call, or create a retriever manually and publish it.
2

Install the widget

npm install @mixpeek/search-js
3

Add to your app

import { MixpeekSearch } from "@mixpeek/search-js";
import "@mixpeek/search-js/styles.css";

export default function App() {
  return (
    <MixpeekSearch
      projectKey="your-retriever-slug"
      placeholder="Search..."
      theme="auto"
      accentColor="#6366f1"
    />
  );
}
Users press Cmd+K (or Ctrl+K) to open the search modal. Results stream in from your retriever pipeline.

Props

PropTypeDefaultDescription
projectKeystringrequiredPublished retriever slug or ret_sk_* API key
placeholderstring"Search..."Input placeholder text
maxResultsnumber10Maximum results to show
theme"light" | "dark" | "auto""auto"Color theme
accentColorstring"#6366f1"Accent color (hex)
position"modal" | "inline""modal"Modal overlay or inline embed
keyboardShortcutbooleantrueEnable Cmd+K / Ctrl+K
showPoweredBybooleantrueShow “Search by Mixpeek” badge
enableAIAnswerbooleanfalseShow AI-generated answer with citations
enableShareLinksbooleanfalseEnable shareable search URLs
defaultOpenbooleanfalseStart with modal open
defaultFiltersRecord<string, unknown>-Default filter values on mount

Callbacks

PropTypeDescription
onSearch(query: string) => voidFires when a search is performed
onResultClick(result, index) => voidFires when a result is clicked
onZeroResults(query: string) => voidFires when no results are found
onFilterChange(filterInputs) => voidFires when filters change
transformResults(results[]) => results[]Transform results before rendering
renderResult(result, index) => ReactNodeCustom result renderer

CDN Usage (No Build Step)

For sites without a build system, load the widget via CDN:
<link rel="stylesheet" href="https://cdn.mixpeek.com/search/v1/mixpeek-search.css" />
<script
  src="https://cdn.mixpeek.com/search/v1/loader.js"
  data-project-key="your-retriever-slug"
  data-mount="search-container">
</script>

<div id="search-container"></div>

Filters

The widget includes built-in filter components for facets, ranges, and LLM-powered smart filtering.

Facet Filter

Single or multi-select dropdown:
<MixpeekSearch projectKey="my-search">
  <FacetFilter
    field="category"
    label="Category"
    options={[
      { label: "Electronics", value: "electronics" },
      { label: "Clothing", value: "clothing" },
    ]}
    multiple={true}
  />
</MixpeekSearch>

Range Filter

Numeric min/max slider:
<RangeFilter
  field="price"
  label="Price"
  min={0}
  max={1000}
  step={10}
  unit="$"
/>

Smart Filter (LLM-based)

Natural language filtering powered by the retriever’s LLM filter stage:
<SmartFilter
  label="Describe what you want"
  placeholder="e.g. red shoes under $50"
/>

AI Answers

Enable enableAIAnswer to show an LLM-generated answer with citations above search results. This requires an agent_search or rag_prepare stage in your retriever.
<MixpeekSearch
  projectKey="docs-search"
  enableAIAnswer={true}
/>

Hooks

Access search state from any child component:
import { useSearchKit } from "@mixpeek/search-js";

function MyComponent() {
  const {
    query,
    results,
    isLoading,
    aiAnswer,
    isOpen,
    open,
    close,
    search,
    filterInputs,
    setFilter,
    clearFilters,
    hasActiveFilters,
  } = useSearchKit();

  return <div>{results.length} results for "{query}"</div>;
}
Available hooks: useSearchKit, useSearch, useFilters, useKeyboardShortcut, useRecentSearches.

Setting Up the Backend

The widget needs a published retriever to connect to. There are two paths: Provision a complete search pipeline in one API call. This creates a namespace, bucket, collection (with web scraper + text embeddings), retriever, and published endpoint automatically:
curl -X POST https://api.mixpeek.com/v1/quickstart/docs-search \
  -H "Authorization: Bearer YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "site_url": "https://docs.example.com",
    "site_name": "Example Docs"
  }'
The response includes a retriever slug and embed snippet ready to paste:
{
  "retriever_slug": "example-docs-search",
  "api_key": "ret_sk_...",
  "embed_snippet": "<MixpeekSearch projectKey=\"example-docs-search\" />"
}
Options: enable_code_search (default: true), enable_image_search (default: false), max_pages (default: 200), max_depth (default: 3).

Bootstrap CLI

The @mixpeek/react-searchkit package includes a CLI to scaffold a retriever with search, filter, and RAG stages:
npx mixpeek-bootstrap --api-key YOUR_API_KEY --slug my-site-search
This creates a retriever with feature_search, attribute_filter, and rag_prepare stages pre-configured.

Manual Setup

For full control, create each resource yourself:
1

Create a namespace and bucket

Set up storage and enable the feature extractors you need (guide).
2

Create a collection

Configure a collection with a feature extractor (e.g., text_extractor, web_scraper, multimodal_extractor) and trigger processing on your data (guide).
3

Create and publish a retriever

Build a retriever with the stages you need, then publish it to get a slug for the widget (guide).

Publishing a Retriever

Once you have a retriever, publish it to make it accessible to the widget:
from mixpeek import Mixpeek

client = Mixpeek(api_key="your-api-key")

result = client.retrievers.publish(
    retriever_id="ret_abc123",
    public_name="my-search",
)

print(result.public_url)  # https://mxp.co/r/my-search
The public_name becomes the projectKey you pass to the widget.

Authentication

The widget supports two authentication modes:
ModeprojectKey valueWhen to use
Public slug"my-retriever-slug"Public-facing search (no auth needed)
Scoped API key"ret_sk_..."Authenticated access with a retrieverSlug prop
// Public slug (most common)
<MixpeekSearch projectKey="my-retriever-slug" />

// Scoped API key
<MixpeekSearch projectKey="ret_sk_..." retrieverSlug="my-retriever-slug" />

Examples

The search widget is used on mixpeek.com as the site-wide search in the navigation bar, powered by @mixpeek/search-js with the mixpeek-blog-search retriever slug.
<MixpeekSearch
  projectKey="mixpeek-blog-search"
  placeholder="Search..."
  theme={isScrolled ? "light" : "dark"}
  accentColor="#6366f1"
  maxResults={10}
  showPoweredBy={true}
  keyboardShortcut={true}
  transformResults={(results) =>
    results.map((r) => ({
      id: r.document_id || r.id,
      title: r.title || r.page_title || "Mixpeek",
      content: r.content || r.text || "",
      page_url: r.page_url || r.url || null,
      image_url: r.image_url || null,
      score: r.score,
    }))
  }
/>

Exported Components

For building fully custom search experiences, the package exports composable sub-components:
ComponentDescription
SearchButtonStandalone search trigger button
SearchModalSearch modal container
SearchInputInput field
SearchResultsResults list
ResultCardIndividual result card
AIAnswerAI-generated answer panel
FilterPanelFilter container
FacetFilterSelect/multi-select filter
RangeFilterMin/max range slider
SmartFilterLLM-powered natural language filter
PoweredBy”Search by Mixpeek” badge
ShareLinkShareable search URL generator
ZeroResultsEmpty state placeholder
IntentCTAEnterprise CTA capture

Retrievers

Build the retriever pipeline behind your widget

Retriever Stages

Configure search, reranking, and enrichment stages

Interactions

Use interaction data to improve search relevance

JavaScript SDK

Full SDK for programmatic access