@chakra-docs/chakra
v0.2.0
Published
Chakra UI component layer for Chakra Docs.
Maintainers
Readme
@chakra-docs/chakra
Chakra UI component layer for Chakra Docs.
Created by Ryan Hefner and Commune Software.
Chakra-based building blocks for composing documentation pages inside existing Chakra applications: docs layout primitives, sidebar navigation, desktop and mobile tables of contents, breadcrumbs, page and heading actions, search, version/collection switching, pagination, callouts, Markdown rendering, and code block shells. React and Chakra stay as peer dependencies, and host apps own the Chakra provider, routing, and branding. All components are client components (the package ships with 'use client').
Install
npm install @chakra-docs/chakra @chakra-ui/react @emotion/react react react-domPeer dependencies: @chakra-ui/react (>=3.36 <4), @emotion/react (>=11 <12),
react (>=18 <20), and react-dom (>=18 <20). Emotion is a direct peer
because Chakra UI requires the host application to provide it.
Syntax highlighting
Install the optional @chakra-docs/shiki package to highlight both CodeBlock and Markdown code fences without Postkit:
import { DocsProvider } from '@chakra-docs/chakra';
import { createChakraDocsShikiAdapter } from '@chakra-docs/shiki';
const adapter = createChakraDocsShikiAdapter();
<DocsProvider config={{ codeBlock: { adapter } }}>{children}</DocsProvider>;Create the adapter once at module scope. It lazily loads Shiki and accepts languages and themes: { light, dark } options. The code-block shell remains styled by Chakra recipes. Existing Chakra UI and Postkit adapters remain supported; no adapter means plain-text code rendering. See the Shiki package for defaults, preloading, and resource lifecycle guidance.
Usage
Wrap your docs pages in your app's ChakraProvider, add a DocsProvider for shared configuration, and compose a page from DocsLayout, DocsArticle, and friends. Pages, nav, and headings come from a Chakra Docs manifest (built with @chakra-docs/source-filesystem or the @chakra-docs/cli generated output):
import { ChakraProvider, defaultSystem } from '@chakra-ui/react';
import {
Callout,
DocsArticle,
DocsBreadcrumbs,
DocsLayout,
DocsPageActions,
DocsPagination,
DocsProvider,
MarkdownContent,
} from '@chakra-docs/chakra';
import type { DocsManifest, DocsPage } from '@chakra-docs/core';
export function DocsRoutePage(props: {
manifest: DocsManifest;
page: DocsPage;
}) {
const { manifest, page } = props;
return (
<ChakraProvider value={defaultSystem}>
<DocsProvider config={{ labels: { search: 'Search docs' } }}>
<DocsLayout headings={page.headings} nav={manifest.nav} page={page}>
<DocsArticle
headings={page.headings}
page={page}
breadcrumbs={<DocsBreadcrumbs nav={manifest.nav} page={page} />}
actions={<DocsPageActions.Root page={page} />}
>
<Callout type="info" title="Note">
This page is generated from Markdown.
</Callout>
<MarkdownContent source={page.body ?? ''} headingPermalinks />
<DocsPagination nav={manifest.nav} page={page} />
</DocsArticle>
</DocsLayout>
</DocsProvider>
</ChakraProvider>
);
}Sidebar disclosures are opt-in so existing navigation remains unchanged:
<DocsLayout
nav={manifest.nav}
page={page}
sidebarCollapsible
sidebarDefaultExpanded="active"
/>"active" opens every branch on the current page's navigation path. Manual
expansion remains open as the route changes, while navigation into a collapsed
branch opens the new active path. Nested branches toggle independently. The
other initial values are "all", "none", or an explicit array of nav item
IDs.
For controlled state, pass sidebarExpandedIds and update it from
onSidebarExpandedChange:
const [expandedIds, setExpandedIds] = useState<readonly string[]>([]);
<DocsLayout
nav={manifest.nav}
page={page}
sidebarCollapsible
sidebarExpandedIds={expandedIds}
onSidebarExpandedChange={setExpandedIds}
/>;Controlled consumers remain the source of truth. When the route enters a
collapsed branch, onSidebarExpandedChange receives the current manual IDs
merged with the active ancestors.
When nav is present, DocsLayout automatically replaces the desktop sidebar
with a hamburger trigger below the lg breakpoint. The trigger opens an
accessible, focus-managed drawer and the active page's branch is expanded. A
selected navigation link closes the drawer. Pass search or other app-owned
controls into the drawer without rebuilding its navigation behavior:
<DocsLayout
nav={manifest.nav}
page={page}
mobileNavigationProps={{
search: <DocsSearch records={manifest.search} />,
title: 'Browse documentation',
}}
/>Set mobileNavigation={false} when the application already owns its mobile
navigation. For a custom header or drawer composition, use the exported
DocsMobileNavigation.Root, Trigger, Content, Header, Title,
CloseTrigger, Search, Body, and Sidebar parts.
The drawer mounts lazily and retains its contents after closing, preserving
manual sidebar expansion across reopenings and client-side navigation. New
active branches open automatically. Set closeOnNavigate={false} on the root
to keep the drawer open for both link selections and page.route changes.
Controlled open and sidebar expandedIds remain application-owned.
Add search and version switching to your site chrome:
import { DocsSearch, DocsVersionSelect } from '@chakra-docs/chakra';
<DocsSearch
records={manifest.search}
collectionId="docs"
onNavigate={(href) => router.push(href)}
/>
<DocsVersionSelect
collections={manifest.collections}
value={activeCollectionId}
onValueChange={setActiveCollectionId}
includeAll
/>To keep the search corpus and ranking work off the client, pass a provider from
@chakra-docs/search/client instead of records. The component requests
popular results when it opens, debounces typed queries, cancels stale requests,
and sends collection scopes to the server:
npm install @chakra-docs/searchimport { DocsSearch } from '@chakra-docs/chakra';
import { createHttpSearchProvider } from '@chakra-docs/search/client';
const searchProvider = createHttpSearchProvider('/api/docs/search');
<DocsSearch
searchProvider={searchProvider}
collectionIds={['docs']}
debounceMs={150}
onNavigate={(href) => router.push(href)}
/>;If both searchProvider and records are passed, remote search takes
precedence. Keep records mode for static deployments that do not have a
search endpoint.
For an immediate, curated opening list, pass defaultResults={featuredPages}
and optionally defaultResultsLabel="New this week". These display-only
DocsSearchResult objects can come from server/build data. The empty-query list
preserves supplied ordering, filters by collection scope, and respects
popularLimit (default six). Typing uses the normal provider or local index;
clearing restores the curated list. An explicit empty array suppresses provider
defaults. The heading defaults to “Recommended.”
Alternatively, set prefetch="intent" (trigger hover/focus) or
prefetch="mount" (after client mount) to warm the provider's empty-query
response. prefetchStaleTimeMs defaults to 60,000. Fresh responses and in-flight
work are reused; stale results remain stable while refreshing and the next
opening/query reset receives the new list. Prefetching is disabled by default,
performs no SSR fetches or search analytics, and is skipped with curated
defaultResults. Cache state is per component and invalidated on provider,
scope, or limit changes. Remount with a context-specific key when auth/tenant
context changes invisibly to these props. Only ship authorized suggestions.
Configuration
DocsProvider accepts a ChakraDocsConfig (config prop) that is merged down the tree and read via useDocsConfig():
linkComponent— aDocsLinkComponentused for internal navigation, including Markdown, sidebar, pagination, and search-result links (for exampleDocsLinkfrom@chakra-docs/next/link). External URLs continue to render as ordinary anchors.labels—Partial<DocsLabels>overrides for UI copy (search,searchPlaceholder,searchLoading,searchError,previousPage,nextPage,onThisPage,copyCode, ...).analytics—DocsAnalyticsCallbacksfor search, code/package copies, page actions/copies, heading-link copies, and feedback. Callbacks are optional, provider-neutral observers; thrown errors and rejected promises are isolated from the UI. Report integration failures inside your callback if needed.codeBlock— sharedCodeBlockdefaults.adapterconfigures syntax highlighting;copy,lineNumbers,size,variant, andwrapconfigure every nested code block unless an instance overrides them.layout—ChakraDocsLayoutConfigsticky offsets (stickyTop,sidebarStickyTop,tocStickyTop,scrollMarginTop), each accepting responsive Chakra values.
Code-copy events fire after a successful clipboard write, not on click. Use
<CodeBlock code="pnpm add @chakra-docs/chakra" packageManager="pnpm" /> to
emit onPackageCommandCopy({ command, manager }) as well as onCodeCopy.
The manager is explicit metadata; ordinary shell blocks are not guessed to be
package commands. A root slotProps.onCopy observer runs alongside analytics.
Standalone Postkit components have their own callbacks; this provider does not
automatically instrument another renderer. Only forward query/content fields
to your analytics service when appropriate for your privacy and consent policy.
Search callbacks include onSearchOpen, onSearchClose({ reason }),
onSearch(query), onSearchResults(event), onSearchError(context), and
onSearchResultSelect(result, context). Result context identifies the query,
collection scope, source (curated/local/remote), mode (default/query),
and result count; selection adds one-based position and interaction.
Result-list events include ordered resultIds and represent list exposure,
not viewport-level impressions. Zero results are distinct from provider errors.
Background prefetching stays silent. Repeated shortcuts, arrow movements, and
equivalent rerenders do not duplicate events. Selection-close events run before
navigation; unmount alone is not reported as dismissal. Modified/prevented link
clicks preserve native behavior without selecting the current dialog.
DocsSearch.analyticsDebounceMs optionally coalesces query-change callbacks
(default 0); pending events are cancelled on clear, close, or unmount.
The existing one-argument selection callback remains compatible.
Theming and recipes
Every visual Chakra Docs component uses a package-owned Chakra slot recipe. The
components include those recipes as runtime fallbacks, so they continue to work
with Chakra's defaultSystem and do not require a custom provider. To override
recipes in a host theme, compose chakraDocsThemeConfig before the app's
overrides:
import {
ChakraProvider,
createSystem,
defaultConfig,
defineConfig,
} from '@chakra-ui/react';
import {
chakraDocsRecipeKeys,
chakraDocsThemeConfig,
} from '@chakra-docs/chakra/theme';
const appTheme = defineConfig({
theme: {
slotRecipes: {
[chakraDocsRecipeKeys.tableOfContents]: {
base: {
activeIndicator: {
w: '3px',
},
},
},
},
},
});
const system = createSystem(defaultConfig, chakraDocsThemeConfig, appTheme);
<ChakraProvider value={system}>{/* app */}</ChakraProvider>;Recipe defaults use portable Chakra semantic colors (bg, fg, and border)
so they inherit naturally from the host system. Applications can introduce a
brand palette or replace any slot without changing component code.
The defaults also include visible keyboard-focus states, 44px mobile hit areas
for standalone controls (without expanding inline links), and wrapping for long
navigation labels, card content and prose. Tables and code blocks retain their
own horizontal scroll areas. Disclosure indicators and dialog surfaces respect
prefers-reduced-motion.
Page-action menus and submenus fit the available viewport and scroll when tall.
Their size and root CSS custom-property overrides carry through portals; root
layout styles do not. Customize menuContent/submenuContent for menu surfaces,
menuItem for rows, and actionContent/label/description for the text stack.
Per-instance slot props still take precedence over recipe defaults.
| Recipe key | Slots |
| --------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| chakraDocsApiTable | root, table, caption, header, row, columnHeader, cell, name, type, defaultValue, description, required |
| chakraDocsLayout | root, mobileNavigation, inner, sidebar, content |
| chakraDocsArticle | root, header, breadcrumbs, heading, title, description, actions |
| chakraDocsBadge | root |
| chakraDocsBreadcrumbs | root, list, item, link, current, separator |
| chakraDocsCards | root, card, icon, content, title, description, badge |
| chakraDocsHeadingPermalink | root, trigger, indicator |
| chakraDocsFeedback | root, prompt, choices, option, comment, actions, submit, status |
| chakraDocsPageActions | root, copyRoot, trigger, primaryTrigger, icon, actionContent, label, indicator, menu, menuTrigger, menuIndicator, menuPositioner, menuContent, menuItem, menuGroup, menuGroupLabel, menuSeparator, submenu, submenuTrigger, submenuIndicator, submenuPositioner, submenuContent, description |
| chakraDocsSidebar | root, list, item, link, sectionTitle, badge, children, trigger, indicator, content |
| chakraDocsSteps | root, item, indicator, content, title, description |
| chakraDocsTabs | root, list, trigger, content |
| chakraDocsTableOfContents | root, label, list, item, link, activeIndicator |
| chakraDocsMobileTableOfContents | root, trigger, triggerLabel, current, indicator, content, list, item, link, activeIndicator |
| chakraDocsMobileNavigation | root, trigger, triggerIcon, triggerLabel, backdrop, positioner, content, header, title, closeTrigger, search, body, sidebar |
| chakraDocsSearch | trigger, triggerLabel, shortcut, backdrop, positioner, root, header, title, body, input, results, sectionLabel, resultList, result, resultLink, resultRow, resultContent, resultTitle, resultDescription, resultBadge, status |
| chakraDocsVersionSelect | root, label, select |
| chakraDocsMarkdownContent | root, heading, paragraph, list, listItem, inlineCode, link, quote, codeBlock, image, separator, tableContainer, table, tableHead, tableBody, tableRow, tableHeader, tableCell, taskCheckbox |
| chakraDocsPagination | root, item, label, link |
| chakraDocsCallout | root, title, content |
| chakraDocsCodeBlock | root, header, title, control, language, copyTrigger, copyIndicator, content, code, codeText |
Page actions stack their label and description vertically inside actionContent, while the icon remains alongside the text. Override chakraDocsPageActions.base.actionContent to customize the text layout or spacing; label and description continue to control typography independently.
The individual recipe definitions, chakraDocsSlotRecipes,
chakraDocsThemeConfig, and chakraDocsRecipeKeys are public exports. Named
*SlotProps props provide per-instance overrides for the same component parts.
For example, an application can replace the default disclosure motion:
const sidebarRecipe = {
base: {
indicator: { transition: 'transform 200ms ease' },
content: {
display: 'grid',
transition: 'grid-template-rows 200ms ease',
'& > ol': { overflow: 'hidden' },
},
},
variants: {
expanded: {
true: { content: { display: 'grid', gridTemplateRows: '1fr' } },
false: { content: { display: 'grid', gridTemplateRows: '0fr' } },
},
},
};API
Components
DocsProvider— merges and providesChakraDocsConfig(labels, link component, analytics, code block adapter, layout offsets) to descendants.DocsLayout— responsive shell that rendersDocsSidebaratlgand above, an automaticDocsMobileNavigationbelowlg(whennavis passed), a content area, andDocsTableOfContents(whenheadingsis passed). Its content wrapper is adivby default so it can safely sit inside an application's existingmain; standalone pages can opt in withcontentSlotProps={{ as: 'main' }}. UsesidebarContentfor a legend, version control, or other content above the navigation, andsidebarBadgeSlotPropsto style nav badges. Collapsible desktop navigation is enabled withsidebarCollapsible; configure its initial state withsidebarDefaultExpanded, or control it withsidebarExpandedIdsandonSidebarExpandedChange. The mobile drawer uses collapsible active-path navigation by default. PassmobileNavigation={false}to opt out ormobileNavigationPropsto configure its title, search content, controlled state, slots, and sidebar. Props:page,nav,headings,stickyTop,scrollMarginTop,slotProps,contentSlotProps,sidebarContent,sidebarBadgeSlotProps,sidebarCollapsible,sidebarDefaultExpanded,sidebarExpandedIds,onSidebarExpandedChange,sidebarTriggerSlotProps,sidebarIndicatorSlotProps,sidebarContentSlotProps,sidebarSlotProps,mobileNavigation,mobileNavigationProps,tocSlotProps,children.DocsArticle— article wrapper that renders the page title and description header, with optionalbreadcrumbsandactionsregions.DocsBreadcrumbs— navigation path derived fromnavandpage.route, with optional site-level home item.DocsPageActions— compound page action API withRoot,CopyPage,CopyLink,ViewMarkdown,Edit,Menu,Submenu,Group,Separator, andItemcomponents. Without children,Rootcomposes Copy page with a menu of the available standard actions; itssplitvariant uses a compact chevron trigger while safely falling back when either half is unavailable. Defaults are transparentfgtriggers, a sharedborderoutline with one split divider, andbgmenu surfaces with hover, keyboard-highlight and focus states. Appearance belongs tochakraDocsPageActions, not the generic Button/Clipboard/Link recipes; per-instance slot overrides remain supported.Rootsupportssm,md, andlgsizes, and its Chakra Menu-backed overlays provide controlled or uncontrolled state, nested menus, automatic close on selection, Escape and outside-click dismissal, focus restoration, keyboard navigation, typeahead, and collision-aware positioning.DocsHeadingPermalink— accessible clipboard action for a section URL.DocsPageFeedback— compound feedback form with controlled or uncontrolled choice/comment state, async submission status, and application-owned persistence.DocsCards— compound responsive card grid withRootand safe linkedCardparts.DocsSteps— semantic ordered procedure withRootand independently composableItemparts.DocsTabs— compound tabs powered by Chakra Tabs, with arrow/Home/End keyboard navigation, roving focus, controlled/uncontrolled state, and optional same-page synchronization throughsyncKey. Styling remains owned bychakraDocsTabsand per-instance slot props.DocsApiTable— responsive semantic API-reference table for names, types, defaults, descriptions, and required markers.DocsBadge— neutral metadata badge with an opt-inaccenttone.DocsSidebar— sticky nav list built fromDocsNavItem[], highlighting the active route. Children render above the navigation list. Its direct disclosure props arecollapsible,defaultExpanded,expandedIds, andonExpandedChange, with matchingtriggerSlotProps,indicatorSlotProps, andcontentSlotPropsoverrides. Branch headings become buttons witharia-expandedandaria-controls; linked branches retain their link and add a separately labeled disclosure button. Badge elements expose their value throughdata-badgeandtitle. The legacychildrenrecipe slot remains supported alongside the newtrigger,indicator, andcontentslots.DocsMobileNavigation— compound hamburger/drawer navigation withRoot,Trigger,Content,Header,Title,CloseTrigger,Search,Body, andSidebarparts. The default root composition handles focus, Escape, outside interaction, scroll containment, active-path expansion, route-change closing, and close-on-selection. Use the parts to replace any visual region while retaining the shared state and accessibility behavior.DocsTableOfContents— sticky "On this page" list that tracks the active heading on scroll and smooth-scrolls on click. The active section uses a squareactiveIndicatorslot, which can be overridden in the theme or withactiveIndicatorSlotProps.DocsMobileTableOfContents— disclosure-based mobile heading navigation using the same active-heading and scroll-offset behavior.DocsLayoutincludes it by default when headings are provided; passmobileToc={false}to opt out.DocsSearch— Cmd/Ctrl+K search dialog with keyboard navigation, popular/default results, and collection scoping. Passrecordsfor synchronous local search orsearchProviderfor remote search; the provider takes precedence when both are present. Remote mode sendscollectionId/collectionIds,limit, andpopularLimitto the server, loads popular results on open, debounces typed queries (debounceMs, default 150 ms), and aborts superseded requests.onNavigatehandles both unmodified pointer selection and Enter-key activation; modified clicks retain normal browser behavior. Props:records,searchProvider,debounceMs,collectionId,collectionIds,limit,popularLimit,placeholder,onNavigate,onResultSelect, plusslotProps/triggerSlotProps/inputSlotProps/resultSlotProps.DocsVersionSelect— labeled native select for switching collections/versions. Props:collectionsoroptions,value/defaultValue,onValueChange,includeAll,allValue,allLabel,label,labelHidden, plus slot props.DocsPagination— previous/next links derived from the flattened nav and the currentpage.route. Props:nav,page.MarkdownContent— CommonMark/GFM renderer powered byreact-markdownandremark-gfm, with no Postkit dependency. Supports h1–h6 and Setext headings, nested/ordered/task lists, emphasis, strikethrough, reference links, autolinks, images, footnotes, thematic/hard breaks, responsive tables, quotes rendered asCallout, and fenced/indented code rendered asCodeBlock. Heading anchors agree with filesystem manifests and section search. Raw HTML/JSX is escaped; executable MDX and directives require a separate renderer. Unsafe link/image URLs are omitted. Props includesource,headingPermalinks,getHeadingHref,codeBlockProps,tableLabel, and slot props. Tables scroll horizontally in a labelled, keyboard-focusable region. Style them throughtableContainer,table,tableHead,tableBody,tableRow,tableHeader, andtableCellrecipe slots or corresponding*SlotProps. Images, separators and task checkboxes exposeimage,separator, andtaskCheckboxslots.Callout— bordered note box. Props:type('info' | 'warning' | 'success' | 'danger', default'info'),title,slotProps,children.CodeBlock— ChakraCodeBlock-based code shell with an optional title/language header and configurable copy action, line numbers, wrapping, highlighted lines, size, maximum height, andoutline,subtle, orplainrecipe variant. Props includecode,language,title,copy,lineNumbers,wrap,highlightLines,size,variant,maxHeight,slotProps, andchildren. Copying defaults on; line numbers and wrapping default off.
Hooks and helpers
useDocsConfig()— read the mergedChakraDocsConfig(with default labels applied).createDocsVersionOptions(collections)— map collections toDocsVersionOption[].filterSearchRecordsByCollections(records, collectionIds)— scope search records to a set of collections.createDocsBreadcrumbItems(nav, activeRoute)— return every nav ancestor and the active page for breadcrumb rendering.
Types
ChakraDocsConfig, DocsLabels, DocsAnalyticsCallbacks, DocsLinkProps, DocsLinkComponent, DocsComponentProps, DocsLayoutProps, DocsArticleProps, DocsBreadcrumbsProps, DocsBreadcrumbItem, DocsPageActionsRootProps, DocsPageActionsSize, DocsPageActionProps, DocsPageActionsMenuProps, DocsPageActionsSubmenuProps, DocsPageActionsGroupProps, DocsPageActionsSeparatorProps, DocsPageActionsOpenChangeDetails, DocsPageActionsPositioning, DocsPageActionsPlacement, DocsHeadingPermalinkProps, DocsPageFeedbackRootProps, DocsPageFeedbackValue, DocsPageFeedbackSubmitDetails, DocsCardsRootProps, DocsCardProps, DocsStepsRootProps, DocsStepProps, DocsTabsRootProps, DocsTabsValuePartProps, DocsApiTableProps, DocsApiTableItem, DocsBadgeProps, DocsSidebarProps, DocsSidebarDefaultExpanded, DocsMobileNavigationRootProps, DocsMobileNavigationTriggerProps, DocsMobileNavigationContentProps, DocsMobileNavigationPartProps, DocsMobileNavigationCloseTriggerProps, DocsMobileNavigationSidebarProps, DocsMobileNavigationOpenChangeDetails, DocsTableOfContentsProps, DocsMobileTableOfContentsProps, DocsSearchProps, DocsVersionSelectProps, DocsVersionOption, CalloutProps, CodeBlockProps, MarkdownContentProps, ChakraDocsLayoutConfig, ChakraDocsStickyTop, ChakraDocsCodeBlockConfig, ChakraDocsCodeBlockAdapter, ChakraDocsCodeBlockHighlighter, and related code block types.
Help and contributing
See the project README, open an issue, or read the contribution guidelines. Report vulnerabilities privately through the security policy.
License
MIT
