Quick Start
1
Allowlist — drop messages from unknown senders
2
PII redaction — rewrite content before the LLM sees it
How It Works
Decision Table
Supported Adapters
Every built-in messaging adapter honours the gate decision:Custom adapters must call
fire_message_received and check the returned drop / content fields to participate in the gate.Common Patterns
Allowlist
Rate Limiter
Keyword Ban
Combined Gate + Redaction
- Blocked user’s messages: agent stays silent, no reply sent.
- Messages containing an SSN pattern: LLM sees
[SSN]instead of the digits. - All other messages: unchanged.
User Interaction Flow
A Telegram user sends a message. The gate runs before the agent responds:Symmetry with Outbound
MESSAGE_RECEIVED (inbound) and MESSAGE_SENDING (outbound) share the same deny / modified_input contract. Use the same pattern for both directions:
Best Practices
Keep the gate cheap
Keep the gate cheap
The hook runs on every inbound message. Avoid blocking I/O or heavy computation — use in-memory lookups and pre-compiled regex patterns.
Fail-open, not fail-closed
Fail-open, not fail-closed
Raising an exception lets the message through. Explicitly call
HookResult.deny(...) if you mean to block.Mutate content only for redaction
Mutate content only for redaction
The LLM will see the
modified_input content and may quote it back in replies. Only rewrite when necessary (e.g. PII scrubbing).Use deny for hard blocks, not redaction
Use deny for hard blocks, not redaction
deny prevents agent dispatch entirely. modified_input still dispatches — use it only when you want the agent to respond to the sanitised content.Related
Hook Events
Complete reference for all hook events and input types
Bot Lifecycle Hooks
Gateway, session, and schedule lifecycle hooks

