Vertical Slice en .NET: una mirada pragmática más allá de la arquitectura limpia
Este articulo no es para enseñar Vertical Slice ni para repetir diagramas de Clean Code, ya existe mucha documentación en Internet. Mi enfoque es un recordatorio sencillo: programamos para resolver problemas reales. A veces nos aferramos a plantillas “porque así es patrón”, y terminamos defendiendo la forma en vez del resultado. Mi experiencia: pensar por casos de uso baja el ruido, reduce choques entre personas y pone el foco en entregar valor.
Qué quiero provocar
Antes de elegir una estructura, pregúntate:
- ¿Aporta claridad? ¿Alguien nuevo ubica rápido dónde tocar?
- ¿Nos hace más rápidos sin perder calidad?
- ¿Reduce riesgos de verdad (no escenarios hipotéticos)?
- ¿Sirve al cliente hoy, no a un “quizás” de mañana?
Si no, suena a formalismo. Y el formalismo se paga caro en tiempo y mantenimiento.
Mini historia (muy realista)
En un equipo con capas muy marcadas, casi cada PR tocaba “services” y “repositories” compartidos: choques constantes y discusiones sobre “¿dónde debería ir?”. Al movernos a features autocontenidas, las PR se volvieron más cortas y rara vez chocábamos. El caso de uso “se leía solo”.
El punto que destapa todo: EF Core, repositorio y unidad de trabajo
Suele pasar: se crea un repositorio y una unidad de trabajo encima de Entity Framework Core solo para “respetar el patrón”. ¿El costo? Mucho trámite que pasa llamadas sin aportar. Peor: al imponer ese repositorio encima de EF, te obligas a agregar ahí todos los métodos de consulta que el caso de uso necesite. Aparecen cinco consultas distintas… y terminas parchando la interfaz o multiplicando métodos. Resultado: recortas el potencial de EF Core (consultas expresivas, proyecciones, filtros encadenados) y conviertes algo potente en una API limitada.
“Si agregas esa abstracción porque de verdad crees que en el futuro vas a cambiar a otro motor de base de datos, ok, tiene sentido (aunque en la práctica es raro). Lo acepto: válido aunque no coincida al 100%. Pero si la razón es solo ‘porque el patrón lo dice’, ahí está mal.”
En un enfoque por features, inyectar el DbContext en el lugar del caso de uso te deja todo el poder del ORM a mano: consultas claras, proyecciones directas y menos capas de por medio. Eso acelera y baja la parafernalia.
¿Cuándo sí haría un repositorio/unidad de trabajo?
- Si tienes más de una fuente de datos real (EF + Dapper + servicio externo) y alternas según escenario.
- Si un agregado con invariantes gana legibilidad y pruebas más limpias con un repositorio explícito.
- Si expones un puerto de aplicación de alto nivel que ordena el lenguaje del negocio.
Fuera de eso, envolver por costumbre te frena y te limita sin beneficio claro.
Checklist rápida
- ¿Hay conflictos de merge por tocar capas compartidas?
- ¿Las PR son largas y difusas por “protocolo” de capas?
- ¿Necesitas consultas ricas y tu repositorio se vuelve un cajón de sastre?
- ¿El equipo invierte horas defendiendo plantillas, no resultados?
Si marcaste varias, prueba a organizar por features y a evitar capas por costumbre. Mide después: PR más cortas, menos choques, menos burocracia.
Nota breve para que no parezca fanatismo
No digo que Vertical Slice sea “mejor para todos”. Tiene sus problemas: puede aparecer duplicación si nadie decide cuándo factorizar, el cross-cutting se dispersa si no hay convenciones (validación, logging, seguridad), y en equipos grandes conviene acordar nombres y ubicación para no perder descubribilidad. Hay que vigilarlo.
Lo que uso en el día a día (y por qué)
En mi práctica diaria uso una mezcla: features verticales en la aplicación, principios de Clean para mantener el dominio independiente y una infraestructura clara para lo técnico (persistencia, cache, mensajería, auth). Funciona porque cuida los principios sin caer en rigidez de manual.
Criterios de excepción (para no caer en blanco/negro)
- Abstrae cuando haya variabilidad real (hoy EF, mañana otra cosa) o cuando el contrato de negocio gane claridad.
- No abstraigas cuando sea solo “por tradición” y te quite el poder de la herramienta (como EF Core) sin un beneficio claro.
- Factoriza duplicación cuando duela (mantenimiento, bugs, coste), no antes.
Otros ejemplos donde el pragmatismo debe ganar
1) CRUD simple “vitaminado” con Clean, CQRS y eventos de dominio
He visto apps que son altas/bajas/modificaciones sin reglas complicadas, pero se les cuelga todo el aparato: CQRS completo, Clean con muchas capas, eventos por todos lados. Resultado: más trámite que valor.
- Cuándo sí: necesitas escala clara (lecturas y escrituras con ritmos muy distintos), auditoría fina o proyecciones complejas que justifican separar rutas y modelos.
- Cuándo no: CRUD directo con validaciones básicas y poco volumen. Empieza simple; añade piezas si el dolor aparece.
2) Microservicios para un sistema local, pequeño y de mantenimiento
Para una empresa local con un módulo de back-office acotado, irse a microservicios por defecto suele sumar sobrecarga operativa (infra, observabilidad, despliegues, resiliencia, consistencia distribuida) sin retorno claro.
- Cuándo sí: equipos múltiples con ritmos de despliegue independientes, bounded contexts bien definidos, requerimientos fuertes de aislamiento y escalado por partes.
- Cuándo no: un equipo pequeño, alcance reducido y dependencias simples. Un monolito modular llega más lejos de lo que parece.
3) “Usar MediatR = hacer CQRS”
MediatR no es sinónimo de CQRS. Es una librería que implementa el patrón mediador y ofrece cosas útiles (handlers, notificaciones, behaviours).
- Si solo lo usas para separar comandos/consultas sin aprovechar behaviours, notificaciones o eventos, quizá estás añadiendo una dependencia que no te hace falta: crea interfaces simples y listo.
- Si sí lo usas para mediador real (behaviours transversales, eventos de dominio, notificaciones), entonces tiene sentido: centralizas transversales y ordenas el flujo.
Cierro
Vertical Slice y Clean no son bandos; son herramientas para mirar el mismo problema. Lo importante es el pragmatismo: elegir lo que hace al equipo más claro, más rápido y más efectivo para el cliente hoy. Si la única defensa de una decisión es “porque el patrón”, sospecha: quizá no es la mejor decisión para tu contexto.
Si quieres seguir aprendiendo sobre estos temas te invito a ver mis otras publicaciones.
Referencias

Soy un Ingeniero en Informática, apasionado de la tecnología y, siempre trato de estar aprendiendo para estar al día con las últimas tecnologías, me especializo en el desarrollo Backend con .NET, pero durante estos años, he trabajado con muchas otras tecnologías que me han ayudado en mi crecimiento profesional.