Willow Design System – Our Hackathon Journey 🚀

🌱 Inspiration & "A-ha!" Moment

While building a Bolt-based healthcare app three weeks before the hackathon, our team hit a brick wall: UI chaos.

  • Buttons drifted off-brand after every merge
  • Designers ping-ponged Figma links nobody opened
  • Accessibility audits flared red warnings minutes before demos

After burning four hours reconciling three button variants, someone blurted:

"We're not saving patients—we're playing CSS whack-a-mole!"

That frustration crystallised into a vision: a drop-in component registry for Bolt that stamps out design drift before it starts.

📚 What We Learned

  • Design ≠ pixels – it's process. A shared component registry is the real single source of truth
  • DevX drives adoption. If setup isn't ridiculously easy, nobody installs it
  • Accessibility early > fixes late. Baking WCAG-AA colours and keyboard navigation into every primitive costs pennies up-front and saves dollars down-stream
  • Bolt's plugin surface is friendlier than we thought. Its Vite-based scaffold can be extended in ~50 lines of code

🛠️ How We Built Willow

Phase Key Actions Time
Scaffolding Forked shadcn/ui, themed it with Willow palette, codified tokens in Tailwind config 1 day
CLI Prototype Wrote a Node script to detect Bolt projects, copy templates, and inject deps 8 hrs
Component Registry Added versioned @willow/core & @willow/react packages; generated React/TS types 1 day
Storybook & Docs Auto-generated MDX from prop types 6 hrs
Accessibility Pass Ran Axe & Lighthouse; fixed contrast, focus rings, ARIA labels 4 hrs
"Willow CLI" Polish Added progress bar, emoji logs, error handling, and rollback on failure 1 day

Stack: React • TypeScript • Tailwind CSS • shadcn/ui • Vite • Commander.js • Turborepo

⚔️ Challenges We Faced

Challenge What Went Wrong How We Solved It
Bolt's Package Sandbox Initial postinstall failed—Bolt blocked FS writes outside /app Used Bolt's workspace API to write files in src/ only; replaced symlinks with copies
Theme Overlap Tailwind's default colours clashed with Willow palette Disabled core colour plugin, generated custom classes with tailwind-merge
DX vs. Bundle Size Shipping whole registry ballooned JS by 80 kB Implemented tree-shakable barrel exports and sideEffects: false
Accessibility Debt Dropdown component lacked keyboard support Refactored to headless pattern + roving tabindex; added Jest a11y tests

Built With

  • bolt
  • commander.js
  • shadcn
Share this project:

Updates