Compliance

The trust story your compliance lead reads in one sitting.

One short page for the finance, healthcare, government, legal, insurance and education buyers we now onboard. Where customer data lives. What gets logged and how long it is kept. Who can read it. And a one-line way to request the DPA, a privacy review, or signed terms — without a Slack thread.

Residency · managed
Audit-logged
30-day rolling
Read-only Graph
Single-tenant
01

Where Microsoft Graph refresh tokens and the issues_history table live

Two artefacts carry customer PII on the platform — the cached Microsoft Graph refresh token, and the issues_history table where the scan walker records every finding it surfaces. Each lives in a different layer, with a different residency story.

Microsoft Graph refresh-token cache

  • The cached refresh token is per-admin and scoped to the signed-in admin's own Entra tenant (via the offline_access scope). Token issuance and rotation both happen inside that tenant — Wardwell never holds a multi-tenant application token.
  • Rotation is driven by Microsoft's token endpoint, not by Wardwell's own cron. The cache is revoked at account deletion in the same transaction that purges the admin's rows (see §04).
  • The cached tokens sit alongside better-auth's session table on the same managed Postgres instance that hosts the scan rows — so data residency inherits the managed region declared by the platform's rdbms capability in polsia.toml.
See a live anonymized digestA concrete example of what a tenant receives each week.

issues_history · the rolling history table

  • The ScanFinding rolling-history table that backs the /issues page lives on the same managed Postgres instance, and inherits its managed region. Wardwell does not co-locate a database anywhere else.
  • There is one sub-processor for the database itself: the platform's rdbms capability declared in polsia.toml. No replication to a second region, no off-cluster export.
  • The data subject for GDPR purposes is the tenant admin who registered the app. No end-user personal contact data (no People API reads, no contact or calendar pulls, no Teams message inspection) is ever collected, so the per-finding rows do not carry end-user PII.
02

What audit logging captures on every scan

The platform is the source of truth for audit events. Each scan logs the same three artefacts — its wall-clock window, the per-issue list, and the per-finding history — and the better-auth session lifecycle stamps the surrounding sign-in events. Anyone answering an auditor can read all of it from one screen.

Scan      -> startedAt, completedAt, errorMessage
ScanIssue -> per-issue detail (one row per issue surfaced)
ScanFinding -> observedAt, lastSeenAt       (rolling history)
  • A Scan row records startedAt, completedAt, and any errorMessage — so an auditor can size the scan window without reading log output.
  • Each per-issue ScanIssue row carries the issue payload — broken-link candidate, redirect-chain picture, observed URL — so the trail from startedAt to a specific finding is queryable per scan run.
  • Per-finding ScanFinding rows carry observedAt and lastSeenAt, so an auditor following one broken-link case can confirm when it was first seen and when the acknowledgement stamp landed.
  • Better-auth stamps every sign-in, sign-out and refresh — along with the issuing IP and user agent — and every /api/issues read is itself timestamped, so the admin can see who pulled what and when.
03

Who can read those records

Every audit event — sign-in, sign-out, session refresh, scan run, case opened, finding acknowledged — surfaces inside the app rather than in a separate console. There is no second tool to provision, no separate grant of access, and no Slack thread to scroll.

  • Tenant admins read the audit surface inside the app on /issues — the same view they triage findings in. No PII payload, no separate log-shipper console.
  • Page-level access patterns (which /scan or /issues routes loaded, traversal order) come from polsia-analytics — without PII.
  • The Polsia ops team reads fewer of these rows for ops than a tenant admin reads for triage. Nothing outside the platform reads tenant scan data.
  • Sign-in forensicsship in the same surface: the admin's profile lists the better-auth session with issuance and revocation timestamps, so "who was signed in at 14:03 last Tuesday" is a single page away.
04

Retention windows

Three retention windows cover the audit surface — the rolling history on ScanFinding, the tenant-lifetime rows on Scan / ScanIssue, and the out-of-band digest email that bridges the rolling window.

What this is — and is not

  • The 30-day window covers the per-finding rolling history only — ScanFinding rows. The parent Scan and the per-scan ScanIssue rows stay for as long as your tenant is on board; they are not part of the rolling window.
  • A weekly digest email (jobs/weekly-issues-digest.js) ships the same finding rows out of band before the rolling window prunes them, so the audit trail lives in the inbox even after it leaves the table.
  • Account deletion is one transaction: User, Scan, ScanIssue, ScanFinding, Session, and WaitlistEntry rows are purged, and the cached Graph refresh token is revoked at the same time.
  • The cron schedule is declared versioned in polsia.toml alongside the schema, so any change to the window is a reviewable diff against the deployment record.
05

Sub-processors

Three names appear on the data-flow diagram, in this order: Polsia, Stripe, and Microsoft. Only the first two are Polsia-side sub-processors receiving customer scan data — Microsoft operates the identity layer on the customer's own Entra tenant.

Sub-processor list · what leaves Wardwell

  • Polsia— operates the platform, including the managed Postgres instance declared by the platform's rdbms capability in polsia.toml. The Scan, ScanIssue, ScanFinding, better-auth session, and waitlist rows all live here.
  • Stripe — processes payments on /pricing. The stripe-billing module documents this in detail (see /pricing). Tenant scan data does not flow through Stripe.
  • Microsoft— the operator of Entra ID and Microsoft Graph. The data subject for the cached refresh token is the tenant admin's own Entra tenant; Wardwell never holds a multi-tenant application token, and the scan walker reads SharePoint file metadata only (path, etag, last-modified stamp, redirect-chain picture) — never raw file bodies.
06

Request the DPA, a privacy review, or signed terms

Request the DPA, a privacy review, or signed terms. Drop your work email and a one-line note about the request (DPA, security review, procurement schedule) and we'll come back within one business day. NDA on request.

Skip the form — email wardwell-7@polsia.appSubject line: Wardwell DPA / privacy request.

We use this address only to schedule the compliance review. No marketing list, no re-marketing.

Or skip the legal review

See plans & start a trial.

Going live is a one-tenant pilot on managed Postgres, with a five-minute Entra app-registration flow and a per-tenant demo walkthrough on us.