Skip to content

Phase 2 - Design System & Tokens

  • Tier: Foundation (Phase 2 of 12)
  • Scope: Essential — every project completes this phase (scope labels follow ADR-033)
  • Duration: 1-2 days
  • Dependencies: Phase 0-1 completed
  • Deliverables: Design tokens, Tailwind config, CSS architecture, accessibility primitives
  • Code examples: Phase 2 - Code Examples
  • Content architecture defined
  • TypeScript configured
  • Tailwind CSS installed
  • Design requirements gathered
StepTaskScopeNotes
2.01Define color paletteEssentialHSL for flexibility
2.02Set up typography scaleEssentialFluid type optional
2.03Create spacing systemEssentialConsistent scale
2.04Define radius tokensEssentialBorder radius system
2.05Add shadow systemEssentialElevation tokens
2.06Create motion tokensEssentialTransitions/animations (surface them via @theme inline in src/styles/global.css so utilities like duration-fast and ease-out exist)
2.07Set up dark modeEssentialCSS variables approach
2.08Add a11y primitivesEssentialFocus, contrast
2.09Configure TailwindEssentialExtend with tokens
2.10Create token buildEssentialJSON to CSS/Tailwind
2.11Document usageEssentialGuidelines for devs
2.12Add WCAG checksEssentialScript to iterate all semantic text/background pairs for WCAG AA

Tailwind CSS v4 is stable and provides significant improvements over v3, including better performance, enhanced design token integration, and improved developer experience.

Key Tailwind v4 Benefits:

  • Better Performance: Faster build times and smaller CSS output
  • Enhanced Design Tokens: Native CSS variables support
  • Improved DX: Better IDE support and error messages
  • Migration Path: Clear upgrade path from v3 configurations

Current Implementation: The project pins the current Tailwind v4 release (exact version in versions.json), so you get the latest stable v4 patches while maintaining compatibility. Configuration is CSS-first: there is no tailwind.config.ts; tokens are mapped in src/styles/global.css via @theme inline.

Current Approach: The project currently leverages Astro’s built-in <Image> component for image optimization. This component, often paired with the Sharp.js library under the hood (as per default Astro configurations), handles tasks like resizing, format conversion (e.g., to AVIF, WebP), and generating responsive srcset attributes. This is generally sufficient for optimal performance and image handling at the current scale.

Future Consideration: Image CDN Fallback/Enhancement While the built-in solution is robust, if the project experiences a significant spike in traffic, or if the requirements for delivering numerous device-specific image variants become more complex, integrating a dedicated image CDN should be considered.

Services like Cloudflare Images (or similar offerings like Cloudinary, Imgix) provide benefits such as:

  • Real-time Resizing and Optimization: Images can be transformed on-the-fly based on request parameters or device characteristics, reducing the need to pre-generate all variants.
  • Global CDN Delivery: Faster image delivery worldwide.
  • Advanced Features: Watermarking, format negotiation, and more sophisticated art direction capabilities.

This is not an immediate requirement but a potential future enhancement to keep in mind for scalability and advanced image manipulation needs. The decision to integrate such a service would involve cost considerations and a re-evaluation of the image delivery pipeline.

  1. Hardcoded Colors: Using hex values directly in components

    • Solution: Always use token classes or CSS variables
  2. Missing Dark Mode: Not considering dark mode from start

    • Solution: Use semantic tokens that work in both modes
  3. Poor Contrast: Not validating WCAG compliance

    • Solution: Run contrast checks on all color combinations
  4. Motion Sickness: Not respecting prefers-reduced-motion

    • Solution: Add motion guards in global CSS
  • Color palette defined with semantic naming
  • Typography scale configured
  • Spacing system consistent
  • Border radius tokens defined
  • Shadow system created
  • Motion tokens established
  • Dark mode functioning
  • Accessibility utilities created
  • Tailwind extended with tokens
  • Token build script working
  • WCAG contrast validated
  • Usage guidelines documented

If design system needs major changes:

  1. Token Updates:

    Terminal window
    # Keep old tokens
    cp tokens/base.json tokens/base.json.backup
    # Rebuild tokens/dist/ (scripts/src/build-tokens.ts ships with the starter)
    pnpm run tokens:build
    # Validate contrast in light and dark mode (scripts/src/validate-contrast.ts)
    pnpm run design:validate
  2. Tailwind Config Issues:

    • Revert the @theme inline token mapping in src/styles/global.css
    • Clear Tailwind cache
    • Rebuild CSS
  3. Breaking Changes:

    • Use CSS variables for gradual migration
    • Keep old classes temporarily
    • Document deprecations
  • tokens/base.json - Core design tokens (palette, type, spacing, radius, shadow, motion)
  • tokens/semantic.json - Role tokens with light value / dark overrides
  • src/styles/global.css - Global styles and Tailwind v4 CSS-first configuration (@theme inline)
  • scripts/src/build-tokens.ts - Token build (pnpm run tokens:build → tokens/dist/)
  • scripts/src/validate-contrast.ts - WCAG AA gate (pnpm run design:validate)
  • “Create accessible color palette with WCAG AA compliance”
  • “Set up Tailwind with design tokens”
  • “Implement dark mode with CSS variables”
  • “Create fluid typography scale”
  • Brand colors if any
  • Typography preferences
  • Motion preferences
  • Accessibility requirements