From 80b1badf74729e1f7f8c2f94848d85a6ab6f3cda Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Nicol=C3=B2=20Boschi?= Date: Thu, 19 Mar 2026 20:29:55 +0100 Subject: [PATCH] feat(docs): Integrations Hub + unified page hero (#620) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * fix(security): address all Dependabot vulnerability alerts Python (uv.lock, pyproject.toml): - authlib 1.6.6 → 1.6.9 (JWS header injection, OIDC hash binding, Bleichenbacher padding oracle) - pyasn1 0.6.2 → 0.6.3 (unbounded recursion DoS) - pyjwt 2.10.1 → 2.12.1 (unknown crit header extensions - also in integration-tests and crewai) - orjson 3.11.4 → 3.11.7 (deeply nested JSON recursion DoS) - tornado 6.5.2 → 6.5.5 (multipart DoS, incomplete cookie validation) npm (package.json, package-lock.json): - next ^16.1.6 → ^16.1.7 (HTTP smuggling, CSRF bypass, cache DoS, null origin bypass) - fast-xml-parser override updated to >=5.5.6 (numeric entity expansion bypass) - undici override added >=7.24.0 (WebSocket overflow, smuggling, CRLF injection, DoS) - flatted override added >=3.4.0 (unbounded recursion DoS) - svgo override added >=3.3.3 (DOCTYPE entity expansion DoS) - dompurify override added >=3.3.2 (XSS vulnerability) * feat(docs): add Integrations Hub and unified page hero - Add /integrations page with search, type filter, and card grid - Integrations defined in a single JSON file (src/data/integrations.json) supporting official and community entries with icon, author, and link - Scrolling integrations banner moved from global navbar to /integrations only - Remove IntegrationsGrid component; replace all usages with link to hub - Add PageHero component with full-bleed gradient background, shared across Cookbook, FAQ, Best Practices, Changelog, and Blog index pages - Remove FAQ from top navbar (already in Resources dropdown) - Move integration changelogs table to bottom of changelog page --- .../docs/developer/api/quickstart.mdx | 4 +- hindsight-docs/docs/developer/index.mdx | 4 +- hindsight-docs/docusaurus.config.ts | 6 +- .../src/components/PageHero.module.css | 46 ++ hindsight-docs/src/components/PageHero.tsx | 16 + .../src/components/SupportedGrids.tsx | 18 +- hindsight-docs/src/data/integrations.json | 114 +++++ hindsight-docs/src/pages/best-practices.mdx | 4 +- hindsight-docs/src/pages/changelog/index.md | 28 +- hindsight-docs/src/pages/cookbook/index.mdx | 20 +- hindsight-docs/src/pages/faq.mdx | 7 +- .../src/pages/integrations/index.module.css | 408 ++++++++++++++++++ .../src/pages/integrations/index.tsx | 163 +++++++ .../src/theme/BlogListPage/index.tsx | 6 +- .../src/theme/BlogListPage/styles.module.css | 31 +- hindsight-docs/src/theme/Navbar/index.tsx | 10 +- .../version-0.4/developer/api/quickstart.mdx | 4 +- .../version-0.4/developer/index.mdx | 4 +- 18 files changed, 787 insertions(+), 106 deletions(-) create mode 100644 hindsight-docs/src/components/PageHero.module.css create mode 100644 hindsight-docs/src/components/PageHero.tsx create mode 100644 hindsight-docs/src/data/integrations.json create mode 100644 hindsight-docs/src/pages/integrations/index.module.css create mode 100644 hindsight-docs/src/pages/integrations/index.tsx diff --git a/hindsight-docs/docs/developer/api/quickstart.mdx b/hindsight-docs/docs/developer/api/quickstart.mdx index 47fe2bc0..01b87243 100644 --- a/hindsight-docs/docs/developer/api/quickstart.mdx +++ b/hindsight-docs/docs/developer/api/quickstart.mdx @@ -9,7 +9,7 @@ Get up and running with Hindsight in 60 seconds. import Tabs from '@theme/Tabs'; import TabItem from '@theme/TabItem'; import CodeSnippet from '@site/src/components/CodeSnippet'; -import {ClientsGrid, IntegrationsGrid} from '@site/src/components/SupportedGrids'; +import {ClientsGrid} from '@site/src/components/SupportedGrids'; {/* Import raw source files */} import quickstartPy from '!!raw-loader!@site/examples/api/quickstart.py'; @@ -117,7 +117,7 @@ go get github.com/vectorize-io/hindsight/hindsight-clients/go ## Integrations - +Browse all supported integrations in the [Integrations Hub](/integrations). ## Next Steps diff --git a/hindsight-docs/docs/developer/index.mdx b/hindsight-docs/docs/developer/index.mdx index 22a712d2..f986ce5a 100644 --- a/hindsight-docs/docs/developer/index.mdx +++ b/hindsight-docs/docs/developer/index.mdx @@ -3,7 +3,7 @@ sidebar_position: 1 slug: / --- -import {ClientsGrid, IntegrationsGrid} from '@site/src/components/SupportedGrids'; +import {ClientsGrid} from '@site/src/components/SupportedGrids'; # Overview @@ -122,7 +122,7 @@ These settings only affect the `reflect` operation, not `recall`. ## Integrations - +Browse all supported integrations in the [Integrations Hub](/integrations). ## Next Steps diff --git a/hindsight-docs/docusaurus.config.ts b/hindsight-docs/docusaurus.config.ts index 0d231a2e..16400b7f 100644 --- a/hindsight-docs/docusaurus.config.ts +++ b/hindsight-docs/docusaurus.config.ts @@ -209,10 +209,10 @@ const config: Config = { className: 'navbar-item-developer', }, { - to: '/faq', + to: '/integrations', position: 'left', - label: 'FAQ', - className: 'navbar-item-faq', + label: 'Integrations', + className: 'navbar-item-integrations', }, { to: '/changelog', diff --git a/hindsight-docs/src/components/PageHero.module.css b/hindsight-docs/src/components/PageHero.module.css new file mode 100644 index 00000000..8b8041a1 --- /dev/null +++ b/hindsight-docs/src/components/PageHero.module.css @@ -0,0 +1,46 @@ +.hero { + width: 100vw; + position: relative; + left: 50%; + margin-left: -50vw; + /* cancel Docusaurus's margin-vert--lg on the page
*/ + margin-top: -2rem; + padding: 4rem 1.5rem 3.5rem; + text-align: center; + background: radial-gradient(ellipse 80% 60% at 50% 0%, rgba(0, 116, 217, 0.12) 0%, transparent 70%), + var(--ifm-background-color); + border-bottom: 1px solid var(--ifm-color-emphasis-200); + margin-bottom: 3rem; +} + +[data-theme='dark'] .hero { + background: radial-gradient(ellipse 80% 60% at 50% 0%, rgba(0, 116, 217, 0.18) 0%, transparent 70%), + var(--ifm-background-color); + border-bottom-color: rgba(255, 255, 255, 0.07); +} + +.title { + font-size: 3rem; + font-weight: 800; + background: linear-gradient(135deg, #0074d9, #009296); + -webkit-background-clip: text; + -webkit-text-fill-color: transparent; + background-clip: text; + letter-spacing: -0.03em; + line-height: 1.15; + margin-bottom: 0.75rem; +} + +.subtitle { + font-size: 1.05rem; + color: var(--ifm-color-emphasis-600); + max-width: 560px; + margin: 0 auto; + line-height: 1.7; +} + +@media (max-width: 640px) { + .title { + font-size: 2.2rem; + } +} diff --git a/hindsight-docs/src/components/PageHero.tsx b/hindsight-docs/src/components/PageHero.tsx new file mode 100644 index 00000000..fa4ae606 --- /dev/null +++ b/hindsight-docs/src/components/PageHero.tsx @@ -0,0 +1,16 @@ +import React, {type ReactNode} from 'react'; +import styles from './PageHero.module.css'; + +interface PageHeroProps { + title: string; + subtitle?: string; +} + +export default function PageHero({title, subtitle}: PageHeroProps): ReactNode { + return ( +
+

{title}

+ {subtitle &&

{subtitle}

} +
+ ); +} diff --git a/hindsight-docs/src/components/SupportedGrids.tsx b/hindsight-docs/src/components/SupportedGrids.tsx index 6d28cbea..61d73aef 100644 --- a/hindsight-docs/src/components/SupportedGrids.tsx +++ b/hindsight-docs/src/components/SupportedGrids.tsx @@ -1,7 +1,7 @@ import React from 'react'; import type {IconType} from 'react-icons'; import {IconGrid} from './IconGrid'; -import {SiPython, SiGo, SiOpenai, SiAnthropic, SiGooglegemini, SiOllama, SiCrewai, SiPydantic, SiVercel} from 'react-icons/si'; +import {SiPython, SiGo, SiOpenai, SiAnthropic, SiGooglegemini, SiOllama} from 'react-icons/si'; import {LuTerminal, LuPlug, LuZap, LuBrainCog, LuSparkles, LuGlobe} from 'react-icons/lu'; const OpenAICompatibleIcon: IconType = ({size = 28, ...props}) => ( @@ -27,22 +27,6 @@ export function ClientsGrid() { ); } -export function IntegrationsGrid() { - return ( - - ); -} export function LLMProvidersGrid() { return ( diff --git a/hindsight-docs/src/data/integrations.json b/hindsight-docs/src/data/integrations.json new file mode 100644 index 00000000..2c11d969 --- /dev/null +++ b/hindsight-docs/src/data/integrations.json @@ -0,0 +1,114 @@ +{ + "integrations": [ + { + "id": "litellm", + "name": "LiteLLM", + "description": "Add long-term memory to any LLM via LiteLLM proxy callbacks. Zero code changes — configure once and every model gets memory.", + "type": "official", + "by": "hindsight", + "category": "framework", + "link": "/sdks/integrations/litellm", + "icon": "/img/icons/litellm.png" + }, + { + "id": "crewai", + "name": "CrewAI", + "description": "Give CrewAI agents persistent, cross-session memory. Facts learned in one run are available in every future run.", + "type": "official", + "by": "hindsight", + "category": "framework", + "link": "/sdks/integrations/crewai", + "icon": "/img/icons/crewai.png" + }, + { + "id": "pydantic-ai", + "name": "Pydantic AI", + "description": "Integrate Hindsight memory into Pydantic AI agents with a simple dependency injection pattern.", + "type": "official", + "by": "hindsight", + "category": "framework", + "link": "/sdks/integrations/pydantic-ai", + "icon": "/img/icons/pydanticai.png" + }, + { + "id": "vercel-ai-sdk", + "name": "Vercel AI SDK", + "description": "Add persistent memory to Vercel AI SDK applications. Works with any model provider supported by the AI SDK.", + "type": "official", + "by": "hindsight", + "category": "framework", + "link": "/sdks/integrations/ai-sdk", + "icon": "/img/icons/vercel.png" + }, + { + "id": "vercel-chat", + "name": "Vercel Chat", + "description": "Drop-in memory layer for the Vercel AI Chatbot. Remembers users across sessions out of the box.", + "type": "official", + "by": "hindsight", + "category": "framework", + "link": "/sdks/integrations/chat", + "icon": "/img/icons/vercel.png" + }, + { + "id": "agno", + "name": "Agno", + "description": "Plug Hindsight into Agno agents for structured, long-term memory storage and retrieval.", + "type": "official", + "by": "hindsight", + "category": "framework", + "link": "/sdks/integrations/agno", + "icon": "/img/icons/agno.png" + }, + { + "id": "hermes", + "name": "Hermes", + "description": "Use Hindsight as the memory backend for the Hermes multi-agent messaging framework.", + "type": "official", + "by": "hindsight", + "category": "framework", + "link": "/sdks/integrations/hermes", + "icon": "/img/icons/hermes.png" + }, + { + "id": "local-mcp", + "name": "MCP Server", + "description": "Expose Hindsight memory as a Model Context Protocol server. Compatible with Claude, Cursor, and any MCP client.", + "type": "official", + "by": "hindsight", + "category": "mcp", + "link": "/sdks/integrations/local-mcp", + "icon": "/img/icons/mcp.png" + }, + { + "id": "openclaw", + "name": "OpenClaw", + "description": "Integrate Hindsight with OpenClaw to add memory capabilities to Claude-based agent workflows.", + "type": "official", + "by": "hindsight", + "category": "framework", + "link": "/sdks/integrations/openclaw", + "icon": "/img/icons/openclaw.png" + }, + { + "id": "skills", + "name": "Claude Code Skills", + "description": "Add Hindsight memory to Claude Code agents via the Skills integration. Persistent context across coding sessions.", + "type": "official", + "by": "hindsight", + "category": "tool", + "link": "/sdks/integrations/skills", + "icon": "/img/icons/skills.png" + }, + { + "id": "hindsight-openclaw-pro", + "name": "hindsight-openclaw-pro", + "description": "Production-grade Hindsight memory plugin for OpenClaw — per-agent config, multi-bank recall, and IaC bank management via the hoppro CLI.", + "type": "community", + "by": "mrkhachaturov", + "category": "framework", + "link": "https://github.com/mrkhachaturov/hindsight-openclaw-pro", + "icon": "/img/icons/openclaw.png" + } + ] +} diff --git a/hindsight-docs/src/pages/best-practices.mdx b/hindsight-docs/src/pages/best-practices.mdx index 4a6f2c50..4fa2e0fe 100644 --- a/hindsight-docs/src/pages/best-practices.mdx +++ b/hindsight-docs/src/pages/best-practices.mdx @@ -4,9 +4,9 @@ description: Practical guidance for agents and developers integrating Hindsight hide_table_of_contents: true --- -# Best Practices +import PageHero from '@site/src/components/PageHero'; -Practical guidance for agents and developers integrating Hindsight memory into production systems. + **Contents** - [Core Concepts](#core-concepts) — Memory banks, taxonomy, memory types diff --git a/hindsight-docs/src/pages/changelog/index.md b/hindsight-docs/src/pages/changelog/index.md index 0abf569f..82b28107 100644 --- a/hindsight-docs/src/pages/changelog/index.md +++ b/hindsight-docs/src/pages/changelog/index.md @@ -2,22 +2,9 @@ hide_table_of_contents: true --- -# Changelog +import PageHero from '@site/src/components/PageHero'; -This changelog highlights user-facing changes only. Internal maintenance, CI/CD, and infrastructure updates are omitted. - -For full release details, see [GitHub Releases](https://github.com/vectorize-io/hindsight/releases). - -## Integration Changelogs - -| Integration | Package | Description | -|---|---|---| -| [LiteLLM](/changelog/integrations/litellm) | `hindsight-litellm` | Universal LLM memory via LiteLLM (100+ providers) | -| [Pydantic AI](/changelog/integrations/pydantic-ai) | `hindsight-pydantic-ai` | Persistent memory tools for Pydantic AI agents | -| [CrewAI](/changelog/integrations/crewai) | `hindsight-crewai` | Persistent memory for CrewAI agents | -| [AI SDK](/changelog/integrations/ai-sdk) | `@vectorize-io/hindsight-ai-sdk` | Memory integration for Vercel AI SDK | -| [Chat SDK](/changelog/integrations/chat) | `@vectorize-io/hindsight-chat` | Memory integration for Vercel Chat SDK | -| [OpenClaw](/changelog/integrations/openclaw) | `@vectorize-io/hindsight-openclaw` | Hindsight memory plugin for OpenClaw | + ## [0.4.19](https://github.com/vectorize-io/hindsight/releases/tag/v0.4.19) @@ -606,3 +593,14 @@ For full release details, see [GitHub Releases](https://github.com/vectorize-io/ **Bug Fixes** - Fixed the standalone Docker image so it builds/runs correctly. ([`1056a20`](https://github.com/vectorize-io/hindsight/commit/1056a20)) + +## Integration Changelogs + +| Integration | Package | Description | +|---|---|---| +| [LiteLLM](/changelog/integrations/litellm) | `hindsight-litellm` | Universal LLM memory via LiteLLM (100+ providers) | +| [Pydantic AI](/changelog/integrations/pydantic-ai) | `hindsight-pydantic-ai` | Persistent memory tools for Pydantic AI agents | +| [CrewAI](/changelog/integrations/crewai) | `hindsight-crewai` | Persistent memory for CrewAI agents | +| [AI SDK](/changelog/integrations/ai-sdk) | `@vectorize-io/hindsight-ai-sdk` | Memory integration for Vercel AI SDK | +| [Chat SDK](/changelog/integrations/chat) | `@vectorize-io/hindsight-chat` | Memory integration for Vercel Chat SDK | +| [OpenClaw](/changelog/integrations/openclaw) | `@vectorize-io/hindsight-openclaw` | Hindsight memory plugin for OpenClaw | diff --git a/hindsight-docs/src/pages/cookbook/index.mdx b/hindsight-docs/src/pages/cookbook/index.mdx index 22241ce5..07d6d363 100644 --- a/hindsight-docs/src/pages/cookbook/index.mdx +++ b/hindsight-docs/src/pages/cookbook/index.mdx @@ -4,26 +4,12 @@ hide_table_of_contents: true --- import CookbookGrid from '@site/src/components/CookbookGrid'; +import PageHero from '@site/src/components/PageHero'; + +
-
-

Cookbook

-

- Practical examples and complete applications built with Hindsight. -

-
- ## Recipes **Contents** - [What is Hindsight and how does it differ from RAG?](#what-is-hindsight-and-how-does-it-differ-from-rag) @@ -64,7 +65,7 @@ Unlike vector databases (just search) or RAG systems (document retrieval), Hinds ### Which integrations are supported? - +Browse all supported integrations in the [Integrations Hub](/integrations). --- diff --git a/hindsight-docs/src/pages/integrations/index.module.css b/hindsight-docs/src/pages/integrations/index.module.css new file mode 100644 index 00000000..abd08684 --- /dev/null +++ b/hindsight-docs/src/pages/integrations/index.module.css @@ -0,0 +1,408 @@ +/* ── Full-width hero ─────────────────────────────────────────────────────── */ +.heroSection { + width: 100%; + padding: 5rem 1.5rem 4rem; + text-align: center; + background: radial-gradient(ellipse 80% 60% at 50% 0%, rgba(0, 116, 217, 0.12) 0%, transparent 70%), + var(--ifm-background-color); + border-bottom: 1px solid var(--ifm-color-emphasis-200); +} + +[data-theme='dark'] .heroSection { + background: radial-gradient(ellipse 80% 60% at 50% 0%, rgba(0, 116, 217, 0.18) 0%, transparent 70%), + var(--ifm-background-color); + border-bottom-color: rgba(255, 255, 255, 0.07); +} + +.heroTitle { + font-size: 3.2rem; + font-weight: 800; + background: linear-gradient(135deg, #0074d9, #009296); + -webkit-background-clip: text; + -webkit-text-fill-color: transparent; + background-clip: text; + letter-spacing: -0.03em; + line-height: 1.1; + margin-bottom: 0.75rem; +} + +.heroSubtitle { + font-size: 1.05rem; + color: var(--ifm-color-emphasis-600); + max-width: 500px; + margin: 0 auto 2.25rem; + line-height: 1.7; +} + +/* ── Search ──────────────────────────────────────────────────────────────── */ +.searchWrapper { + position: relative; + max-width: 640px; + margin: 0 auto; +} + +.searchInput { + width: 100%; + box-sizing: border-box; + padding: 1.05rem 3.5rem 1.05rem 1.5rem; + border-radius: 14px; + border: 2px solid var(--ifm-color-emphasis-300); + background: var(--ifm-background-surface-color); + color: var(--ifm-font-color-base); + font-size: 1.1rem; + font-family: inherit; + outline: none; + transition: border-color 0.15s ease, box-shadow 0.15s ease; + box-shadow: 0 4px 24px rgba(0, 0, 0, 0.08); +} + +.searchInput::placeholder { + color: var(--ifm-color-emphasis-400); +} + +.searchInput:focus { + border-color: #0074d9; + box-shadow: 0 0 0 4px rgba(0, 116, 217, 0.15), 0 4px 24px rgba(0, 0, 0, 0.08); +} + +[data-theme='dark'] .searchInput { + background: #242428; + border-color: rgba(255, 255, 255, 0.15); + box-shadow: 0 4px 24px rgba(0, 0, 0, 0.4); +} + +[data-theme='dark'] .searchInput:focus { + border-color: #4da6ff; + box-shadow: 0 0 0 4px rgba(77, 166, 255, 0.18), 0 4px 24px rgba(0, 0, 0, 0.4); +} + +.searchClear { + position: absolute; + right: 1rem; + top: 50%; + transform: translateY(-50%); + background: var(--ifm-color-emphasis-200); + border: none; + color: var(--ifm-color-emphasis-600); + cursor: pointer; + font-size: 1rem; + line-height: 1; + width: 24px; + height: 24px; + border-radius: 50%; + display: flex; + align-items: center; + justify-content: center; + transition: background 0.1s; +} + +.searchClear:hover { + background: var(--ifm-color-emphasis-300); +} + +/* ── Hero stats ──────────────────────────────────────────────────────────── */ +.heroStats { + display: inline-flex; + align-items: center; + gap: 0.6rem; + font-size: 0.82rem; + color: var(--ifm-color-emphasis-500); + margin-top: 1.25rem; +} + +.stat strong { + color: var(--ifm-color-emphasis-800); +} + +[data-theme='dark'] .stat strong { + color: var(--ifm-color-emphasis-700); +} + +.statDivider { + color: var(--ifm-color-emphasis-300); +} + +/* ── Page container ──────────────────────────────────────────────────────── */ +.page { + max-width: 1200px; + margin: 0 auto; + padding: 2.5rem 1.5rem 5rem; +} + +/* ── Toolbar (filters + count) ───────────────────────────────────────────── */ +.toolbar { + display: flex; + align-items: center; + justify-content: space-between; + margin-bottom: 1.75rem; + flex-wrap: wrap; + gap: 0.75rem; +} + +.filterGroup { + display: flex; + align-items: center; + gap: 0.4rem; +} + +.filterPill { + display: inline-flex; + align-items: center; + font-size: 0.82rem; + font-weight: 500; + padding: 0.3rem 0.85rem; + border-radius: 999px; + border: 1px solid var(--ifm-color-emphasis-300); + background: transparent; + color: var(--ifm-color-emphasis-700); + cursor: pointer; + transition: all 0.15s ease; + font-family: inherit; +} + +.filterPill:hover { + border-color: var(--ifm-color-primary); + color: var(--ifm-color-primary); +} + +.filterPillActive { + background: var(--ifm-color-primary); + border-color: var(--ifm-color-primary); + color: #fff !important; +} + +[data-theme='dark'] .filterPill { + border-color: rgba(255, 255, 255, 0.15); + color: var(--ifm-color-emphasis-600); +} + +/* ── Result count ────────────────────────────────────────────────────────── */ +.resultCount { + font-size: 0.8rem; + color: var(--ifm-color-emphasis-400); + margin: 0; +} + +/* ── Grid ────────────────────────────────────────────────────────────────── */ +.grid { + display: grid; + grid-template-columns: repeat(3, 1fr); + gap: 1.25rem; + margin-bottom: 4rem; +} + +@media (max-width: 996px) { + .grid { grid-template-columns: repeat(2, 1fr); } +} + +@media (max-width: 640px) { + .grid { grid-template-columns: 1fr; } + .heroTitle { font-size: 2.2rem; } +} + +/* ── Card ────────────────────────────────────────────────────────────────── */ +.card { + display: flex; + flex-direction: column; + border-radius: 12px; + border: 1px solid var(--ifm-color-emphasis-200); + background: var(--ifm-background-surface-color); + text-decoration: none !important; + color: inherit; + transition: box-shadow 0.2s ease, transform 0.2s ease; + overflow: hidden; +} + +[data-theme='dark'] .card { + background: #1c1c1e; + border-color: rgba(255, 255, 255, 0.07); +} + +.card:hover { + transform: translateY(-2px); + box-shadow: 0 6px 24px rgba(0, 116, 217, 0.12); + text-decoration: none !important; + color: inherit; +} + +.cardHeader { + display: flex; + align-items: center; + justify-content: space-between; + padding: 1rem 1.1rem 0; +} + +.cardIcon { + width: 36px; + height: 36px; + object-fit: contain; + flex-shrink: 0; +} + +.typeBadge { + font-size: 0.63rem; + font-weight: 700; + text-transform: uppercase; + letter-spacing: 0.05em; + padding: 0.15rem 0.5rem; + border-radius: 999px; +} + +.typeBadgeOfficial { + background: rgba(0, 116, 217, 0.12); + color: #0074d9; +} + +[data-theme='dark'] .typeBadgeOfficial { + background: rgba(0, 116, 217, 0.2); + color: #4da6ff; +} + +.typeBadgeCommunity { + background: rgba(0, 146, 150, 0.12); + color: #009296; +} + +[data-theme='dark'] .typeBadgeCommunity { + background: rgba(0, 146, 150, 0.2); + color: #00bcc0; +} + +.cardBody { + flex: 1; + padding: 0.85rem 1.1rem 0.75rem; +} + +.cardTitle { + font-size: 1rem; + font-weight: 700; + margin: 0 0 0.4rem; + color: var(--ifm-heading-color); + letter-spacing: -0.01em; + border-bottom: none !important; + border-image: none !important; +} + +.cardDescription { + font-size: 0.82rem; + color: var(--ifm-color-emphasis-600); + line-height: 1.6; + margin: 0; + display: -webkit-box; + -webkit-line-clamp: 3; + -webkit-box-orient: vertical; + overflow: hidden; +} + +.cardFooter { + display: flex; + align-items: center; + padding: 0.65rem 1.1rem 0.9rem; + margin-top: 0.25rem; + border-top: 1px solid var(--ifm-color-emphasis-100); +} + +[data-theme='dark'] .cardFooter { + border-top-color: rgba(255, 255, 255, 0.06); +} + +.byLine { + display: inline-flex; + align-items: center; + gap: 0.5rem; + font-size: 0.78rem; + font-family: 'JetBrains Mono', 'Fira Code', 'SF Mono', Monaco, Consolas, monospace; + color: var(--ifm-color-emphasis-600); +} + +.authorIcon { + width: 22px; + height: 22px; + border-radius: 50%; + object-fit: cover; + flex-shrink: 0; + border: 1px solid var(--ifm-color-emphasis-200); +} + +[data-theme='dark'] .authorIcon { + border-color: rgba(255, 255, 255, 0.1); +} + +.authorName { + font-weight: 500; +} + +/* ── Empty state ─────────────────────────────────────────────────────────── */ +.empty { + text-align: center; + padding: 4rem 2rem; + color: var(--ifm-color-emphasis-500); +} + +.resetButton { + margin-top: 1rem; + padding: 0.4rem 1rem; + border-radius: 6px; + border: 1px solid var(--ifm-color-primary); + background: transparent; + color: var(--ifm-color-primary); + font-size: 0.85rem; + font-family: inherit; + cursor: pointer; + transition: all 0.15s ease; +} + +.resetButton:hover { + background: var(--ifm-color-primary); + color: #fff; +} + +/* ── Submit banner ───────────────────────────────────────────────────────── */ +.submitBanner { + border-radius: 14px; + border: 1px solid var(--ifm-color-emphasis-200); + background: linear-gradient(135deg, rgba(0, 116, 217, 0.06), rgba(0, 146, 150, 0.06)); + padding: 2.5rem 2rem; + text-align: center; +} + +[data-theme='dark'] .submitBanner { + border-color: rgba(255, 255, 255, 0.08); + background: linear-gradient(135deg, rgba(0, 116, 217, 0.1), rgba(0, 146, 150, 0.1)); +} + +.submitBannerContent { + max-width: 480px; + margin: 0 auto; +} + +.submitBannerTitle { + font-size: 1.3rem; + font-weight: 700; + margin-bottom: 0.5rem; +} + +.submitBannerText { + font-size: 0.9rem; + color: var(--ifm-color-emphasis-600); + margin-bottom: 1.25rem; + line-height: 1.6; +} + +.submitButton { + display: inline-block; + padding: 0.55rem 1.4rem; + border-radius: 8px; + background: linear-gradient(135deg, #0074d9, #009296); + color: #fff !important; + font-size: 0.9rem; + font-weight: 600; + text-decoration: none !important; + transition: opacity 0.15s ease, transform 0.15s ease; +} + +.submitButton:hover { + opacity: 0.9; + transform: translateY(-1px); + color: #fff !important; +} diff --git a/hindsight-docs/src/pages/integrations/index.tsx b/hindsight-docs/src/pages/integrations/index.tsx new file mode 100644 index 00000000..78b1581b --- /dev/null +++ b/hindsight-docs/src/pages/integrations/index.tsx @@ -0,0 +1,163 @@ +import React, {useMemo, useState} from 'react'; +import Link from '@docusaurus/Link'; +import useBaseUrl from '@docusaurus/useBaseUrl'; +import Layout from '@theme/Layout'; +import IntegrationsBanner from '@site/src/components/IntegrationsBanner'; +import integrationsData from '@site/src/data/integrations.json'; +import styles from './index.module.css'; + +const INTEGRATIONS_JSON_URL = + 'https://github.com/vectorize-io/hindsight/edit/main/hindsight-docs/src/data/integrations.json'; + +type IntegrationType = 'official' | 'community'; + +interface Integration { + id: string; + name: string; + description: string; + type: IntegrationType; + by: string; + category: string; + link: string; + icon?: string; +} + +function IntegrationCard({integration}: {integration: Integration}) { + const iconSrc = useBaseUrl(integration.icon ?? ''); + const faviconSrc = useBaseUrl('/img/favicon.png'); + const isExternal = integration.link.startsWith('http'); + + return ( + +
+ {integration.icon && } + + {integration.type === 'official' ? 'Official' : 'Community'} + +
+
+

{integration.name}

+

{integration.description}

+
+
+ {integration.type === 'official' ? ( + + + Hindsight Team + + ) : ( + + + @{integration.by} + + )} +
+ + ); +} + +export default function IntegrationsHub(): React.ReactElement { + const [search, setSearch] = useState(''); + const [selectedType, setSelectedType] = useState('all'); + + const integrations = integrationsData.integrations as Integration[]; + + const filtered = useMemo(() => { + const q = search.toLowerCase().trim(); + return integrations.filter((i) => { + if (selectedType !== 'all' && i.type !== selectedType) return false; + if (q && !i.name.toLowerCase().includes(q) && !i.description.toLowerCase().includes(q)) return false; + return true; + }); + }, [integrations, search, selectedType]); + + const officialCount = integrations.filter((i) => i.type === 'official').length; + const communityCount = integrations.filter((i) => i.type === 'community').length; + + return ( + + + {/* Full-width hero with its own background */} +
+

Integrations Hub

+

+ Connect Hindsight to your stack. Browse official integrations and community-built connectors. +

+ +
+ setSearch(e.target.value)} + aria-label="Search integrations" + autoComplete="off" + /> + {search && ( + + )} +
+ +
+ {officialCount} official + · + {communityCount} community +
+
+ + {/* Scrolling banner */} + + + {/* Main content */} +
+
+
+ {(['all', 'official', 'community'] as const).map((t) => ( + + ))} +
+ {filtered.length} integration{filtered.length !== 1 ? 's' : ''} +
+ + {filtered.length === 0 ? ( +
+

No integrations match your search.

+ +
+ ) : ( +
+ {filtered.map((integration) => ( + + ))} +
+ )} + +
+
+

Built something with Hindsight?

+

+ Share your integration with the community. Open a pull request and add your entry to the integrations list. +

+ + Submit an integration → + +
+
+
+
+ ); +} diff --git a/hindsight-docs/src/theme/BlogListPage/index.tsx b/hindsight-docs/src/theme/BlogListPage/index.tsx index 63f6a928..fd67b6b7 100644 --- a/hindsight-docs/src/theme/BlogListPage/index.tsx +++ b/hindsight-docs/src/theme/BlogListPage/index.tsx @@ -3,6 +3,7 @@ import Link from '@docusaurus/Link'; import Layout from '@theme/Layout'; import type {Props} from '@theme/BlogListPage'; import type {PropBlogPostContent} from '@docusaurus/plugin-content-blog'; +import PageHero from '@site/src/components/PageHero'; import styles from './styles.module.css'; const CLOUD_TAG = 'hindsight-cloud'; @@ -70,10 +71,7 @@ export default function BlogListPage({items, metadata}: Props): React.ReactEleme return (
-
-

{blogTitle}

- {blogDescription &&

{blogDescription}

} -
+ {cloudPosts.length > 0 && (
diff --git a/hindsight-docs/src/theme/BlogListPage/styles.module.css b/hindsight-docs/src/theme/BlogListPage/styles.module.css index 7a9341e7..8ad6c526 100644 --- a/hindsight-docs/src/theme/BlogListPage/styles.module.css +++ b/hindsight-docs/src/theme/BlogListPage/styles.module.css @@ -1,33 +1,7 @@ .blogPage { max-width: 1280px; margin: 0 auto; - padding: 4rem 2rem 6rem; -} - -/* ── Header ─────────────────────────────────────── */ -.header { - text-align: center; - margin-bottom: 4rem; -} - -.headerTitle { - font-size: 3rem; - font-weight: 800; - background: linear-gradient(135deg, #0074d9, #009296); - -webkit-background-clip: text; - -webkit-text-fill-color: transparent; - background-clip: text; - margin-bottom: 0.75rem; - line-height: 1.15; - letter-spacing: -0.03em; -} - -.headerSubtitle { - font-size: 1.05rem; - color: var(--ifm-color-emphasis-600); - max-width: 520px; - margin: 0 auto; - line-height: 1.7; + padding: 2rem 2rem 6rem; } /* ── Section ─────────────────────────────────────── */ @@ -93,9 +67,6 @@ gap: 2rem; } - .headerTitle { - font-size: 2.25rem; - } } /* ── Card ────────────────────────────────────────── */ diff --git a/hindsight-docs/src/theme/Navbar/index.tsx b/hindsight-docs/src/theme/Navbar/index.tsx index 4509c6f3..48ce38ad 100644 --- a/hindsight-docs/src/theme/Navbar/index.tsx +++ b/hindsight-docs/src/theme/Navbar/index.tsx @@ -1,15 +1,11 @@ import React, {type ReactNode} from 'react'; import NavbarLayout from '@theme/Navbar/Layout'; import NavbarContent from '@theme/Navbar/Content'; -import IntegrationsBanner from '@site/src/components/IntegrationsBanner'; export default function Navbar(): ReactNode { return ( - <> - - - - - + + + ); } diff --git a/hindsight-docs/versioned_docs/version-0.4/developer/api/quickstart.mdx b/hindsight-docs/versioned_docs/version-0.4/developer/api/quickstart.mdx index 2f6bab98..eebba331 100644 --- a/hindsight-docs/versioned_docs/version-0.4/developer/api/quickstart.mdx +++ b/hindsight-docs/versioned_docs/version-0.4/developer/api/quickstart.mdx @@ -9,7 +9,7 @@ Get up and running with Hindsight in 60 seconds. import Tabs from '@theme/Tabs'; import TabItem from '@theme/TabItem'; import CodeSnippet from '@site/src/components/CodeSnippet'; -import {ClientsGrid, IntegrationsGrid} from '@site/src/components/SupportedGrids'; +import {ClientsGrid} from '@site/src/components/SupportedGrids'; {/* Import raw source files */} import quickstartPy from '!!raw-loader!@site/examples/api/quickstart.py'; @@ -107,7 +107,7 @@ curl -fsSL https://hindsight.vectorize.io/get-cli | bash ## Integrations - +Browse all supported integrations in the [Integrations Hub](/integrations). ## Next Steps diff --git a/hindsight-docs/versioned_docs/version-0.4/developer/index.mdx b/hindsight-docs/versioned_docs/version-0.4/developer/index.mdx index 22a712d2..f986ce5a 100644 --- a/hindsight-docs/versioned_docs/version-0.4/developer/index.mdx +++ b/hindsight-docs/versioned_docs/version-0.4/developer/index.mdx @@ -3,7 +3,7 @@ sidebar_position: 1 slug: / --- -import {ClientsGrid, IntegrationsGrid} from '@site/src/components/SupportedGrids'; +import {ClientsGrid} from '@site/src/components/SupportedGrids'; # Overview @@ -122,7 +122,7 @@ These settings only affect the `reflect` operation, not `recall`. ## Integrations - +Browse all supported integrations in the [Integrations Hub](/integrations). ## Next Steps