How I Actually Build Design Systems

(It’s Less Linear Than It Sounds)

person writing on white paper

Most design system articles make the work look very tidy. Foundations first. Components next. Patterns after that. Everything neatly stacked.✨

That has never been my experience.

In reality, it’s a loop.🔁 You define tokens, then a real screen breaks them. You fix the tokens, then a component feels off. You adjust the component, and suddenly a layout you thought was done doesn’t hold up anymore. You’re constantly moving back and forth, and at some point you stop expecting things to be final.

Foundations are still where I start. Color, spacing, typography - all of it matters.🎨 But I no longer treat those decisions as permanent. Real product screens have a way of humbling early assumptions. Dense tables, long labels, accessibility needs - they show you very quickly where your “clean” system isn’t as flexible as you thought.

For a long time, I designed components in isolation. They looked great on their own. Then I dropped them into dashboards, long forms, or data-heavy screens and things started falling apart.😬 Spacing felt wrong. Hierarchy got muddy. States were missing. That was frustrating at first, but it was also useful. Those screens did a better job of testing the system than any checklist ever could.

Something else I didn’t expect to matter as much as it does is naming. Bad names slow people down.🐌 They make designers hesitate and engineers work around the system instead of with it. Good names don’t draw attention to themselves. They just make sense. Getting there takes longer than it should, and it’s rarely perfect on the first try.

I’ve also learned to be careful about standardizing too early. Seeing the same pattern twice doesn’t automatically mean it should become a component. Sometimes things look similar but behave differently enough that forcing them together creates more confusion later. Letting some patterns stay loose has actually made the system easier to use.

Documentation comes after all of that.📝 Not because it’s unimportant, but because documenting something that hasn’t settled yet is a waste of time. Once components are used in enough real situations, the guidance writes itself. What works. What breaks. What people keep getting wrong.

Working closely with engineering changed how I think about the system as well.🤝 When design and code drift apart, people stop trusting both. When they stay aligned, the system starts to feel like shared ground instead of a handoff artifact. That alignment takes effort, but it’s worth it every time.

At some point, I stopped trying to make the system complete. Completeness sounds nice, but it’s unrealistic. What matters more is covering the common problems well and being honest about the gaps. A system that admits its limits is easier to extend than one that pretends to solve everything.

If the system is doing its job, it doesn’t get noticed much.👀 People just use it. Fewer questions. Fewer workarounds. Less rework. That’s usually how I know it’s working.