Authentication
Developer Reference
This page covers internal implementation details. It is not included in the User Guide.
Escher uses a layered authentication model: Cognito OIDC for end-user access, OS Keychain isolation for cloud credentials, and internal network isolation for service-to-service calls.
Architecture overview
Desktop App ──OIDC token──▶ ALB (Cognito listener rule)
│
Gateway ─────────────────────────────────┐
│ internal network (Cloud Map DNS) │
┌────────┼──────────┐ │
▼ ▼ ▼ │
Analysis Playbook Context │
Agent Agent Engine ──▶ Asset Store │
│
SurrealDB ◀───┘No service-to-service bearer tokens. Backend components communicate over the private VPC subnet, addressed via AWS Cloud Map DNS (*.escher.internal). Network-level isolation is the security boundary between services.
End-user authentication (desktop app)
The Escher desktop app authenticates users through AWS Cognito with the OIDC authorization code flow.
Flow
- On first launch, the desktop app opens a browser window to the Cognito Hosted UI.
- The user logs in (email/password or SSO identity provider).
- Cognito returns an authorization code. The app exchanges it for
id_token,access_token, andrefresh_token. - Tokens are stored in the OS Keychain via the
v2-tauri-plugin-vaultRust plugin — never written to disk. - The
v2-auth-libraryTypeScript package manages the token lifecycle: refresh before expiry, re-prompt on refresh failure.
Token format
| Token | Type | Used for |
|---|---|---|
id_token | JWT (RS256) | User identity claims — sub, email, groups |
access_token | JWT (RS256) | Sent as Authorization: Bearer to Gateway |
refresh_token | Opaque | Exchanged for new access_token before expiry (TTL 30 days) |
Gateway verification
The ALB Cognito listener rule validates the access_token signature before traffic reaches Gateway. Gateway receives a pre-validated JWT on every request. Gateway extracts sub and groups claims for tenant routing.
ALB listener rule:
action: authenticate-cognito
UserPoolArn: arn:aws:cognito-idp:us-west-1:ACCOUNT:userpool/POOL_ID
UserPoolClientId: CLIENT_ID
UserPoolDomain: escher-auth.auth.us-west-1.amazoncognito.com
OnUnauthenticatedRequest: denyService-to-service authentication
Production (ECS)
All backend services run inside a private VPC subnet and communicate via AWS Cloud Map service discovery. There are no service tokens, no mTLS certificates, and no inter-service Authorization headers.
| Service | DNS name (internal) | Port |
|---|---|---|
| Analysis Agent | analysis-agent.escher.internal | 8081 |
| Playbook Agent | playbook-agent.escher.internal | 8082 |
| Context Engine | context-engine.escher.internal | 8001 |
| Asset Store | asset-store.escher.internal | 8000 |
Security is enforced at the ECS task security group level — only Gateway's security group has egress permission to the agent ports, and only Context Engine has egress to Asset Store.
Local development (Docker Compose)
Same topology using localhost with fixed port assignments. See Docker Compose for port layout.
LLM API authentication
Analysis Agent and Integrations Agent call the Anthropic API directly using an API key.
# Analysis Agent (Go) — set in ECS task environment / .env locally
ANTHROPIC_API_KEY=sk-ant-...
# Integrations Agent (Go) — same pattern
ANTHROPIC_API_KEY=sk-ant-...
CLASSIFIER_MODEL=claude-haiku-4-5-20251001The API key is never passed to or through the Gateway. It is loaded by the agent process at startup from its ECS task definition environment variable (stored in AWS Secrets Manager, injected via secretsFrom in the task definition).
Cloud credential handling
Cloud credentials (AWS access keys, Azure tokens, GCP service account keys) are a separate concern from Escher service authentication:
- Storage: OS Keychain via
v2-tauri-plugin-vault(Rust, Tauri plugin) - Access: Only the local Tauri plugins (
v2-tauri-plugin-scanner,v2-tauri-plugin-estate) read credentials — they never leave the user's machine - Transmission: Cloud credentials are never sent to any Escher backend service. The desktop app executes all cloud API calls locally using the stored credentials.
- Profiles: Each profile has its own credential set; see Profiles
Summary
| Auth boundary | Mechanism | Where enforced |
|---|---|---|
| User → ALB | Cognito OIDC access_token | ALB listener rule |
| ALB → Gateway | ALB passes validated JWT | ALB/Gateway |
| Gateway → Agents | Internal VPC network | ECS security groups |
| Agents → Context Engine | Internal VPC network | ECS security groups |
| Context Engine → Asset Store | Internal VPC network | ECS security groups |
| Analysis Agent → Anthropic | ANTHROPIC_API_KEY header | Agent process |
| Desktop app → cloud | Local credentials from OS Keychain | Tauri plugins |
Next steps
- API Overview — Which APIs exist and who calls them
- ECS Deployment — Security group and VPC configuration
- Profiles — Cloud credential lifecycle