{"openapi":"3.1.0","info":{"title":"Agent Email Protection Gateway","description":"Inbound + outbound prompt-injection protection for AI email agents. Vendor-neutral API over a swappable detection core.","version":"0.1.0"},"paths":{"/v1/health":{"get":{"summary":"Health","operationId":"health_v1_health_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HealthResponse"}}}}}}},"/v1/inbound/scan":{"post":{"summary":"Inbound Scan","operationId":"inbound_scan_v1_inbound_scan_post","parameters":[{"name":"authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InboundScanRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/InboundScanResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/v1/outbound/review":{"post":{"summary":"Outbound Review","operationId":"outbound_review_v1_outbound_review_post","parameters":[{"name":"authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OutboundReviewRequest"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/OutboundReviewResponse"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/v1/usage":{"get":{"summary":"Usage Endpoint","description":"The calling tenant's usage today + its limits.","operationId":"usage_endpoint_v1_usage_get","parameters":[{"name":"authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Usage Endpoint V1 Usage Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/v1/metrics":{"get":{"summary":"Metrics Endpoint","description":"Global in-process metrics (admin-only — aggregates span all tenants).","operationId":"metrics_endpoint_v1_metrics_get","parameters":[{"name":"authorization","in":"header","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authorization"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"title":"Response Metrics Endpoint V1 Metrics Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}}},"components":{"schemas":{"DlpFinding":{"properties":{"kind":{"type":"string","title":"Kind"},"excerpt":{"type":"string","title":"Excerpt"},"span":{"prefixItems":[{"type":"integer"},{"type":"integer"}],"type":"array","maxItems":2,"minItems":2,"title":"Span"}},"type":"object","required":["kind","excerpt","span"],"title":"DlpFinding"},"HTTPValidationError":{"properties":{"detail":{"items":{"$ref":"#/components/schemas/ValidationError"},"type":"array","title":"Detail"}},"type":"object","title":"HTTPValidationError"},"HealthResponse":{"properties":{"status":{"type":"string","title":"Status"},"core":{"type":"string","title":"Core"},"core_live":{"type":"boolean","title":"Core Live"},"version":{"type":"string","title":"Version"},"extras":{"additionalProperties":true,"type":"object","title":"Extras"}},"type":"object","required":["status","core","core_live","version"],"title":"HealthResponse"},"InboundScanRequest":{"properties":{"raw_email":{"type":"string","title":"Raw Email","description":"Raw email body. HTML or plain text; MIME parts may be concatenated."},"content_type":{"type":"string","title":"Content Type","description":"text/html or text/plain","default":"text/html"},"subject":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Subject","description":"Subject line — also scanned (a known injection vector)."},"extra_untrusted":{"items":{"type":"string"},"type":"array","title":"Extra Untrusted"}},"type":"object","required":["raw_email"],"title":"InboundScanRequest"},"InboundScanResponse":{"properties":{"verdict":{"$ref":"#/components/schemas/Verdict"},"score":{"type":"number","maximum":1.0,"minimum":0.0,"title":"Score","description":"Aggregated injection-risk score, 0..1"},"reasons":{"items":{"type":"string"},"type":"array","title":"Reasons"},"signals":{"items":{"$ref":"#/components/schemas/Signal"},"type":"array","title":"Signals"},"sanitized_text":{"type":"string","title":"Sanitized Text","description":"Normalized, de-obfuscated, hidden-content-stripped text."},"spotlighted_text":{"type":"string","title":"Spotlighted Text","description":"Sanitized text wrapped as inert DATA for the downstream agent."},"core":{"type":"string","title":"Core","description":"Which commercial/OSS core produced the ML score."}},"type":"object","required":["verdict","score","reasons","signals","sanitized_text","spotlighted_text","core"],"title":"InboundScanResponse"},"OutboundReviewRequest":{"properties":{"message":{"type":"string","title":"Message","description":"The agent's proposed outbound content (email body / tool args)."},"content_type":{"type":"string","title":"Content Type","description":"text/html or text/plain","default":"text/html"},"recipients":{"items":{"type":"string"},"type":"array","title":"Recipients","description":"Proposed recipients — checked against allowlist."},"inbound_risk":{"$ref":"#/components/schemas/Verdict","description":"The verdict from the inbound mail that triggered this action (taint). If the flow touched untrusted mail, outbound is gated harder.","default":"allow"},"action":{"type":"string","title":"Action","description":"send_email | forward | reply | delete | calendar_write | other","default":"send_email"},"user_goal":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"User Goal","description":"The user's original instruction/goal — enables action-alignment checks (does this send actually advance what the user asked for?)."}},"type":"object","required":["message"],"title":"OutboundReviewRequest"},"OutboundReviewResponse":{"properties":{"decision":{"$ref":"#/components/schemas/Verdict"},"reasons":{"items":{"type":"string"},"type":"array","title":"Reasons"},"clean_message":{"type":"string","title":"Clean Message","description":"Message with exfil channels stripped/rewritten."},"dlp_findings":{"items":{"$ref":"#/components/schemas/DlpFinding"},"type":"array","title":"Dlp Findings"},"stripped_links":{"items":{"type":"string"},"type":"array","title":"Stripped Links","description":"Auto-loading images / suspicious links removed or rewritten."},"requires_human":{"type":"boolean","title":"Requires Human","description":"True when an irreversible action must be human-confirmed.","default":false},"core":{"type":"string","title":"Core"}},"type":"object","required":["decision","reasons","clean_message","dlp_findings","stripped_links","core"],"title":"OutboundReviewResponse"},"Signal":{"properties":{"code":{"type":"string","title":"Code"},"detail":{"type":"string","title":"Detail"},"weight":{"type":"number","title":"Weight","default":0.0}},"type":"object","required":["code","detail"],"title":"Signal","description":"A single piece of evidence that fed the verdict (for explainability)."},"ValidationError":{"properties":{"loc":{"items":{"anyOf":[{"type":"string"},{"type":"integer"}]},"type":"array","title":"Location"},"msg":{"type":"string","title":"Message"},"type":{"type":"string","title":"Error Type"},"input":{"title":"Input"},"ctx":{"type":"object","title":"Context"}},"type":"object","required":["loc","msg","type"],"title":"ValidationError"},"Verdict":{"type":"string","enum":["allow","flag","block"],"title":"Verdict"}}}}