CodeBlock
Server-rendered, syntax-highlighted code block with a language-label header and a copy button. Dual-theme via Shiki — same HTML for light + dark.
Install command
pnpm dlx @hex-core/cli add submit-buttonTypeScript snippet
import { Button } from "@hex-core/components";
export function SubmitButton({ pending }: { pending: boolean }) {
return (
<Button type="submit" disabled={pending}>
{pending ? "Saving…" : "Save changes"}
</Button>
);
}Multi-snippet — component + registry entry + install
import { Button } from "@hex-core/components";
export function SubmitButton({ pending }: { pending: boolean }) {
return (
<Button type="submit" disabled={pending}>
{pending ? "Saving…" : "Save changes"}
</Button>
);
}{
"name": "submit-button",
"category": "form",
"props": [
{ "name": "pending", "type": "boolean", "required": true }
]
}pnpm dlx @hex-core/cli add submit-buttonInstallation
pnpm dlx @hex-core/cli add code-blockInline TS sample
Explicit language overrides label inference.
<CodeBlock language="tsx" code={`<Button>Click</Button>`} />API Reference
| Prop | Type | Default | Description |
|---|---|---|---|
coderequired | string | — | The code to display. Plain text — no markdown fences. |
label | string | — | Header label (e.g. "pnpm", "tsx"). Inferred from `language` if omitted. |
language | "bash" | "ts" | "tsx" | "js" | "jsx" | "json" | "css" | "html" | "md" | "py" | "text" | — | Shiki grammar key. Overrides inference from `label`. |
themes | object | [object Object] | Override the default theme pair. Keys: `light`, `dark` — values are Shiki theme IDs. |
className | string | — | Additional CSS classes on the outer card. |
AI Guidance
When to use
Render any code snippet in docs, copy-to-clipboard install commands, or static AI chat output where server rendering is acceptable. Pair with Markdown's `components.pre` override to take over markdown code fences.
When not to use
Don't use for streaming chat where the code grows mid-render — async Server Components can't update token-by-token. Use Streamdown's built-in client CodeBlock for that.
Common mistakes
- Passing markdown-fenced code (with ```) — strip the fences first
- Forgetting that this is async — must be awaited or rendered as RSC
- Using a Shiki theme that isn't bundled — fails with a runtime fetch error
Accessibility
Highlighted output is plain text inside a `<pre>` — screen readers read it normally. The copy button has its own `aria-label`. Add a meaningful `aria-label` on the wrapper if the label alone isn't descriptive.
Token budget: 320
Verified against @hex-core/components@1.12.0