Skip to main content
Vorel handles customer PII on your behalf. This page documents the technical controls that protect that data: what’s in place today and what’s on the roadmap. For the formal compliance picture (DPA, certifications, regulator-facing language), see Compliance.

Multi-tenant isolation

Every Vorel customer (“tenant”) shares the same Postgres database. Cross-tenant data leakage prevention is a 4-layer defence:
1

Postgres Row-Level Security (RLS)

Every tenant-scoped table has a policy: rows are visible only when the row’s tenant_id matches the current request’s tenant context. The Vorel app connects as a non-superuser database role. Forgetting to set the tenant context returns zero rows: fail-closed by design.
2

Transaction-scoped tenant context

Every tenant-facing route opens a Postgres transaction and sets the current tenant context as the first statement. Exits cleanly on commit/rollback.
3

Operator-side admin lint

Operator-console reads use a separate database client that bypasses RLS by design (it’s used for cross-tenant operator views like the tenants list). Every such query MUST filter by tenant explicitly. Our CI runs a static check that flags any cross-tenant query without an explicit tenant filter and blocks the PR. Legitimate cross-tenant queries (e.g. listing all tenants) need an explicit annotation explaining why.
4

Append-only triggers

Three tables (messages, audit_log, billing_events) reject UPDATE + DELETE via Postgres triggers. Even if RLS were bypassed, mutation isn’t possible from the application’s database role.
This setup was pressure-tested in a 2026-05-01 internal cross-tenant-leak walkthrough; the static lint shipped same-day to close the failure-mode class.

Encryption

LayerMechanism
At rest (database)Disk-level encryption (managed by our hosting provider)
At rest (cache/queue)Disk-level encryption (managed by our hosting provider)
In transit (internal)TLS within the private hosting network
In transit (public)Edge-terminated TLS at app.vorel.ai (HSTS max-age=63072000; includeSubDomains; preload)
CRM credentialsAES-256-GCM, 12-byte random IV per row, master key from a secret-store environment variable. A KMS-backed envelope-encryption path (per-row DEK + KMS-wrapped KEK) is implemented in code but dormant today; it activates when KMS is configured.
Webhook outboundHMAC-SHA256 signed bodies (X-Webhook-Signature) + TLS to your URLs
Tenant API keysscrypt-hashed at rest (Node native, N=2^14, r=8, p=1, 64-byte derived key, per-key 16-byte salt); 58-char vapk_live_<48 hex> issuance shape; plaintext shown once at creation
JWTsHS256 over rotated shared secret, short TTL (5 min for tool calls, 2 min for worker calls)

Append-only audit

Three tables capture immutable audit trails:
  • messages: every conversation turn, immutable once written. Underpins the conversation transcript that QA scoring + analytics rely on.
  • audit_log: every operator-console read AND every mutation. Forensic trail for who-saw-what + who-did-what. Includes both operator actions (e.g. “claimed voice number for tenant X”) and reads (e.g. “operator opened tenant X’s CRM-credentials page”).
  • billing_events: every vendor cost-of-goods event (voice, telephony, and model spend per call) AND every chargeable event (per conversation, per minute). Immutable for accounting integrity.
Append-only is enforced via Postgres triggers: even superuser writes are blocked unless explicitly bypassed via a dedicated operator-side database role used for retention sweeps + the right-to-erasure path. Recent audit action additions cover the new architectural surfaces: pci_vault_redirect_issued / pci_vault_redirect_completed / pci_vault_redirect_failed (PCI vault-redirect payment flows), pci_enable_toggled / pci_vendor_changed (per-tenant PCI configuration), crm_as_sor_enforcement_disabled (per-tenant CRM-write enforcement override), and impersonation_started / impersonation_ended (operator view-as-tenant sessions).

Rate limiting

Vorel enforces a layered rate-limit stack to defend against floods, accidents, and runaway integrations:
LayerLimitWhere
Per-IP webhook500 req/min/api/webhooks/* (before signature verification)
Per-authenticated-user200 req/minAll authenticated dashboard surfaces
Per-API-key200 req/minEach issued vapk_* key has its own bucket
Per-(tenant, tool)50 req/minEach internal tool endpoint
Per-(tenant, agent-router)1000 req/minThe agent dispatch chokepoint
Per-tenant aggregate5000 req/minAcross all authenticated surfaces
Per-customer-number (chat)30 req/minWhatsApp inbound, post-payload-parse
Built on a fixed-window primitive backed by our in-memory data store, with a fail-open posture: a transient cache outage admits all traffic rather than 429-everyone. Plan-aware limits land at the call site when our billing model launches.

Right-to-access + right-to-erasure

Vorel ships first-class endpoints for PDPL Art. 15-17 + GDPR Art. 15-17:
  • POST /api/tenant/export (operator-gated): returns a ZIP of conversations + messages + leads + appointments + offerings + knowledge_base + audit_log for a single tenant. Default redaction: customer email + phone redacted; opt-out via include_full_pii=true (audit-logged). Includes a chain-of-custody README.
  • POST /api/tenant/forget (operator-gated, dry-run-by-default): runs a 7-step scrub for a single customer phone within a single tenant: tombstones conversations, redacts message content, nulls leads/appointments PII, scrubs audit-log JSONB references. Wrapped in a Postgres transaction for atomicity. Salted-hash audit-log references so the deletion event is provable without re-introducing the PII.
When a customer requests their data or asks to be forgotten, your operator routes the request through these endpoints + provides you with the resulting export ZIP or audit-log reference as proof of deletion.

SLOs

We maintain a set of 5 service-level objectives:
SLOTarget
Tool surface success rate99.9%
Voice call success rate99.5%
Voice turn p95 latency< 3s
Operator console availability99.9%
Outbound webhook delivery99.0% (within 6 attempts; backoff ladder [60s, 300s, 1800s, 7200s, 43200s])
A 4-state error-budget policy (healthy / caution / concern / exhausted) drives engineering response.

Observability + incident response

  • OpenTelemetry tracing exported to a managed observability backend for distributed tracing + custom metrics dashboards.
  • Centralized error monitoring for uncaught exceptions across web + workers.
  • Structured JSON logs with W3C trace-context propagation across every cross-process boundary (web, workers, and workflow automation).
  • app.vorel.ai/status: public status page with operator-curated incident banner.
  • Incident response playbook: sev definitions, RACI matrix, 6-phase response, tenant comms templates aware of PDPL Art. 17 + GDPR Art. 33’s 72-hour regulator-notification window.

Compliance posture

StandardStatus
PDPL (UAE Personal Data Protection Law)Designed to support PDPL obligations: PII inventory + DPA template + automated right-to-access + erasure paths are all live. Not a certification (PDPL has no certification scheme); the DPA template requires counsel review before signing
GDPRAligned with the same data-subject-rights paperwork posture. EU regions are captured as declared posture (tenant.region='eu'); per-region storage routing is on the roadmap, so EU-region data is hosted in our US region today and disclosed via the DPA
SOC 2Not yet certified. Foundational evidence is in place (PII inventory, data-flow diagram, incident-response playbook, control matrix, SLOs). SOC 2 Type 1 is targeted for Q4 2026, contingent on selecting and onboarding a compliance-automation platform (founder decision pending). A Type 2 follow-on may follow for enterprise customers
PCISAQ-A: outsourced vault-redirect payment processing; PAN/CVC/expiry never touch Vorel infrastructure; CI lint gate refuses DTMF imports on payment paths. See Payments + PCI
HIPAANot turn-key; available only via per-customer engagement (BAAs with all PHI-touching vendors). The clinic vertical pack ships with safety guards (forbidden_phrases='diagnose') but a HIPAA-grade workflow requires a separate engagement
CRM-as-SoRArchitecturally enforced: class-(c) transcript + PII tables purge on policy-locked TTL windows after CRM-write success. CI hard-fail gate refuses schema PRs that lack a class declaration. See Data retention
For the formal documents (DPA template, PII inventory excerpt for buyer DD, SLO commitments), see Compliance.

Bug bounty + disclosure

We don’t run a formal bug bounty today. To report a security issue: email security@vorel.ai with details. We’ll acknowledge within 48 hours, triage within 5 business days, and credit you in the changelog once fixed if you’re comfortable with disclosure. We do NOT use Vorel-collected customer data for any purpose other than running your tenant. We do NOT sell, share, or analyse customer data across tenants. We do NOT use customer conversations for training third-party AI models.