Security
Agentend takes a defense-in-depth approach to security. The PALADIN system provides 5 layers of injection defense, while the auth module handles identity verification and the guardrails module validates inputs and outputs.
PALADIN — 5-layer injection defense
PALADIN (Proactive Agent-Layer Anti-injection Defense INfrastructure) is a multi-layer system that detects and neutralizes injection attacks before they reach the LLM. Layer 1 — the InputSanitizer — runs on every incoming request.
Layer 1: Input sanitization
The InputSanitizer strips control characters, removes known injection patterns, and validates input length. It detects and blocks:
- •Script injection —
<script>,<iframe>,<object>tags - •Protocol abuse —
javascript:anddata:text/htmlURIs - •Event handler injection — inline
on*=attributes - •Template injection —
${...}and{{...}}patterns - •Code execution —
exec(),eval(),__import__ - •SQL injection — UNION, SELECT, INSERT, UPDATE, DELETE, DROP, CREATE, ALTER keywords
- •Shell injection — command chaining (
; rm), pipe to shell, backtick substitution,$()expansion
from agentend.security.sanitizer import InputSanitizer
sanitizer = InputSanitizer(
max_length=100000,
allow_html=False,
allow_sql=False,
allow_shell=False,
)
# Sanitize user input
clean = sanitizer.sanitize(user_input)
# Check for injection patterns
patterns = sanitizer.has_injection_patterns(user_input)
if patterns:
log.warning(f"Detected injection patterns: {patterns}")Layer 2: Prompt armoring
System prompts are wrapped with injection-resistant delimiters and instructions that tell the LLM to ignore overrides embedded in user input.
Layer 3: Output validation
Agent responses are scanned for leaked system prompts, PII, and hallucinated tool calls before being sent to the client.
Layer 4: Tool call validation
Tool calls are validated against a whitelist of allowed tools and argument schemas before execution. This prevents the LLM from invoking tools it should not have access to or passing malicious arguments.
Layer 5: Behavioral monitoring
Runtime monitoring detects anomalous patterns like repeated tool calls, unusual output lengths, or attempts to exfiltrate data through side channels.
Authentication
Agentend supports three authentication methods, configured in fleet.yaml:
| Method | Description |
|---|---|
| JWT | JSON Web Tokens with configurable secret and algorithm (default: HS256) |
| OAuth2 | External OAuth2 provider with client ID/secret |
| API Key | Header-based API key validation (default header: X-API-Key) |
# fleet.yaml
auth:
enabled: true
provider: jwt
jwt:
secret: ${JWT_SECRET}
algorithm: HS256Per-capability RBAC
Role-Based Access Control restricts which capabilities a user can invoke. Roles are extracted from the JWT claims and matched against capability requirements at dispatch time.
Guardrails
The guardrails module provides configurable input and output validation:
| Guardrail | Direction | Description |
|---|---|---|
| max_length | Input | Maximum input length (default: 10,000 chars) |
| sanitize_html | Input | Strip HTML tags from input |
| check_pii | Output | Detect personally identifiable information in responses |
| check_toxicity | Output | Check for toxic or harmful content |
| redact_sensitive | Output | Redact sensitive data (keys, passwords, etc.) |
Multi-tenant RLS
Agentend uses PostgreSQL Row-Level Security (RLS) to enforce data isolation between tenants. Every database query is automatically scoped to the authenticated tenant. This is enforced at the persistence layer via SQLAlchemy 2.0 async models, so there is no way to accidentally query another tenant's data.