Trust center · Security overview
Every claim, mapped to evidence.
Architecture deep-dive lives at /security; this page is what you skim before scheduling a vendor review call. Each claim links to the code, test, or doc you can verify for yourself.
Authentication & access
- ✓
API keys are scrypt-hashed at rest
Keys never round-trip a plaintext value through any storage layer. Hash params (N=2^15, r=8, p=1) live alongside the hash so verification is straightforward. A database breach surfaces hashes, not credentials.
apps/server/src/lib/api-keys.ts · hashApiKey() / verifyApiKey()
- ✓
MFA: TOTP + recovery codes
AES-256-GCM at-rest encryption of TOTP secrets. Recovery codes are scrypt-hashed (mirroring API key handling). Step-up gate (V-353e) requires MFA on destructive admin paths.
apps/server/src/lib/mfa-totp.ts · apps/server/src/services/mfa.ts
- ✓
OAuth 2.0 (invite-only) with PKCE-S256
Third-party OAuth requires admin invitation (no self-service client registration). PKCE-S256 mandatory; client_secret sha256-hashed at rest; one-shot authorization codes; opaque bearer tokens (no JWT).
apps/server/src/services/oauth.ts · apps/server/src/lib/oauth-pkce.ts
- ✓
BYOK Anthropic keys + gui_control_keys + Mac LiveKit secrets: AES-256-GCM at rest
Three classes of plaintext-equivalent secret material live in AES-256-GCM ciphertext under the same host-resident encryption key as MFA TOTP secrets: (1) customer-supplied Anthropic API keys when used as the BYOK LLM rail for agent sessions; (2) per-session gui_control_keys (HMAC keys for the gui_control plane); and (3) per-Mac LiveKit API secrets registered via POST /v1/mac-nodes/register (LK.2 — used by the control plane to mint the per-session JWTs that the gui-client uses to subscribe to live video). All three are decrypted in-memory only at execution time, never logged, never echoed in responses. Pino-redact + Sentry- scrub guard against accidental leak across both log + error paths.
apps/server/src/services/byok-anthropic.ts · apps/server/src/lib/byok-anthropic-encryption.ts · apps/server/src/lib/livekit-secret-encryption.ts
Transport & egress
- ✓
TLS 1.3 on every customer-facing path
Cloudflare edge enforces TLS 1.3 strict to the
api.driftstack.dev+app.driftstack.devorigins. No plaintext HTTP on any path; the deploy pipeline's TLS check rejects the release otherwise. - ✓
Customer-configurable egress (per profile)
Each profile can attach its own egress: SOCKS5 with full UDP/WebRTC/QUIC tunnelling, OpenVPN (.ovpn), or WireGuard (.conf). Sessions bound to the profile dial the tunnel before launching the browser; DNS leaks blocked. Without an attached config, session traffic exits via Driftstack's own EU network egress. Driftstack does not log session-traffic payloads (destination URLs / response bodies); the proxy layer forwards bytes without persisting them.
Webhooks & integrations
- ✓
Outbound webhooks are HMAC-SHA256 signed
Every webhook delivery carries
X-Driftstack-Signaturewith timestamp + body HMAC. Customers verify via the SDK helper; replay attacks rejected via timestamp tolerance window.apps/server/src/lib/webhook-signing.ts
- ✓
Inbound webhooks (Stripe, NowPayments) signature-verified before any state mutation
Stripe: V-080 timestamp+sha256 HMAC. NowPayments: V-487 HMAC-SHA512 on canonical-keyed JSON. Shared raw-body parser ensures the bytes the signature was computed over are the bytes the verifier sees.
apps/server/src/lib/stripe-signing.ts · apps/server/src/lib/nowpayments-signing.ts
Data residency & retention
- ✓
EU-only data plane
Compute (Hetzner Nuremberg), database (Neon Frankfurt), object storage (Cloudflare R2 EU jurisdiction). Full sub-processor list at /trust/sub-processors.
- ○
Capture retention (roadmap)
Today's API returns capture bytes inline; there is no server-side capture retention layer to configure. Session recordings + their retention controls land with V-540 — see /docs/recordings.
- ✓
Account deletion: 30-day grace, then hard delete
Cancellation triggers soft-delete with 30 days of recovery. After that: hard delete of profile data, sessions, captures. Per our DPA.
Observability & incident response
- ✓
Public incident history + status page
Customer-impacting outages are posted publicly within the incident-response SLA window. Live status at status.driftstack.dev; historical archive at /trust/incidents.
- ✓
Vulnerability disclosure: 2-day ack, 5-day triage
Safe-harbour for good-faith research. Coordinated disclosure window: 90 days, extendable on agreement. Full policy at /trust/compliance.
- ✓
Chaos engineering rehearsal harness
Sub-processor outages, DB failover, Redis-down, webhook-signature failures — all covered by scripted drills in
scripts/chaos/. Drills run dry-run by default; execute mode requires explicit operator opt-in.scripts/chaos/
Still need a deeper look?
The architecture deep-dive at /security walks the five-pillar surface in detail. For pen-test evidence or compliance certifications, see /trust/compliance. Anything else, just email.