La Capa de Dominio en Clean Architecture: Qué debe contener y por qué
El dominio es el corazón de un sistema con arquitectura limpia, aquí te muestro un ejemplo real.

En Clean Architecture, el Dominio es el corazón del sistema. Aquí vive el conocimiento del negocio: reglas, políticas, modelos, entidades y comportamientos que definen cómo funciona realmente tu aplicación, independientemente de frameworks, bases de datos o infraestructura.

La capa de Dominio debe ser completamente pura, independiente y estable.
Si cambias la base de datos, la API, o el UI… el Dominio no cambia.

A continuación te presento los 8 elementos que pertenecen a la capa Domain, con una explicación para cada uno.

Los 8 elementos que conforman la capa de Dominio

Te iré explicando uno a uno los elementos y juntaré todo en un ejemplo real de una capa de dominio, tal como lo verías en un proyecto con arquitectura limpia allá afuera, en la industria. El proyecto lo llamaré Ecommerce.

El código está disponible en este repo de mi Github.

1. Entidades (Entities)

Objetos del dominio que tienen identidad propia y cambian con el tiempo.
Dos entidades pueden tener datos iguales, pero si su identidad es distinta, son entidades diferentes.

En el proyecto Ecommerce las entidades son:

  • Order.cs
  • OrderLine.cs
  • Customer.cs

La entidad más importante es Order, que actúa como tu Aggregate Root, con invariantes, cambios de estado, reglas de negocio, etc.

Más ejemplos reales de la industria

  • En un ERP: Invoice, PurchaseOrder, Shipment
  • En un banco: Account, Transfer, Loan
  • En un ecommerce gigante (Amazon): Cart, Order, ReturnRequest

2. Value Objects (Objetos de Valor)

Son objetos sin identidad, representados solo por su valor.
Son inmutables, intercambiables y se comparan por valor.

Estos se pueden ubicar en la carpeta Shared, en Ecommerce tienes a:

  • Money.cs

Money encapsula lógica como:

  • Inmutabilidad
  • Operaciones seguras (Add, Multiply)
  • Unidad monetaria

Más ejemplos reales de la industria...

  • Email (valida formato)
  • Address (país, ciudad, ZIP… siempre consistente)
  • Coordinates (latitud/longitud)

3. Aggregate Roots (Agregados)

Los agregados (aggregate) son conjunto de entidades y value objects que forman una unidad de consistencia, con reglas que deben mantenerse en conjunto.

El agregado establece límites claros para las reglas del negocio.

Por otro lado, un aggregate root es la entidad principal de un agregado, es la única puerta de entrada para modificar el agregado y todo debe mantenerse consistente a través de ella.

En Ecommerce el agregado principal es:

  • Order
    Contiene las líneas del pedido y controla la consistencia del agregado:
    • No duplicar productos
    • No modificar si está pagado
    • Total > 0
    • Controla eventos como OrderCreatedEvent

Más ejemplos reales de la industria...

  • Account → maneja transacciones y saldo
  • Order → maneja líneas, pagos, estados
  • Booking → maneja fechas, habitaciones, disponibilidad

4. Domain Services (Servicios de Dominio)

Lógica del dominio que no pertenece naturalmente a una sola entidad o value object.
Modelan reglas “entre” entidades, o políticas externas.

Aquí tenemos:

  • ICreditPolicy.cs
  • DefaultCreditPolicy.cs

Este servicio encapsula la regla: ¿Tiene el cliente crédito suficiente para crear un pedido?

Esta lógica no pertenece ni a Order ni a Customer de manera natural → por eso es un Domain Service.

Otros ejemplos reales de la industria...

  • Calcular límites de crédito en bancos
  • Aplicar reglas de impuestos entre países
  • Determinar si un usuario puede acceder a un recurso (IAM)
  • Calcular elegibilidad en un préstamo

5. Interfaces de Repositorio (Repository Interfaces)

Son contratos que definen cómo se almacenan y recuperan aggregate roots, sin importar la tecnología.

El ejemplo salta a la vista, está en la carpeta Orders:

  • IOrderRepository.cs

Esto es dominio puro: defines cómo el Dominio quiere recuperar y persistir Order.
La implementación vive en infraestructura.

Más ejemplos reales de la industria...

  • ICustomerRepository
  • IInvoiceRepository
  • ICartRepository

En DDD nunca expones EF Core al dominio.

6. Domain Events (Eventos de Dominio)

Son aquellos eventos que representan algo significativo que ocurrió en el dominio, y que otras partes del sistema podrían necesitar conocer.

Tenemos dos y bien organizados:

  • OrderCreatedEvent.cs
  • OrderPaidEvent.cs

Son eventos que informan al resto del sistema que algo del negocio pasó.

Más ejemplos reales de la industria...

  • PaymentProcessed
  • UserRegistered
  • ProductBackInStock
  • ShipmentDelivered

Los eventos permiten integrar bounded contexts o workflows (como envío de emails).

7. Domain Exceptions (Excepciones del Dominio)

Salta a la vista, está en la carpeta Shared:

  • DomainException.cs

Esta excepción no representa un error técnico, sino una infracción de una regla del negocio:

  • No se puede pagar un order sin líneas
  • No se puede agregar un producto duplicado
  • No se puede crear un order sin cliente

Más ejemplos reales de la industria...

  • InsufficientFundsException
  • CreditLimitExceededException
  • InvalidBookingDateException

8. Specifications / Rules (Especificaciones del dominio)

Las reglas del negocio son aquellos lineamientos propios del negocio, los que normalmente te los da el product owner o el dueño del negocio.

Las invariantes son reglas del negocio que siempre deben cumplirse, sin importar cómo evolucione el agregado.
Son las leyes internas del agregado.

En el método EnsureInvariants() de la entidad Order puedes ver invariantes, que son reglas que deben cumplirse siempre.

Más ejemplos reales de la industria

  • “Un cliente puede comprar si está activo y sin deudas”
  • “Un vuelo sólo puede reservarse si hay cupos”
  • “Un préstamo sólo puede aprobarse si el score crediticio es suficiente”

Si quieres ver el código está disponible en este repo de mi Github, y no te olvides de darle estrella y seguirme! 🐿️🙌


Si esta entrada te ha gustado compártela!

Imagen de portada basada en: Foto de Jeremy Hynes en Unsplash

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *