Ejercicio 1 — La matriz honesta
- Los números de TicketFlow: 5 microservicios = 5 pipelines (el CI del 41 ×5), 5 despliegues/semana (la cadencia cae de 2.1/día a ~0.4/servicio), 12 de las 18 features del roadmap serían distribuidas (el checkout toca tickets+payments+events), y la saga del 32 pasaría de "un caso" a "el estándar" de todo flujo entre módulos. El costo de red+timeouts+breakers (54) en cada borde: ~2 semanas de setup + el mantenimiento permanente.
- El mejor argumento REAL a favor: la independencia de despliegue y falla del pago — "si el checkout explota (el pico del 36), el pago NO debe caer con él" (el blast radius). Pesa más que su costo cuando: el volumen de pagos justifica su operación separada Y el PCI (56) exige frontera física Y el equipo supera 8-10 devs.
- El argumento contrario (la decisión): "Con 1 dev, 1 app y 50k ventas/mes, la frontera modular (2) compra las fronteras y la salida abierta por el 10% del costo; los microservicios pagarían 5 pipelines, 12 flujos distribuidos y una saga por feature. Trigger documentado: PCI o volumen ×10. Revisión: el trigger, no la moda".
Ejercicio 2 — La modularización
- El mapa: tickets (reserva/expiración/disponibilidad), payments (pasarela/ledger/comisiones), events (catálogo/venues), identity (auth/MFA), shared (Money, Clock, outbox, errores del 26). El
utilsdel 24 se disuelve: lo de dominio a su módulo, lo compartido estable a shared, lo huérfano se borra (el hunting). - Lo que la interfaz revela: payments usaba
Ticketde tickets DIRECTAMENTE (el import escondido del cálculo de comisión) y events leíaReservation.objects(el dashboard de ocupación) — 2 violaciones reales cazadas al ESCRIBIR la interfaz: los imports que la frontera obliga a subir son el inventario honesto del acoplamiento. - El CI con 12 combinaciones prohibidas (5 módulos, n×(n−1)): cazó los 2 violadores del ejercicio 2 + 1 fixture de tests que importaba models de otro módulo (migrado a la interfaz). El test de frontera es el linter de la arquitectura: sin él, la constitución es un doc bonito.
Ejercicio 3 — Los contratos
- El contrato síncrono:
def test_contrato_tickets_reservar():
r = tickets.reservar(user, event_uuid, ["A1"], clock=FakeClock(...))
assert isinstance(r, ReservationSummary) # el DTO del 25: el contrato
with pytest.raises(SeatUnavailable): # las excepciones SON el contrato
tickets.reservar(user, event_uuid, ["A1"], clock=FakeClock(...))Si la firma cambia, este test (corriendo desde payments/) rompe: el contrato entre módulos es testado como el pacto entre servicios de la 35.
- El contrato async:
PaymentSucceededcon payload mínimo{intent_id, ref, amount}(la 25: autosuficiente), consumido por tickets para CONFIRMAR. Si fuera síncrono: la transacción única se rompería (el cobro dentro de la TX de reserva = el pool del 39 sufriendo + el UNKNOWN del 32 sin reconciliación) y el receptor quedaría acoplado al emisor en tiempo real — el async compra la desacoplación temporal al precio de la eventualidad (la 32: converge).
- La regla (8 líneas): "Síncrono si la operación pertenece a la MISMA transacción (asiento+estado). Async si el receptor es periférico o tolera el retraso (emails, analytics, confirmación tras pago). Caso de estudio: reservar() síncrona (misma TX), PaymentSucceeded async (convergencia), PaymentFailed async (compensación)".
Ejercicio 4 — El umbral y el strangle
- El trigger: el PCI (56) — "se extrae payments cuando el cumplimiento exija la frontera física de los datos de tarjeta (el dominio que PAGA su operación con un requisito regulatorio) o cuando el volumen de pagos ×10 frente al resto (55: el escalado divergente). Medible: la fecha del PCI y el ratio de volumen en el dash del 46".
- El strangle comparado (la estimación del 49):
CON la frontera preparada (interfaces+eventos+tests): 3 semanas
F1 (3 d) el servicio nuevo duplica el flujo (el flag decide)
F2 (3 d) canary del 46 (5%→50% del tráfico al servicio nuevo)
F3 (2 d) 100% + monolito destrona el código (11)
F4 (3 d) la limpieza + el contrato HTTP (14)
SIN frontera (el re-write del acoplamiento): 2-3 meses
(los 12 flujos distribuidos, la saga en cada uno, los contratos desde cero)El ratio 3:1-4:1 ES el valor de la modularidad de hoy: la frontera no se compra mañana, se paga en pequeñas cuotas desde hoy.
- Los 5 cambios que la extracción obliga (mitigados por la frontera): (1) el contrato entre módulos pasa de import a HTTP/gRPC (los tests de la 35 son el molde); (2) la saga del 32 cruza la red (los UNKNOWN de la red se añaden a los de la pasarela — el 54); (3) el outbox deja de ser tabla compartida: stream externo (30); (4) la identidad: el token interno del 18 entre servicios; (5) la observabilidad: la traza del 46 cruza servicios (el trace_id ya viaja, la 45).
Ejercicio 5 — La defensa
- El pitch (10 líneas): "Hoy el monolito usa 3 réplicas de las cuales 2 están para el checkout del viernes: el escalado divergente que justificaría microservicios es 1 servicio de 5. Los 12 flujos que tocarían pasan a distribuidos: cada uno con la saga del 32, el 54 y el contract del 14. La propuesta: monolito modular con fronteras testadas (hoy), el trigger PCI/volumen documentado (mañana), y el strangle con la frontera hecha (el día X): la misma salida a 1/4 del costo. Si el volumen ×10 llega, el plan ya está pagado."
- La respuesta en 3 frases: "Fronteras sí, física aún no: los módulos están separados por interfaz y eventos (el 52/53). Extraer ahora paga 5 pipelines y 12 flujos distribuidos por el beneficio de 1. El ADR tiene el trigger: cuando el PCI o el volumen lo pida, la extracción ya está pagada."
- La regla personal (extracto): "Modularidad antes que distribución; la frontera se paga en cuotas desde el día 1 (interfaz+eventos+test); el trigger del strangle se escribe ANTES de necesitarlo; la moda no es una métrica."
Resumen del profesor
- Los microservicios no arreglan el acoplamiento: lo hacen pagable — primero la frontera conceptual (con tests), después la física si el negocio la exige.
- El monolito modular: interfaces públicas, eventos vía outbox, FK prohibidos entre módulos, shared pequeño — el test de frontera en CI es la constitución.
- El strangle con frontera preparada cuesta 1/3-1/4 que sin ella: la modularidad de hoy es la pre-pago de la extracción de mañana — con el trigger escrito en el ADR.