Evans argues that Tailwind became a way to avoid learning CSS itself, and that avoidance was making her worse at building interfaces. She didn't leave because Tailwind is bad software, but because the abstraction became a substitute for understanding — and understanding is what she actually needed for her personal projects.
Evans documents how modern CSS features like custom properties, container queries, and :has() — which didn't exist when she first reached for Tailwind — now make it practical to write well-structured vanilla CSS. Her post walks through file organization, class naming, and responsive design patterns that work without a framework.
The editorial notes that Tailwind has legitimate strengths for large teams with mixed frontend skill levels — consistent spacing scales, purged production builds, colocation of styles with markup, and a design-token system that enforces visual coherence. It's used in production at Shopify, GitHub, and thousands of startups with a steep real adoption curve.
The editorial synthesizes Evans' post into a broader industry observation: Tailwind solves the 'I don't want to think about CSS' problem, but for many projects, thinking about CSS is exactly what developers should be doing. This articulates something many developers feel but haven't said out loud.
Julia Evans — known online as @b0rk, author of beloved programming zines and the blog jvns.ca — published a post this week titled "Moving away from Tailwind, and learning to structure my CSS." The post details her experience removing Tailwind CSS from her personal projects and replacing it with hand-written, structured CSS. It hit the front page of Hacker News and collected 497 points, making it one of the highest-engagement frontend posts of the month.
Evans' framing is characteristically honest. She didn't leave Tailwind because it's bad software. She left because she realized it had become a way to avoid learning CSS itself — and that avoidance was making her worse at building interfaces. The argument isn't that Tailwind is harmful; it's that for her, the abstraction became a substitute for understanding, and understanding is what she actually needed.
The post walks through her process of restructuring CSS for projects like her interactive programming exercises, covering how she organizes files, names classes, handles responsive design, and uses modern CSS features (custom properties, container queries, `:has()`) that didn't exist when she first reached for Tailwind.
This post landed with force because it articulates something a lot of developers feel but haven't said out loud: Tailwind solves the "I don't want to think about CSS" problem, but for many projects, thinking about CSS is exactly what you should be doing.
The Tailwind debate is one of the most persistent in frontend development. The framework has legitimate strengths — consistent spacing scales, purged production builds, colocation of styles with markup, and a design-token system that enforces visual coherence across teams. For large teams with mixed frontend skill levels, Tailwind genuinely reduces a category of bugs. It's used in production at Shopify, GitHub (partially), and thousands of startups. Its adoption curve has been steep and real.
But Evans' critique hits a different nerve. She's not building a design system for a 40-person team. She's building personal tools and educational projects where she is the only developer, the only designer, and the person who will maintain the code for years. In that context, Tailwind's value proposition inverts. The utility classes don't save coordination costs — there's no one to coordinate with. They add a build dependency and a layer of indirection between her and the actual styling language.
The HN discussion surfaced the usual fault lines but with more nuance than the typical Tailwind flame war. Several commenters distinguished between "Tailwind for teams" (where it enforces consistency) and "Tailwind for individuals" (where it can inhibit learning). Others pointed out that modern CSS has closed many of the gaps that made utility-first frameworks attractive in the first place — custom properties replace most of what Sass variables did, nesting is native, and `@layer` gives you explicit cascade control without specificity hacks.
A recurring theme in the discussion: developers who adopted Tailwind in 2020-2022, when CSS was genuinely more painful, are now reconsidering as the platform has matured. The CSS spec has moved fast. Container queries, `:has()`, `color-mix()`, native nesting, `@scope`, and cascade layers have all shipped in major browsers since Tailwind's peak adoption wave. The platform caught up, and some of the escape hatches are no longer necessary.
What makes Evans' post more useful than a typical "I quit X" blog is that she documents what she moved *to*. Her approach isn't novel in academic terms — it draws from ideas that CSS practitioners have advocated for years — but it's practical and specific:
Scoped class names over utility classes. Instead of `class="flex items-center gap-4 p-6 bg-white rounded-lg shadow-md"`, she uses semantic class names like `.exercise-card` with the styles defined in a corresponding CSS file. The tradeoff is obvious: you write more CSS, but you can read your HTML.
CSS custom properties as design tokens. Colors, spacing, and typography scales are defined as custom properties on `:root`, giving her the same consistency benefits Tailwind provides through its config — but with zero build step and full browser DevTools support.
File-per-component organization. Each major UI component gets its own CSS file, imported via `@import`. This is the structure that CSS Modules and styled-components tried to enforce through tooling, but modern CSS makes it possible with just the platform.
Minimal nesting, no BEM. She avoids deep nesting (max two levels) and doesn't use BEM naming conventions, preferring short, descriptive class names scoped by component context. Her heuristic: if you need more than two levels of nesting, your component is too complex and should be split.
This approach won't scale to every project. A 200-component design system with 15 contributors needs more structure — and possibly a tool like Tailwind or StyleX to enforce it. But for the vast universe of personal projects, small team apps, and content sites, it's a reminder that CSS without a framework is not CSS without structure.
If you're maintaining a Tailwind project that works, this post is not a reason to rewrite. Tailwind at scale, with an established component library, is fine. The switching cost almost certainly exceeds the benefit.
But if you're starting a new project — especially a small or solo one — Evans' experience is worth internalizing. The question isn't "Tailwind vs. vanilla CSS" but "do I understand what my styles are doing, and does my tooling help or hinder that understanding?" If you're copying Tailwind class strings from docs without knowing what `flex-shrink-0` computes to, you're writing CSS you can't debug.
For team leads evaluating frontend tooling: the 2026 CSS platform is materially different from the 2020 CSS platform. If your Tailwind adoption was motivated by gaps that native CSS has since filled (variables, nesting, scope), it's worth auditing whether the framework still earns its place in your dependency tree. This doesn't mean ripping it out — it means asking whether new developers on your team are learning CSS or learning Tailwind, and whether that distinction matters for your codebase's long-term health.
The broader signal here is that the frontend ecosystem may be entering a "back to the platform" phase. Between Evans' post, the growing adoption of native CSS features, and increasing skepticism of build-step-heavy workflows, the pendulum is swinging toward fewer abstractions. Not no abstractions — fewer.
Evans' post will not end the Tailwind debate. Nothing will — it's a genuine values disagreement about what CSS development should feel like. But the post's resonance (497 HN points is a strong signal for a CSS methodology post) suggests a meaningful cohort of developers are ready to re-engage with CSS as a language rather than a problem to be abstracted away. The platform has earned another look. Whether you take it depends on your team, your project, and your willingness to write a `.card` class with your own hands.
Top 10 dev stories every morning at 8am UTC. AI-curated. Retro terminal HTML email.