Spec Reference
Every required field, every recommended section, every YAML rule.
What’s in a DESIGN.md
A DESIGN.md is a standard Markdown file. The top of the file is YAML frontmatter (between --- delimiters). Below the closing --- is a prose Markdown body.
---
# YAML frontmatter: machine-readable token bundle
name: Stripe
spec: webdesignhot/0.1
colors:
bg: '#ffffff'
...
---
# Stripe
Prose body: 15 canonical sections covering visual theme,
color roles, typography usage, component patterns, motion,
voice, lineage, and agent prompt guide.
The frontmatter is what the CLI, MCP, and export commands read. The prose body is what coding agents read during generation — it provides the semantic context that token values alone don’t convey.
Every token documented in this reference produces output like the above. The frame is rendered from Linear's DESIGN.md frontmatter — no hand-tweaked CSS.
Required frontmatter fields
| Field | Type | Example |
|---|---|---|
name | string | Stripe |
tagline | string | Infrastructure for the internet economy |
spec | string | webdesignhot/0.1 |
colors | object | see colors block |
typography | object | see typography block |
Every valid DESIGN.md must have all five. design-md lint reports an error if any are missing.
Recommended frontmatter
These fields are not required but are present in most catalog entries and improve agent output quality.
| Field | Type | Purpose |
|---|---|---|
categories | string[] | Taxonomy — ['saas', 'fintech'] |
tags | string[] | Freeform labels — ['dark-mode', 'minimal'] |
source_url | string | Production URL the tokens were extracted from |
lineage | object | Brand influences; see lineage block |
aliases | object | Tailwind/shadcn role mapping; see aliases block |
radii | object | Corner-radius scale |
spacing | object | Spacing scale |
shadow | object | Box-shadow definitions |
motion | object | Easing and duration tokens |
breakpoints | object | Viewport breakpoints in px |
components | object | Per-component token overrides |
dark | object | Dark-mode palette (single-theme entries) |
themes | object | Multi-theme config (multi-theme entries) |
colors block
The colors object maps semantic role names to hex values. Single-theme entries have a flat map:
colors:
bg: '#ffffff'
surface: '#f6f9fc'
border: '#e6ebf1'
text: '#0a2540'
text-dim: '#425466'
text-faint: '#8898aa'
brand: '#635bff'
brand-alt: '#0055de'
on-brand: '#ffffff'
success: '#09825d'
warning: '#b5830a'
danger: '#cd3d64'
Core roles every entry should define:
| Role | Meaning |
|---|---|
bg | Page/canvas background |
surface | Card, panel, elevated surface |
border | Default border color |
text | Primary body text |
text-dim | Secondary/muted text |
brand | Primary interactive color (buttons, links, focus rings) |
on-brand | Text/icon color on a brand-colored surface |
Semantic state roles (optional but recommended):
| Role | Use |
|---|---|
success | Positive confirmation states |
warning | Caution, degraded states |
danger | Destructive actions, error states |
Multi-theme entries nest palettes by theme name — see the themes block.
typography block
The typography object has named style slots. Each slot accepts family, size, weight, lineHeight, and letterSpacing:
typography:
display:
family: '"Sohne Kraftig", -apple-system, sans-serif'
weight: '500'
letterSpacing: '-0.025em'
body:
family: '"Sohne Buch", -apple-system, sans-serif'
size: '16px'
weight: '400'
lineHeight: '1.6'
mono:
family: '"Sohne Mono", "Fira Code", monospace'
size: '13px'
lineHeight: '1.5'
scale:
xs: '12px'
sm: '14px'
base: '16px'
lg: '18px'
xl: '20px'
'2xl': '24px'
'3xl': '30px'
'4xl': '36px'
The three named slots (display, body, mono) are expected. scale is a flat size map — agents use it when generating typography utilities.
radius block
Corner-radius scale. Values are CSS length strings:
radii:
none: '0px'
sm: '4px'
md: '8px'
lg: '12px'
xl: '16px'
full: '9999px'
Most entries define sm, md, lg. full is used for pill buttons and avatar circles.
spacing block
Base spacing scale. Values are numbers (pixels) or CSS strings:
spacing:
'1': '4px'
'2': '8px'
'3': '12px'
'4': '16px'
'5': '20px'
'6': '24px'
'8': '32px'
'10': '40px'
'12': '48px'
'16': '64px'
Keys follow Tailwind’s numeric convention so agents can map them to utility classes directly.
shadow block
Box-shadow definitions by elevation level:
shadow:
sm: '0 1px 2px rgba(0,0,0,0.06)'
md: '0 4px 16px rgba(0,0,0,0.08), 0 1px 3px rgba(0,0,0,0.04)'
lg: '0 16px 48px rgba(0,0,0,0.12), 0 4px 12px rgba(0,0,0,0.06)'
focus: '0 0 0 3px rgba(99,91,255,0.25)'
focus is a special role — it defines the keyboard focus ring color. Agents use it for :focus-visible styles.
motion block
Easing curves and duration tokens in milliseconds:
motion:
ease: 'cubic-bezier(0.4, 0, 0.2, 1)'
ease-in: 'cubic-bezier(0.4, 0, 1, 1)'
ease-out: 'cubic-bezier(0, 0, 0.2, 1)'
duration-fast: 150
duration-standard: 240
duration-slow: 320
reduced-motion: 'respects prefers-reduced-motion: reduce'
ease is the general-purpose curve for hover/focus. duration-fast covers micro-interactions; duration-standard covers panel opens; duration-slow covers dialog entrances.
breakpoints block
Viewport widths in pixels:
breakpoints:
sm: 640
md: 768
lg: 1024
xl: 1280
2xl: 1440
Keys match Tailwind’s default names. Agents use these when writing @media queries or Tailwind responsive prefixes.
components block
Per-component token overrides. Each key is a canonical component slot name:
components:
button-primary:
bg: '#635bff'
text: '#ffffff'
radius: '6px'
font-weight: '500'
padding: '10px 18px'
button-secondary:
bg: 'transparent'
border: '#e6ebf1'
text: '#0a2540'
radius: '6px'
card:
bg: '#ffffff'
border: '#e6ebf1'
radius: '8px'
shadow: '0 4px 16px rgba(0,0,0,0.08)'
padding: '24px'
input:
bg: '#ffffff'
border: '#e6ebf1'
border-focus: '#635bff'
radius: '6px'
padding: '10px 14px'
font-size: '15px'
badge:
radius: '4px'
font-size: '12px'
font-weight: '500'
padding: '2px 8px'
Canonical component slots: button-primary, button-secondary, button-ghost, card, input, select, checkbox, badge, tag, tooltip, dialog, nav, nav-item, sidebar, table, table-row.
Slots are not exhaustive — add any component your design system defines. The naming convention is kebab-case.
lineage block
Documents brand influences and design heritage. Agents use this when generating prose commentary:
lineage:
summary: >
Clean Swiss-modernist roots filtered through SF tech minimalism.
Heavy Dieter Rams influence — purpose-first, no decoration that doesn't
serve the function.
influences:
- name: Swiss International Style
role: Grid discipline, typographic hierarchy, white space
url: https://en.wikipedia.org/wiki/International_typographic_style
- name: Dieter Rams
role: Ten principles of good design; form follows function
url: https://en.wikipedia.org/wiki/Dieter_Rams
- name: Linear
role: Inspiration for tight spacing and monochromatic neutrals
url: https://linear.app
influences entries are objects with name, role, and url. The url must be a valid absolute URL — design-md lint validates this. Internal references like url: "see source_url" will fail validation.
aliases block
Maps shadcn/ui and Tailwind semantic role names to this design’s token names:
aliases:
# shadcn/ui → design.md role
background: bg
foreground: text
primary: brand
primary-foreground: on-brand
secondary: surface
secondary-foreground: text-dim
muted: surface
muted-foreground: text-faint
border: border
input: border
ring: brand
destructive: danger
destructive-foreground: on-brand
This lets design-md export --to shadcn produce a globals.css that maps shadcn’s CSS variables to the brand’s actual tokens. Keys on the left are shadcn/Tailwind names; values on the right are keys in the colors block.
themes block
Multi-theme entries nest palettes under colors by theme name, and declare a themes config block:
themes:
default: light
available: [light, dark, high-contrast]
switch-via: 'data-theme attribute on <html>; persisted in localStorage'
colors:
light:
bg: '#ffffff'
text: '#0f172a'
brand: '#7c3aed'
surface: '#f8fafc'
border: '#e2e8f0'
on-brand: '#ffffff'
dark:
bg: '#0f0f0f'
text: '#f8fafc'
brand: '#a78bfa'
surface: '#1a1a1a'
border: '#2a2a2a'
on-brand: '#0f0f0f'
high-contrast:
bg: '#000000'
text: '#ffffff'
brand: '#facc15'
surface: '#111111'
border: '#444444'
on-brand: '#000000'
Single-theme entries with a dark mode use a flat colors block plus a separate dark block (not nested):
colors:
bg: '#fafafa'
text: '#0a0a0a'
brand: '#16a34a'
on-brand: '#ffffff'
dark:
bg: '#0a0a0a'
surface: '#141416'
text: '#ededed'
brand: '#22c55e'
on-brand: '#0a0a0a'
The 15-section Markdown body
Below the closing ---, every catalog entry has a prose body with these 15 canonical sections in order:
| # | Section heading | Contents |
|---|---|---|
| 1 | Visual Theme & Atmosphere | Overall mood, aesthetic category, what first impression the design creates |
| 2 | Color Palette & Usage | Role-by-role breakdown of colors with usage rules and frequency guidance |
| 3 | Typography System | Font choices, size scale, weight hierarchy, when to use display vs body vs mono |
| 4 | Component Styling Patterns | How buttons, cards, inputs, badges look and behave — what distinguishes them |
| 5 | Layout & Spacing | Grid approach, container widths, density, whitespace philosophy |
| 6 | Iconography | Icon style (outline/filled/duotone), stroke weight, sizing conventions |
| 7 | Motion & Animation | Speed, easing, what gets animated vs what stays static |
| 8 | Imagery & Media | Photography style, illustration treatment, video usage |
| 9 | Accessibility | Contrast ratios, keyboard nav patterns, reduced-motion support, ARIA habits |
| 10 | Voice & Tone | Writing style, length, vocabulary, what to avoid |
| 11 | Dark Mode | How the dark variant changes mood, which tokens shift, what stays the same |
| 12 | Lineage & Influences | Where the design came from, what it borrows from, what it rejects |
| 13 | Do’s & Don’ts | Concrete dos and don’ts — specifics, not generic advice |
| 14 | Agent Prompt Guide | How an AI agent should apply this design system — what to prioritize, what traps to avoid |
| 15 | Quick Reference | Compact token cheat-sheet for scanning at a glance |
Sections don’t need to be long — three to five paragraphs each is normal. The value is specificity: “use brand only on interactive elements” is useful; “use color intentionally” is not.
Schema validation
design-md lint validates a DESIGN.md against the webdesignhot/0.1 schema:
design-md lint stripe.design.md
What it checks:
- Required fields present (
name,tagline,spec,colors,typography) specvalue is a recognized version stringcolorshas at minimumbg,text,brand,on-brandlineage.influences[].urlvalues are valid absolute URLstypographyhas at minimum one named slot (bodyordisplay)- No unknown top-level keys that could indicate a typo (warns, not errors)
- YAML parses without errors
Exit code 0 = valid. Exit code 1 = one or more errors. Errors print to stderr; clean output prints to stdout (useful for CI piping).
# CI usage
design-md lint DESIGN.md && echo "valid" || exit 1