Output Guardrail
Reject responses under 20 characters with a post-hook that raises OutputCheckError.
"""
Output Guardrail
=============================
Output Guardrail.
"""
from agno.agent import Agent
from agno.exceptions import CheckTrigger, OutputCheckError
from agno.models.openai import OpenAIResponses
from agno.run.agent import RunOutput
def enforce_non_empty_output(run_output: RunOutput) -> None:
"""Reject empty or very short responses."""
content = (run_output.content or "").strip()
if len(content) < 20:
raise OutputCheckError(
"Output is too short to be useful.",
check_trigger=CheckTrigger.OUTPUT_NOT_ALLOWED,
)
# ---------------------------------------------------------------------------
# Create Agent
# ---------------------------------------------------------------------------
agent = Agent(
name="Output-Checked Agent",
model=OpenAIResponses(id="gpt-5.2"),
post_hooks=[enforce_non_empty_output],
)
# ---------------------------------------------------------------------------
# Run Agent
# ---------------------------------------------------------------------------
if __name__ == "__main__":
agent.print_response("Summarize the key ideas in clean architecture.", stream=True)Guardrail InputCheckError and OutputCheckError become failed run outputs. They are not caught by the source's try/except around print_response() or aprint_response(). Use run() or arun() and check the returned status before displaying content or declaring success.
Add this helper after your imports:
from agno.run import RunStatus
def show_checked_response(response) -> None:
if response.status != RunStatus.completed:
print(f"Run rejected or failed ({response.status.value}).")
return
print(response.content)A generic failed status can also indicate a provider error. Nonstream run outputs do not expose a check_trigger field. Output rejected by a post-hook can remain in the run record; this helper withholds it from the display. Streaming content may already have been emitted before the post-hook runs.
Check output before displaying it
Add the helper above and replace the original if __name__ == "__main__" block with:
if __name__ == "__main__":
show_checked_response(agent.run('Summarize the key ideas in clean architecture.'))This checks the final status before displaying the answer. It does not retract streamed content or erase rejected content from stored runs.
Run the Example
Set up your virtual environment
uv venv --python 3.12
source .venv/bin/activateInstall dependencies
uv pip install -U agno openaiExport your OpenAI API key
export OPENAI_API_KEY="your_openai_api_key_here"Apply the current checks
Add the status helper and apply the replacements described above. Keep the original imports and agent definitions that the replacement uses.
Run the example
Save the adapted code as output_guardrail.py, then run:
python output_guardrail.pyFull source: cookbook/02_agents/08_guardrails/output_guardrail.py