Skip to content

Bug: Output guardrail on supervisor agent causes SSE stream to never terminate #1415

Description

@WXWwangxinwei

Description

When an agent with sub-agents (supervisor pattern) has outputGuardrails configured, the SSE stream never terminates — the stream reaches the finish step but does not emit the finish event, and the controller never closes. The client hangs indefinitely waiting for the stream to end.

Reproduction

  1. Create a supervisor agent with sub-agents and output guardrails:
import { Agent } from "@voltagent/core";

const mainAgent = new Agent({
  name: "main",
  model: /* any model */,
  subAgents: [/* ... */],
  inputGuardrails: [/* works fine */],
  outputGuardrails: [
    {
      name: "output-sanitizer",
      execute: async ({ output }) => {
        // Simple pass-through or sanitization logic
        return { action: "modify", output };
      },
    },
  ],
});
  1. Call agent.streamText() or trigger via the built-in SSE server endpoint.

  2. Observe: the stream emits content chunks but never emits the finish event. The SSE connection stays open indefinitely. The client hangs.

Expected Behavior

When the model finishes generating and the output guardrail's execute returns, the stream should emit the finish event and close the SSE connection normally.

Actual Behavior

  • Stream reaches the finish step internally
  • No finish event is emitted to the client
  • SSE controller never closes
  • Client hangs indefinitely

Workaround

Remove outputGuardrails from supervisor agents. Input guardrails work correctly and do not cause this issue.

const mainAgent = new Agent({
  name: "main",
  model: /* any model */,
  subAgents: [/* ... */],
  inputGuardrails: [/* works fine */],
  // outputGuardrails: [/* REMOVED — causes SSE hang */],
});

Environment

  • @voltagent/core: 2.9.2 (also confirmed not fixed in 2.10.0)
  • Node.js: v22.18.0
  • OS: Windows 10 / Linux (Docker)

Additional Context

  • This only affects agents with sub-agents (supervisor pattern). Standalone agents with output guardrails appear to work fine.
  • inputGuardrails on the same supervisor agent work correctly.
  • This was tested with both streamText() and the built-in SSE server endpoint.
  • The closest related fix is PR fix(core,ag-ui): guard double writer.close() and RUN_FINISHED after RUN_ERROR #1135 (v2.6.5) which fixes a double writer.close() exception for agents with sub-agents, but it does not resolve this output guardrail issue.
  • createOutputGuardrail is still a documented feature with no caveat about supervisor incompatibility, so this appears to be an untracked defect rather than a known limitation.

Impact

Output content filtering (sensitive word sanitization, compliance checks, PII redaction) cannot be applied to supervisor agents, forcing users to implement workarounds (post-processing in onEnd hooks or SSE middleware) which are less clean and miss streaming-time interception.

No activity

Activity on this issue will appear here.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions