How AgentGate Works
A technical deep dive into the AgentGate Policy Decision Point — architecture, trust scoring, and enforcement mechanisms.
Architecture Overview
AgentGate is a Policy Decision Point (PDP) that sits between the agent runtime and any tool, API, or resource. Before any agent action executes, the SDK makes a synchronous authorization call to the AgentGate server.
On PERMIT: the SDK returns normally and the agent proceeds. On DENY: the SDK raises AgentGateDenied before the agent touches the resource. On ESCALATE: the call blocks until a human approves or denies via the real-time dashboard.
The 4-Dimensional Trust Score
Every authorization request is scored across four dimensions. The composite score is a weighted sum. Sensitivity thresholds determine the required score: LOW=40, MEDIUM=60, HIGH=75, CRITICAL=90.
Identity Verification
weight: 25%Validates cryptographic tokens issued at registration. Checks that the action falls within the agent's registered authorized_resources and authorized_actions scope. An agent attempting to access /confidential/salary.txt when only authorized for /reports/* fails immediately.
Must pass — binary gate before composite score
Delegation Chain Integrity
weight: 25%When Agent A delegates a task to Agent B, AgentGate traverses the full delegation chain. Every ancestor's declared scope is checked. If Agent A can only read reports, Agent B cannot inherit write access — regardless of what Agent B claims its purpose is.
Chain length penalized: depth 0=1.0, depth 1=0.85, depth 2=0.65
Purpose Alignment
weight: 30%Uses sentence transformer embeddings (all-MiniLM-L6-v2) to compute cosine similarity between the agent's declared purpose at registration and the requested action+resource. A report summarizer trying to read salary data will score low on purpose alignment.
Cosine similarity < 0.3 is a strong DENY signal
Behavioral Anomaly Detection
weight: 20%Tracks per-agent request rates with exponential moving average baselines. Velocity spikes above 2.5x the agent's established baseline trigger ESCALATE. Global fallback threshold: 20 RPM until 10+ requests establish a baseline.
Spike >2.5x baseline triggers ESCALATE regardless of other scores
Decision Outcomes
Composite trust score meets the resource's sensitivity threshold. Action proceeds.
Score is borderline, or a behavioral anomaly was detected. Human-in-the-loop review required. Action is blocked until a human approves or denies via the dashboard.
Trust score is below threshold, scope violation detected, or critical keywords in resource path (salary, credential, private_key, etc.). Action never executes.
ESCALATE cases awaiting human decision. SDK auto-resolves by default: blocks and polls until approval/denial or 90-second timeout (auto-DENY).
Python SDK Usage
from agentgate import AgentGate
# Initialize client
gate = AgentGate(
"http://localhost:8000",
api_key="your-key",
raise_on_deny=True, # raises AgentGateDenied on DENY
raise_on_escalate=False, # returns ESCALATE result, doesn't raise
auto_resolve_pending=True, # blocks until human approves/denies
pending_timeout=95, # seconds before auto-DENY
)
# Register agent with explicit scope
gate.register(
agent_id="report_bot_001",
name="ReportBot",
declared_purpose="Read and summarize quarterly business reports",
authorized_resources=["/reports/*", "/documents/public/*"],
authorized_actions=["read", "search"],
delegation_depth=0,
processes_external_content=False, # enable prompt injection scanning
requires_human_approval=False,
)
# Check before each action
try:
result = gate.authorize(
action="read",
resource="/reports/q3.pdf",
justification="User requested Q3 summary",
)
print(result["decision"]) # PERMIT
print(result["trust_breakdown"]) # {"identity": 0.92, "delegation": 1.0, ...}
print(result["explanation"]) # Human-readable reasoning
except AgentGateDenied as e:
print(f"Blocked: {e}") # Agent never touches the resource
# Context manager pattern
with gate.operation("read", "/reports/q4.pdf"):
data = open("/reports/q4.pdf").read() # only runs if PERMIT
# Decorator pattern
@gate.guard("read", resource_arg="path")
def read_document(path: str) -> str:
return open(path).read()