Static evaluateEvaluate user input through registered guardrails using two-phase execution.
Phase 1 (Sequential — sanitizers):
Guardrails with config.canSanitize === true run one-at-a-time in
registration order. Each sees (and may modify) the cumulative sanitized
input. A BLOCK result short-circuits immediately — Phase 2 never runs.
Phase 2 (Parallel — classifiers):
All remaining guardrails run concurrently via Promise.allSettled on
the text produced by Phase 1. A Phase 2 SANITIZE is downgraded to FLAG.
Aggregation: worst-wins (BLOCK > FLAG > ALLOW). The singular
evaluation field is set to the first BLOCK, else the worst-severity
evaluation, else the last evaluation by registration order.
Array of guardrail services (already normalized)
User input to evaluate
Conversational context for policy decisions
Outcome with sanitized input and all evaluations in registration order
Static wrapWrap a response stream with two-phase guardrail filtering.
Partitions services into four groups (once, up front):
canSanitize && evaluateStreamingChunks)evaluateStreamingChunks && !canSanitize)canSanitize && !evaluateStreamingChunks)evaluateOutput)For each TEXT_DELTA chunk: Phase 1 runs streaming sanitizers sequentially (with per-service rate limiting), then Phase 2 runs streaming classifiers in parallel.
For each isFinal chunk: Phase 1 runs final sanitizers sequentially, then
Phase 2 runs final classifiers in parallel. All services with
evaluateOutput participate in final evaluation.
A BLOCK in either phase terminates the stream immediately with an error chunk.
Array of guardrail services (already normalized)
Conversational context for policy decisions
Source response stream to filter
Stream options and input evaluations to embed
Wrapped async generator with guardrail filtering applied
Stateless two-phase parallel guardrail dispatcher.
All methods are static — no instantiation needed. The class exists purely as a namespace to keep the two public entry points grouped.