From c2e19b33717cb6a30b30590a8199ce67f250279e Mon Sep 17 00:00:00 2001 From: chahinebrini Date: Wed, 29 Jul 2026 19:47:11 +0200 Subject: [PATCH] =?UTF-8?q?feat(watch):=20--ignore-from=20=E2=80=94=20Noti?= =?UTF-8?q?fier=20nicht=20vom=20Watchdog=20zum=C3=BCllen=20lassen?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Der Architekten-Message-Notifier (`watch --await-message claude`) feuerte bei JEDER Nachricht — auch bei den Watchdog-Erinnerungen, die alle paar Minuten eintreffen ("review waiting 5m/10m/15m…"). Real erlebt: dreimal hintereinander geweckt worden, ohne dass etwas Neues passiert war. Ein Signal, das im Takt seiner eigenen Erinnerungen feuert, entwertet sich selbst. `--ignore-from ` blendet Absender aus; message-Events tragen dafür jetzt `from` (bisher nur im title). Armung des Architekten künftig mit `--ignore-from agenthub` — echte Agenten-Post weckt weiterhin sofort, die Watchdog-Erinnerungen sieht man beim Pollen ohnehin. Co-Authored-By: Claude Opus 5 (1M context) --- src/cli/commands/watch.ts | 14 ++++++++++---- src/cli/index.ts | 2 ++ src/server/events.ts | 2 ++ src/server/routes.ts | 1 + 4 files changed, 15 insertions(+), 4 deletions(-) diff --git a/src/cli/commands/watch.ts b/src/cli/commands/watch.ts index df78098..dc43365 100644 --- a/src/cli/commands/watch.ts +++ b/src/cli/commands/watch.ts @@ -168,10 +168,16 @@ async function fetchUnreadMessages(serverUrl: string, agent: string): Promise ignored.trim().toLowerCase() === sender); } /** @@ -188,7 +194,7 @@ function isMessageFor(event: AgentHubEvent, agent: string): boolean { */ export async function watchEvents( serverUrl: string, - options: { once?: boolean; role?: string; awaitReview?: boolean; awaitMessage?: string; newOnly?: boolean } = {}, + options: { once?: boolean; role?: string; awaitReview?: boolean; awaitMessage?: string; newOnly?: boolean; ignoreFrom?: string[] } = {}, ): Promise { const url = new URL('/events', serverUrl); // Pass role to the server for an additional server-side filter (saves @@ -280,7 +286,7 @@ export async function watchEvents( await reader.cancel(); return; } - if (options.awaitMessage && isMessageFor(event, options.awaitMessage)) { + if (options.awaitMessage && isMessageFor(event, options.awaitMessage, options.ignoreFrom)) { await reader.cancel(); return; } diff --git a/src/cli/index.ts b/src/cli/index.ts index 904e08d..b0af1d0 100644 --- a/src/cli/index.ts +++ b/src/cli/index.ts @@ -927,6 +927,7 @@ export function createProgram(cwd: string): Command { .option('--await-review', 'Exit when an implementer submits (task → review); architect review-queue notifier') .option('--await-message ', 'Exit when an unread message arrives for agent/role; architect message notifier') .option('--new-only', 'With --await-review/--await-message: ignore existing backlog on connect (re-armable without spinning)') + .option('--ignore-from ', 'With --await-message: comma-separated senders to ignore (e.g. "agenthub" to mute watchdog reminders)') .action(async (options) => { const { serverUrl } = await resolveContext(program, cwd); if (!serverUrl) { @@ -939,6 +940,7 @@ export function createProgram(cwd: string): Command { role: options.role as string | undefined, awaitReview: options.awaitReview as boolean | undefined, awaitMessage: options.awaitMessage as string | undefined, + ignoreFrom: typeof options.ignoreFrom === 'string' ? options.ignoreFrom.split(',') : undefined, newOnly: options.newOnly as boolean | undefined, }); }); diff --git a/src/server/events.ts b/src/server/events.ts index 50c55bf..5e7145a 100644 --- a/src/server/events.ts +++ b/src/server/events.ts @@ -15,6 +15,8 @@ export interface AgentHubEvent { status?: string; role?: string; assignedTo?: string; + /** Absender bei message-Events — erlaubt Empfängern, System-Post zu filtern. */ + from?: string; claimedBy?: string; reviewer?: string; } diff --git a/src/server/routes.ts b/src/server/routes.ts index 00fa18b..b674f7d 100644 --- a/src/server/routes.ts +++ b/src/server/routes.ts @@ -675,6 +675,7 @@ export async function registerRoutes(app: FastifyInstance, cwd: string): Promise id: message.id, title: `${message.from} → ${message.to}`, assignedTo: message.to, + from: message.from, }, message.updatedAt, );