Skip to content

Example Guide

This page is a quick reference for writing content on this site: markdown, Kroki diagrams, tabbed blocks, interactive tables, and code snippets.

Text can be bold, italic, or strikethrough.

Custom blocks configured on this site:

Advantage callout (:::success).

Disadvantage callout (:::warn).

Info callout (:::info).

Fence with the diagram language (or kroki type=…). These render at build time.

d2

plantuml

For architecture diagrams authored in Draw.io, paste the uncompressed XML into a diagramsnet block.

diagramsnet

Also works: mermaid, graphviz, excalidraw, structurizr, diagramsnet, c4 / c4plantuml, vega / vegalite, goat, and the types below. Point PUBLIC_KROKI_SERVER_URL at a core that has the diagramsnet companion enabled.

Fence with the language in Fence. Friendly names c4, vega-lite, and drawio are remapped to Kroki’s API types.

CategoryDiagramFence
UMLBlock diagramblockdiag
UMLSequence diagramplantuml, mermaid, seqdiag
UMLActivity diagramplantuml, mermaid, actdiag
UMLNetwork diagramnwdiag
UMLUse case diagramplantuml
UMLClass diagramplantuml, mermaid
UMLState diagramplantuml, mermaid
UMLObject diagramplantuml
UMLDeployment diagramplantuml
UMLTiming diagramplantuml, wavedrom
UMLEntity relationship diagramerd, plantuml, mermaid
C4C4 context diagramc4plantuml / c4
C4C4 container diagramc4plantuml / c4
C4C4 component diagramc4plantuml / c4
C4Software architecture (Structurizr DSL)structurizr
C4System landscape diagramstructurizr
C4System context diagramstructurizr
C4Container diagramstructurizr
C4Component diagramstructurizr
C4Dynamic diagramstructurizr
C4Deployment diagramstructurizr
DiagramObject oriented graphgraphviz / dot, d2
DiagramWork breakdown structureplantuml
DiagramMind map diagramplantuml, mermaid
DiagramGantt diagrammermaid, plantuml
DiagramDitaa diagramditaa
DiagramPacket diagrampacketdiag
DiagramRack diagramrackdiag
DiagramDigital timing diagram (waveform)wavedrom
DiagramBPMN diagrambpmn
DiagramBytefield diagrambytefield
DiagramHDL component diagramsymbolator
DiagramExcalidrawexcalidraw
Diagramdiagrams.netdiagramsnet / drawio
DiagramWireVizwireviz
DiagramGoATgoat
VisualizationBar chartsvegalite / vega
VisualizationLine and area chartsvegalite / vega
VisualizationCircular chartsvegalite / vega
VisualizationScatter plotsvegalite / vega
VisualizationDistributionsvegalite / vega
VisualizationGeographic mapsvegalite / vega
VisualizationTree diagramsvegalite / vega
VisualizationNetwork diagramsvegalite / vega
VisualizationHeatmapsvegalite / vega
VisualizationWord cloudsvegalite / vega
VisualizationBeeswarm plotsvegalite / vega

Use a renderhtml fence when the diagram is authored as HTML/CSS/SVG and must be rendered, not shown as source. A normal html fence stays a highlighted code block.

Client
API
Database
SVG diagram

Starlight content styles are skipped inside the block (not-content), so inner layout, lists, and headings keep the diagram’s own CSS.

Use this for any markdown — tables, lists, prose — not just code. Outer fences need more colons than inner ones so nesting parses correctly.

DirectiveRole
:::::group-container … :::::Outer tab group
::::group-item[Title] … ::::One tab (+ body)
{active} on an itemDefault selected tab (first if omitted)

Example (outer :::::, items ::::):

Short note for the Alpha tab.

  • One
  • Two

Content for Beta. Nested code or tables go here.

See Company Apply for a real page: level tabs (SDE 1/2/3) each holding a large table.

Container directives close at the first matching fence of the same length. Nesting pattern:

:::::outer
::::mid
:::inner
…
:::
::::
:::::

Rule: outer fences use more colons than inner ones.

Wrap a normal markdown table in :::data-table to add:

  • Search across all columns
  • Sort any column (click the header; chevrons show direction)
  • Pagination (rows per page control)

Links inside cells (e.g. company names) are preserved.

CompanyCategoryLocationsEst. Comp (LPA)
AcmeProductRemote40–60L
GlobexHFTBengaluru55–80L
InitechFintechMumbai30–45L
UmbrellaServicesPan-India18–28L

Attributes on the opening fence:

AttributeDefaultEffect
searchableonSet searchable=false to hide search
sortableonSet sortable=false to disable column sort
pagingonSet paging=false for a full list
perPage25Rows per page (e.g. perPage=50)
:::data-table{perPage=50}
| Name | Score |
|------|-------|
| A | 10 |
:::

Numeric-looking columns (headers matching comp, salary, ctc, lpa, package) sort by the lower bound of ranges like 140–220L.

Put data-table inside group-item with enough colons:

:::::group-container
::::group-item[SDE 3]{active}
:::data-table
| Company | …
| …
:::
::::
:::::

Code fences use Expressive Code. Meta options go after the language on the opening fence.

Wrap multiple fences in :::group (alias :::code-group) to show them as tabs instead of a long scroll. Tab labels use each fence’s title="…", or the language name.

abc.js
export function greet(name) {
return `Hello, ${name}!`;
}
xyz.java
public class Greeter {
public static String greet(String name) {
return "Hello, " + name + "!";
}
}
greet.ts
export function greet(name: string): string {
return `Hello, ${name}!`;
}

You can also label tabs with bracket meta: ```js [abc.js].

src/lib/greet.ts
export function greet(name: string) {
return `Hello, ${name}!`;
}
Install deps
bun install
bun run build

Line numbers are on by default for js, ts, html, java, and python. Toggle per block:

console.log("line 1");
console.log("line 2");
console.log("line 3");
// No gutter numbers on this block
console.log("still highlighted");
// Continues as if this file started at line 40
export const PORT = 4321;

Neutral highlight — draw attention without implying add/remove.

```js {2-3} showLineNumbers
function add(a, b) {
const sum = a + b;
return sum;
}

Explicit form:

const answer = 42;
console.log(answer);

Green = inserted, red = deleted — useful for before/after diffs.

function total(items) {
let sum = 0;
for (const item of items) sum += item.price;
for (const item of items) sum += item.price * item.qty;
return sum;
}

Labeled markers:

type User = {
id: string;
name: string;
email: string;
role: "admin" | "member";
};

Or use a classic diff fence:

export function createUser(input) {
return db.insert(input);
const user = validate(input);
return db.insert(user);
}

Mark words or phrases inside lines:

// TODO: handle empty list
const bug = list[0];
const fixed = list.at(0);

Regular expressions also work: mark=/handle\w+/.

Hide boilerplate; readers expand when needed.

4 collapsed lines
import { createServer } from "node:http";
import { readFile } from "node:fs/promises";
import path from "node:path";
import { fileURLToPath } from "node:url";
export async function handler(req, res) {
res.writeHead(200, { "Content-Type": "text/plain" });
res.end("ok");
}
3 collapsed lines
createServer(handler).listen(3000);
console.log("listening on :3000");
process.on("SIGTERM", () => process.exit(0));
const url = "https://api.example.com/v1/users?include=profile,settings&sort=createdAt&order=desc&limit=50";

Most meta flags can be combined on one fence:

```ts title="cache.ts" showLineNumbers mark={5-7} collapse={1-2}
cache.ts
2 collapsed lines
import type { Cache } from "./types";
import { redis } from "./client";
export async function getCachedUser(id: string): Promise<Cache | null> {
const key = `user:${id}`;
const raw = await redis.get(key);
return raw ? JSON.parse(raw) : null;
}
MetaEffect
:::group … :::Tabbed code fences
:::code-groupSame as :::group
:::::group-container + ::::group-item[Title]Tabbed content (markdown body)
group-item[…]{active}Default open content tab
:::data-table … :::Sortable / searchable / paged table
:::data-table{perPage=50}Rows per page (and other flags above)
Language renderhtmlRender HTML/SVG (not a code block)
Language htmlHighlighted HTML source
title="file.ts"Filename / code-tab title
frame="terminal"Terminal-style frame
showLineNumbers / =falseToggle line numbers
startLineNumber=NStart numbering at N
{2,4-6} or mark={…}Neutral line highlight
ins={…} / del={…}Added / removed lines
ins={"label":3-4}Labeled insert/delete
"phrase" / mark="phrase"Inline text highlight
collapse={1-5,10-12}Collapsible ranges
wrapSoft-wrap long lines
Language diff+ / - line prefixes