Saltar al contenido
Julián Campos
  • Inicio
  • Blog
  • Qué hago
  • Quién soy
  • Newsletter
  • Contacto
  • Casos de éxito
Julián Campos

Menú principal

Servicios, casos y contenido para decidir mejor tu próxima web.

  • Inicio
  • Blog
  • Qué hago
  • Quién soy
  • Newsletter
  • Contacto
  • Casos de éxito
Cuéntame tu proyecto

Newsletter técnica

El cuello de botella que diseñé sin darme cuenta

El error silencioso que convierte un código limpio en una experiencia lenta

26 de febrero de 2026 6 minutos de lectura Julian Campos
  • arquitectura
  • arquitectura de software,
  • De CERO a SENIOR
  • Producto

Tabla de contenidos

  1. El problema del acoplamiento oculto
    1. 1. Domain Events
    2. 2. Listeners y Jobs
    3. 3. Colas con Redis + Horizon (La infraestructura asíncrona)
    4. Diagrama y Contratos de Diseño

Sin prisa, pero sin pausa.

Así está siendo el desarrollo de KPIAds.app.

Por suerte o por desgracia, estoy hasta arriba de trabajo y no le estoy pudiendo dedicar el tiempo que me gustaría al desarrollo de mi side project.. pero tampoco lo abandono.

Si sigues las entregas sobre el desarrollo de KPIAds, sabrás (o te intuirás) que estamos acabando la fase de diseño de todo el sistema.

Aunque está siendo bastante lento, es crucial para que luego el desarrollo vaya fluido y las cosas estén claras.

Que no nos toque improvisar en temas tan importantes como la arquitectura de nuestro futuro SaaS.

También sabrás, si leíste la última entrega sobre KPIAds, que en esta última entrega dimos un paso gigante en el diseño de KPIAds: decidimos sacar la lógica de negocio de los controladores y encapsularla en Actions.

Dejamos bien claro cómo sería el flujo de nuestro SaaS , un flujo bien precioso donde todo gira entorno a Route → Controller → Action → View.

Cada pieza tiene una única responsabilidad. Todo parece perfecto.

Pero hay una trampa mortal en la fase de diseño en la que es muy fácil caer. Una trampa que dejará tu código muy limpio, pero que destrozará la experiencia de tu usuario.


Déjame plantearte este escenario.

¿Qué pasa cuando un usuario crea un nuevo proyecto en la plataforma?

  1. Guardamos el proyecto en la base de datos.

  2. Generamos las métricas por defecto.

  3. Le enviamos un email de bienvenida.

  4. Notificamos al administrador por Slack.

Si en nuestro diseño metemos todo esto de forma secuencial dentro de la caja del Action CreateProjectAction… ¿sabes qué va a pasar cuando programemos esto?

Que el usuario hará clic en “Crear”, y se quedará mirando la pantalla de carga durante 4 o 5 segundos mientras el servidor espera a que las APIs de correo y Slack respondan.

Sí, acabamos de diseñar un cuello de botella.

El problema del acoplamiento oculto

Cuando diseñas una Action para que haga su trabajo principal (crear el proyecto) pero además le otorgas la responsabilidad de disparar efectos secundarios (emails, notificaciones, sincronizaciones), estás violando el principio de responsabilidad única por la puerta de atrás.

La solución para diseñar un sistema que escale, sin que los tiempos de respuesta se disparen, se llama Arquitectura Orientada a Eventos o Event-Driven Architecture.

En lugar de que la Action se encargue de todo, su única responsabilidad será hacer su trabajo principal y comunicar al resto que lo ha hecho.

Estos son los 3 pilares de comunicación interna que he dejado definidos en el documento de arquitectura de KPIAds:

1. Domain Events

Un Evento de Dominio no es una acción, es un hecho. Describe algo que ya ha pasado en el sistema.

En nuestro diseño, por ejemplo, hemos definido el evento ProjectCreated.

A partir de ahora, la Action guarda el proyecto y simplemente “dispara” este evento.

Inmediatamente después, devuelve la respuesta al usuario.

Tiempo de espera diseñado: 0.1 segundos, de esta forma el usuario no espera por procesos de terceros.

2. Listeners y Jobs

Pero claro, el email hay que enviarlo… ¿Quién lo diseña?

Para esto tendremos que definir Listeners (oyentes).

Se tratan de cajas en nuestra arquitectura que están escuchando por si alguien grita ProjectCreated.

Es decir, es un trozo de nuestro sistema que está todo el rato pendiente de que alguna otra parte del sistema comunique que ha creado el proyecto (Domain Event).

Pero como enviar un email bloquea el sistema, el Listener no lo envía directamente.

Su única función es empaquetar esa tarea en un Job y tirarlo a una cola de trabajo para que se procese luego.

3. Colas con Redis + Horizon (La infraestructura asíncrona)

Esos Jobs no se ejecutarán en el mismo proceso que atiende al usuario.

Para KPIAds, la decisión de diseño es usar Redis (una base de datos en memoria ultrarrápida) para gestionar estas colas.

Por detrás, habrá Workers (procesos en segundo plano) cogiendo esos trabajos uno a uno.

Y para gobernar todo esto sin ir a ciegas, la pieza clave de monitorización que hemos elegido es Laravel Horizon.

Diagrama y Contratos de Diseño

Como aún no hemos escrito una sola línea de código en el IDE, así es como se ve este flujo en nuestros documentos de diseño. Fíjate en la diferencia entre el tiempo que espera el usuario y lo que pasa por detrás:

Y para que las distintas capas se comuniquen sin acoplarse, en lugar de código PHP, lo que definimos en esta fase son los contratos: qué información viaja en cada paso para que los servicios sean independientes.

[ Acción ] -> CreateProjectAction
Responsabilidad: Escribir en BBDD y emitir evento.

[ Evento de Dominio ] -> ProjectCreated
Payload requerido:
  - project_id (UUID)
  - user_id (UUID)
  - timestamp_creacion

[ Listener ] -> SetupProjectDefaults
Responsabilidad: Escuchar 'ProjectCreated' y despachar Jobs.
Acciones:
  - dispatch(GenerateMetricsJob, payload: project_id)
  - dispatch(SendWelcomeEmailJob, payload: user_id)

Y bueno, hasta aquí la entrega de hoy del desarrollo de mi SaaS para controlar el gasto y rendimiento publicitario.

Quiero que tengas claro con esta entrega en una (de muchas) diferencias entre un programador Junior y uno Senior.

Un perfil Junior se pone a escribir código y mete el envío del email en el controlador para ver si funciona.

Un perfil Senior se sienta primero con un papel, dibuja las cajas y se asegura de que el envío del email no hunda el rendimiento de la aplicación entera.

Diseñar el sistema con Eventos y Colas desde el principio marca la diferencia entre una aplicación frágil y un software preparado para miles de usuarios.

¿Te ha quedado clara esta separación de conceptos en la fase de diseño?

¿Quieres que la semana que viene pasemos ya a ver cómo se traduce esto a código real en el editor?

Nos vemos en la próxima entrega.

Julián

Publicado originalmente en CERO a SENIOR.

Volver a newsletter

CONTACTO

¿Hablamos de tu proyecto?

Si has llegado hasta aquí, es que algo de lo que has leído tiene sentido para ti. Rellena el formulario, te llevará menos de 1 minuto (según mis cálculos o incluso menos) y organizamos una llamada para darle forma.

  • En 48h laborables tendrás una respuesta en tu bandeja de entrada.
  • Si soy la persona adecuada, nos ponemos cara en una llamada para entender bien qué necesitas.
  • Trabajo con pocos proyectos a la vez. Prefiero hacer pocas cosas bien que muchas regular.

Paso 1 de 3

Paso 2 de 3

Paso 3 de 3

¡Buena jugada!

Tu formulario ha llegado. Ahora me toca a mí hacer el siguiente movimiento.

En menos de 48h (laborables) tendrás mi respuesta en tu buzón. No será una respuesta automática ni una propuesta a base de plantillazo. Me lo miro al detalle, lo analizo y te cuento.

Y mientras esperas mi respuesta…

Y mientras esperas mi respuesta…
Te cuento que en 2012 jugué en el Open Internacional de Sevilla contra el Gran Maestro Vladim Malakhatko (hasta salió en el ABC). Yo con negras. Me ganó, pero no encontró la jugada que le aseguraba ganarme una calidad y, casi seguro, la partida.
¿La encuentras tú antes de que yo te responda?

Arrastra una pieza para probar tu jugada

¿La encuentras tú antes de que yo te responda? [bajo el tablero] Toca mover negras y ganan la jugada

Julián Campos

Consultoría técnica, WordPress, integraciones, migraciones y formación para empresas que necesitan criterio senior.

Hablemos

NAVEGACIÓN

  • Inicio
  • Servicios
  • Sobre mí
  • Casos de éxito
  • Blog
  • Contacto

SERVICIOS

  • Consultoría técnica y Fractional CTO
  • Desarrollo WordPress
  • Integraciones y automatización
  • Migraciones de plataformas
  • Formación técnica

REDES

  • LinkedIn
  • X
  • GitHub
© 2026 Julián Campos
  • Privacidad
  • Cookies
  • Legal