Arquitectura
El servicio generado sigue una Arquitectura Hexagonal (Puertos y Adaptadores) combinada con principios de Domain-Driven Design.
Capas
| Capa | Responsabilidad |
|---|---|
Domain |
Logica de negocio pura: aggregate roots, entidades, eventos de dominio e invariantes. Sin dependencias de framework. |
Ports |
Contratos (interfaces) que definen como el dominio interactua con el exterior. Se dividen en input ports (casos de uso) y output ports (persistencia, consultas, publicacion de eventos). |
Services |
Servicios de aplicacion que implementan los input ports y orquestan los output ports. No contienen logica de negocio. |
Adapters |
Implementaciones concretas que conectan los puertos con la tecnologia. Se dividen en inbound (controladores REST, listeners de eventos) y outbound (repositorios JPA, publicadores de eventos). |
Reglas fundamentales:
-
El dominio nunca importa adaptadores ni servicios.
-
Los puertos son solo interfaces.
-
Los adaptadores no dependen entre si — solo de los puertos que implementan.
Commons
El paquete commons provee infraestructura compartida entre bounded contexts: entidades base, puertos de publicacion de eventos, el patron outbox/inbox y el manejo centralizado de excepciones.
Para los contratos de las tres clases base JPA que usan las entidades del dominio, ver Clases base JPA.
Mensajeria
El patron outbox/inbox vive en commons/messaging y commons/service, y respeta las reglas hexagonales del arquetipo:
-
Mensajes en el dominio:
DomainEvent<T>yCommand<T>son records inmutables, sin dependencias de framework. La regla ArchUnitdomain_events_should_be_recordsverifica que los payloads bajoevents/{dominio}/sean records. -
Ports como contratos puros: los publishers y registries (
EventsPublisher,CommandPublisher,EventRegistry,CommandRegistry) y los handlers (DomainEventHandler<T>,CommandHandler<T>) son interfaces. La reglaports_should_be_interfaceslo refuerza, con@EventHandlery@CommandMappingdeclaradas como excepcion por ser meta-anotaciones. -
Adapters aislados por direccion: los JPA adapters de las bandejas y los Spring publishers/listeners viven en
commons/adapter/out/persistence,commons/adapter/out/springycommons/adapter/in/listener/spring. Las reglasinbound_adapters_should_not_depend_on_outbound_adaptersy su inversa impiden que cualquiera de los dos lados llame al otro directamente. -
Servicios de orquestacion sin saltar capas: dispatchers (
OutboxEventsDispatcher,InboxEventsProcessor, etc.) y handler dispatchers viven encommons/servicey solo invocan ports, nunca adapters concretos. La regla generalservice_should_not_depend_on_adapterslos cubre.
Para los contratos detallados del sistema, ver Referencia: Mensajeria. Para el razonamiento detras del diseno (por que outbox, por que cuatro bandejas, etc.), ver Decisiones de mensajeria.