Guides the practical path from 'we have no design system' or 'we have a mess' to a real, functional design system. Component inventory, design token extraction, headless UI adoption (Radix, React Aria, Headless UI), migration order of operations, and the assessment-to-rollout pipeline. Activate on 'design system from scratch', 'bootstrap design system', 'no design system', 'design system migration', 'headless UI adoption', 'component audit', 'design token extraction', 'design system strategy'. NOT for building specific components once a system exists (use design-system-creator), not for generating token files/configs (use design-system-generator).
Guides the practical path from 'we have no design system' or 'we have a mess' to a real, functional design system. Component inventory, design token extraction, headless UI adoption (Radix, React Aria, Headless UI), migration order of operations, and the assessment-to-rollout pipeline. Activate on 'design system from scratch', 'bootstrap design system', 'no design system', 'design system migration', 'headless UI adoption', 'component audit', 'design token extraction', 'design system strategy'. NOT for building specific components once a system exists (use design-system-creator), not for generating token files/configs (use design-system-generator).
allowed-tools
Read,Write,Edit,Glob,Grep,WebSearch,WebFetch
metadata
{"category":"Design & UX","tags":["design-system","migration","headless-ui","radix","react-aria","design-tokens","component-audit","architecture"],"pairs-with":[{"skill":"design-system-creator","reason":"Creator builds the components after Bootstrap establishes the strategy"},{"skill":"design-system-generator","reason":"Generator outputs token files and configs that Bootstrap defines"},{"skill":"design-accessibility-auditor","reason":"Accessibility audit is step 1 of any design system bootstrap"}]}
The practical guide to going from "we have nothing" (or "we have a mess") to a functional design system. This is not about building a component library from scratch in isolation — it is about assessing what exists, extracting what works, choosing the right foundations, and migrating incrementally without breaking production.
When to Use
Use for:
Greenfield projects that need a design system from day one
Existing apps with inconsistent styling and no shared components
Migration from one component library to another (e.g., MUI to Radix)
Extracting a design system from a mature but unsystematic codebase
Score 5-10: You are in emergency mode. Start with tokens + one component.
Score 11-18: You have something to work with. Systematic migration possible.
Score 19-25: You need polish, not a rewrite.
Phase 1: Foundations (Week 1-2)
Design Tokens First
Tokens are the foundation everything else builds on. Define them before touching components.
This is the highest-leverage decision. Choose wrong, and you rewrite everything later.
Comparison Matrix (2025-2026)
Criteria
Radix UI
React Aria
Headless UI
Ark UI
Base UI (MUI)
Component count
28
43
10
30+
20+
API style
Compound components
Hooks + Components
Compound components
Compound components
Hooks
Accessibility
Very good
Best-in-class
Good
Very good
Good
Styling freedom
Full (unstyled)
Full (unstyled)
Full (unstyled)
Full (unstyled)
Full (unstyled)
React Server Comp.
Partial
Yes
Partial
Yes
Partial
Animation support
data-state attrs
Built-in transitions
Transition component
data-state attrs
Minimal
Bundle size (Dialog)
~8KB
~12KB
~5KB
~10KB
~7KB
Ecosystem
shadcn/ui, Radix Themes
Adobe Spectrum
Tailwind ecosystem
Panda CSS
Joy UI
Documentation
Excellent
Very good
Good
Good
Good
Framework support
React only
React only
React + Vue
React + Vue + Solid
React only
Decision Framework
Do you need Vue/Solid support?
├── Yes → Ark UI or Headless UI
└── No → Continue
│
Do you need maximum accessibility (gov, enterprise, WCAG AAA)?
├── Yes → React Aria
│ (strictest ARIA implementation, Adobe-backed)
└── No → Continue
│
Do you want the largest pre-built ecosystem (shadcn/ui)?
├── Yes → Radix UI
│ (shadcn/ui is built on Radix, largest component community)
└── No → Continue
│
Do you need the fewest dependencies possible?
├── Yes → Headless UI (smallest, Tailwind team)
└── No → Radix UI (safe default, best DX)
The shadcn/ui Question
shadcn/ui is not a library — it is a collection of copy-paste components built on Radix + Tailwind. It deserves special consideration:
Tailwind-only (if you use CSS Modules or styled-components, you cannot use it)
Updates are manual (copy-paste means no npm update)
Verdict: If you are starting from zero with React + Tailwind, shadcn/ui is the fastest path to a functional design system. You can customize everything later because you own the source.
# Bootstrap shadcn/ui into an existing project
npx shadcn-ui@latest init
# Add components as needed
npx shadcn-ui@latest add button input card dialog dropdown-menu \
tabs tooltip popover command separator badge
Phase 3: Component Priority Order (Week 2-4)
Do NOT build all components at once. Follow this priority order based on usage frequency and impact.
Step 1: Create new <Button> component in design system
Step 2: Import it alongside old buttons
Step 3: Replace old buttons one page at a time
Step 4: When all old buttons replaced, delete old code
Step 5: Repeat for next component
Track these to know if the design system is working:
Metric
Target
How to Measure
Component coverage
80%+ of UI uses DS components
grep for DS imports vs raw HTML
Token compliance
90%+ of colors/spacing from tokens
grep for hardcoded values
Accessibility score
0 axe violations per page
Storybook a11y addon, Lighthouse
Developer satisfaction
4+/5 in quarterly survey
Internal survey
Time to build new page
50% reduction
Track sprint velocity
Common Pitfalls
Pitfall: Building for Figma First
Designers want pixel-perfect Figma components before code exists. This creates a waterfall where code never matches design and both drift. Build code and Figma in parallel. Code is the source of truth. Figma is a communication tool.
Pitfall: Over-Abstracting Day One
Creating a <Box> component that wraps every possible CSS property. Creating a <Text> component with 47 props. Start concrete, abstract when patterns emerge. You cannot predict your abstractions before building three real pages.
Pitfall: No Migration Path
Building a beautiful new design system that sits in a /packages/ui folder unused because there is no plan for migrating existing code. Plan migration before building components. The best design system is the one that gets adopted.
Pitfall: Choosing by Hype
Picking a headless UI library because it was trending on Twitter. Choose by your team's constraints: framework, accessibility requirements, bundle budget, component coverage needs.
Pitfall: Skipping the Audit
Jumping straight to building components without understanding what already exists. You will build things that already exist in three variants, miss patterns that work, and create migration confusion. Phase 0 is not optional.
Anti-Patterns
Anti-Pattern: The God Theme Object
A single 2000-line theme file with every possible value. Instead, use layered tokens: primitive (raw values) → semantic (purpose-named) → component (component-specific overrides).
Anti-Pattern: Wrapping a Full Library
Taking MUI/Chakra/Ant Design and wrapping every component with your own props "in case we switch later." You will not switch. Use the library directly or build your own. The wrapper adds bugs and zero value.
Anti-Pattern: Design System as a Separate Team
A "design system team" that builds components in isolation while product teams wait. Design system work should be embedded in product work. Build the component when a product team needs it, not before.
Anti-Pattern: Enforcing Before Earning
Mandating design system usage before the system is good enough to want. If developers prefer writing raw CSS over using your components, the components need to be better, not the developers.
Quality Checklist
Component inventory completed with variant count per component
Design tokens extracted from existing codebase (colors, spacing, typography)
Headless UI library selected with documented rationale
Tier 1 components (Button, Input, Dialog, Dropdown) built and documented
Migration strategy defined (strangler fig, not big-bang rewrite)
ESLint rules warn on deprecated component imports
Storybook running with at least default + variants stories per component
Dark mode support via semantic token layer
Zero axe-core violations in Storybook accessibility addon
At least one full page migrated end-to-end as proof of concept
Migration tracking visible to the team (dashboard or spreadsheet)