El patrón Observer define un mecanismo de suscripción para notificar eventos a múltiples objetos interesados, sin acoplar al emisor con cada uno de ellos.
1. El Problema de Partida
Cuando se publica un nuevo artículo en content/knowledge/, hacen falta varias acciones independientes: revalidar la caché ISR de las rutas afectadas, registrar el evento en analítica interna y (opcionalmente) avisar por Slack. Meter las tres llamadas seguidas dentro de la misma función de publicación mezcla responsabilidades y obliga a tocar ese código cada vez que se añade un nuevo consumidor del evento.
2. La Solución Observer
Un PublishEventEmitter mantiene la lista de suscriptores; el publicador solo emite postPublished, sin saber quién ni cuántos escuchan.
// src/lib/events/PublishEventEmitter.js
class PublishEventEmitter {
listeners = [];
subscribe(listener) {
this.listeners.push(listener);
}
emit(event, payload) {
this.listeners.forEach((listener) => listener(event, payload));
}
}
export const publishEvents = new PublishEventEmitter();// src/lib/events/subscribers.js — cada observador es independiente
import { publishEvents } from './PublishEventEmitter';
publishEvents.subscribe((event, post) => {
if (event !== 'postPublished') return;
fetch(`/api/revalidate?path=/knowledge/${post.slugPath}`, { method: 'POST' });
});
publishEvents.subscribe((event, post) => {
if (event !== 'postPublished') return;
console.log(`[analytics] nuevo post publicado: ${post.slug}`);
});
publishEvents.subscribe((event, post) => {
if (event !== 'postPublished' || !post.notifySlack) return;
fetch(process.env.SLACK_WEBHOOK_URL, {
method: 'POST',
body: JSON.stringify({ text: `📄 Nuevo post: ${post.meta.title}` }),
});
});3. Uso al publicar
// scripts/publish-post.js
import { publishEvents } from '../src/lib/events/PublishEventEmitter';
async function publishPost(post) {
await writePostFile(post);
publishEvents.emit('postPublished', post); // Dispara a todos los suscriptores
}4. Ventajas
- Añadir un consumidor no toca
publishPost: basta con un nuevosubscribe(). - Cada observador falla de forma aislada: un error en el webhook de Slack no bloquea la revalidación de caché.
- Trazabilidad clara: todos los efectos secundarios de "publicar" viven en
subscribers.js, no dispersos en la lógica de negocio.