wandres.dev
ARQUITECTURA II · Utility-first, CSS-in-JS y el estado del arte

Qué eligen los equipos en 2026, según el proyecto

El mapa honesto de qué encaja con qué: cinco tipos de proyecto, la elección que domina en cada uno y las razones concretas, sin recomendar una solución universal.

⏱ 17 min

No hay una respuesta correcta a “qué debo usar”, y quien te la dé sin preguntarte nada sobre tu proyecto está vendiendo algo. Lo que sí hay son correlaciones fuertes y explicables entre el tipo de producto y la elección que acaba funcionando, porque cada modelo optimiza una cosa distinta y los proyectos tienen cuellos de botella distintos. Esta lección es ese mapa, con las razones a la vista para que puedas discrepar con criterio.

🎯 Al terminar esta lección sabrás
  • Emparejar cinco tipos de proyecto con el modelo que suele encajar y por qué.
  • Reconocer las señales de que la elección actual ha dejado de servir.
  • Diseñar una estrategia mixta sin acabar con dos sistemas compitiendo.
  • Distinguir lo que hay que decidir ahora de lo que se puede posponer.

Cinco tipos de proyecto

Producto de aplicación con equipo grande. Muchos componentes, mucha rotación, superficie de estilo pequeña por componente, iteración constante. Aquí domina el modelo de utilidades, y la razón principal no es la velocidad de escritura sino la que se explicó en la lección del modelo: convierte disciplina en compilación, y la disciplina es exactamente el recurso que un equipo grande no puede garantizar. El segundo motivo es el borrado seguro: en un producto que cambia todas las semanas, que borrar un componente borre su estilo elimina la fuente principal de crecimiento monótono.

Biblioteca de componentes o sistema de diseño distribuible. Aquí la elección se invierte casi siempre. Una biblioteca que se instala en proyectos ajenos no puede imponerles un motor de build, ni asumir que su marcado será escaneado, ni depender de que el consumidor tenga la misma escala. Lo que se distribuye es CSS plano, con capas declaradas para que el consumidor pueda ganarle sin !important, con custom properties como API pública y con :where() para que la especificidad sea cero y cualquier estilo del consumidor venza. Los detalles de ese contrato están en el nivel 52.

Sitio editorial o de contenido. Pocas plantillas, mucho texto, tipografía trabajada, mucho contenido que no controlas —lo que sale de un gestor de contenidos o de un fichero Markdown no lleva clases—. Aquí las utilidades encajan mal por construcción: no puedes poner clases en HTML que no escribes tú. Domina el CSS escrito a mano, con estilos de elemento dentro de un ámbito, que es exactamente el caso de uso para el que @scope resulta más natural.

Aplicación con mucha complejidad visual. Visualización de datos, editores, herramientas de diseño, animación intensa, layouts irregulares. La complejidad vive dentro del CSS: cálculos, capas, transformaciones encadenadas, sincronización con animaciones. Un modelo que fragmenta el estilo en declaraciones sueltas sobre elementos sueltos estorba aquí. Domina el CSS con módulos o con extracción tipada, ficheros de estilo de verdad, y a menudo bastante CSS escrito a mano sin ninguna herramienta.

Proyecto pequeño, personal o de vida corta. Una landing, una herramienta interna, un prototipo. Cualquier cosa funciona, y la variable que decide es el tiempo de arranque. Sin equipo y sin años por delante, ninguna de las garantías que compran las herramientas tiene valor. CSS plano en un fichero, con capas para el orden y custom properties para los valores, es difícil de superar.

ℹ️
La correlación real es con la fuente del marcado

Si tuvieras que predecir la elección de un equipo con un solo dato, el mejor no es el tamaño ni el sector: es quién escribe el HTML. Marcado generado por componentes que tú controlas favorece utilidades. Marcado que viene de un gestor de contenidos, de Markdown, de un correo o de un tercero favorece CSS con selectores. Casi todas las decisiones sensatas que verás se explican con esa variable.

Las señales de que hay que cambiar

Más útil que elegir bien de entrada es reconocer cuándo la elección ha dejado de servir. Cada modelo falla con síntomas propios.

En un proyecto de utilidades, las señales son: valores arbitrarios entre corchetes multiplicándose en el marcado; listas de clases tan largas que la gente copia y pega componentes enteros en lugar de reutilizarlos; y la aparición de una capa de clases semánticas escritas a mano encima de las utilidades para “arreglar la legibilidad”, que es el momento en que tienes dos sistemas y ninguna de sus ventajas.

En un proyecto de CSS escrito a mano, las señales son las clásicas: el primer !important que no es una utilidad; un fichero de estilos que nadie se atreve a borrar; modificadores que se anulan entre sí; y el síntoma definitivo, que alguien haya escrito una regla nueva porque le pareció más seguro que modificar la existente.

En cualquiera de los dos, hay una señal común y es la peor: que la respuesta a “¿de dónde sale este espaciado?” sea “no sé, copié lo de al lado”.

Estrategias mixtas que sí funcionan

Lo mixto tiene mala fama porque se hace mal, pero hay dos combinaciones que funcionan de verdad, y las dos tienen en común que cada sistema tiene una frontera clara y ninguna zona se estila con los dos.

La primera: utilidades para la composición, CSS con ámbito para el contenido. Layout, espaciado y estructura con utilidades en las plantillas; el contenido de formato largo, que llega sin clases, con una hoja de estilos de tipografía acotada con @scope. La frontera es evidente y no hay solapamiento.

@scope (.prosa) {
  :scope { max-inline-size: 68ch; }
  p { margin-block: 1em; }
  h2 { margin-block: 2em 0.5em; }
  a { text-decoration-thickness: 0.08em; }
}

La segunda: CSS plano para los primitivos, utilidades para el ensamblaje. Los componentes base —botón, campo, tarjeta— son CSS escrito a mano con custom properties como API. Todo lo que los coloca, separa y alinea, utilidades. Esto funciona especialmente bien cuando ya tienes una biblioteca interna y no quieres reescribirla.

Lo que no funciona es mezclar en la misma zona: un componente con clases de utilidad y además una hoja propia que las anula. Ahí pierdes las dos ventajas a la vez —el estilo deja de ser local y la hoja deja de ser la fuente de verdad— y ganas una fuente inagotable de conflictos de especificidad.

La herramienta que hace viables las estrategias mixtas es @layer, y merece la pena decirlo explícito: declarar el orden de capas es lo que convierte “dos sistemas conviviendo” de un problema de suerte en un problema resuelto.

@layer reset, base, componentes, utilidades;

Qué decidir ahora y qué posponer

No todas las decisiones tienen el mismo coste de cambio, y ordenarlas por ese criterio es más útil que ordenarlas por importancia.

Decide ahora, porque cambiarlo después es caro: el orden de capas, la capa de tokens y su estructura, y las fronteras de tus componentes. Eso es modelo de dominio y está en todas partes.

Puedes posponer, porque cambiarlo es más barato de lo que parece: la herramienta de estilo. Como quedó claro en la lección anterior, todas convergen al mismo artefacto —CSS estático más variables— y una migración entre ellas es mecánica y acotada. Nadie ha hundido un proyecto por elegir mal aquí; se han hundido muchos por no tener tokens.

Decide pronto pero puedes equivocarte sin drama: la escala de espaciado y la de tipografía. Son fáciles de ajustar mientras estén en un solo sitio, y ese es el argumento entero a favor de tenerlas en un solo sitio.

La elección de herramienta es la decisión menos importante que vas a tomar, y absorbe el noventa por ciento de la discusión

Vale la pena mirar esto con perspectiva antes de cerrar el nivel, porque el reparto de atención está profundamente desequilibrado y eso tiene consecuencias. Las discusiones sobre herramienta son públicas, tienen bandos, se pueden tener sin conocer tu producto y no exigen ningún trabajo previo: cualquiera puede opinar sobre utilidades frente a CSS plano en un hilo de veinte mensajes. Las decisiones que de verdad determinan si tu CSS será mantenible en cinco años son privadas, aburridas y exigen conocer el dominio: cuántos niveles tiene tu escala de espaciado y por qué; qué significa exactamente “superficie elevada” en tu producto; dónde acaba el botón y empieza el campo; qué configura un componente y qué se queda dentro. Nadie escribe hilos sobre eso, y es exactamente lo que separa un sistema que absorbe cinco años de cambios de uno que se descompone en dieciocho meses. La prueba empírica está a la vista de todos: hay productos excelentes y mantenibles construidos con cada una de las opciones de este nivel, y desastres construidos con cada una de ellas. Si la herramienta fuera la variable determinante, esa distribución sería imposible. La variable determinante es si alguien se sentó a decidir el vocabulario del sistema y lo escribió en un sitio, y eso lo puedes hacer hoy, con la herramienta que ya tengas, sin migrar nada.