Loading…
A bird's-eye view of the Matters AI system and how requests, data, and people flow through it.
┌──────────────────┐
│ Clerk (auth) │
└────┬─────────────┘
│ cookies (.matters.ai)
▼
Public visitor ───► matters.ai workspace.matters.ai ◄─── Internal user
(repo root, Vercel) (apps/workspace, Vercel)
│ │
│ │
├───────► WordPress ◄───┤ (content + settings)
│ │
├───────► MongoDB Atlas ┤ (leads, audit logs, glossary, …)
│ │
├───────► Upstash Redis ┤ (cache, glossary analytics)
│ │
└───────► Mux, Sentry, Slack, MailerLite, Resend/SES, Salesforce
| App | Origin | Purpose | Auth model |
|---|---|---|---|
Public website (repo root — a future apps/web move is planned, see Monorepo → Migration) | matters.ai, www.matters.ai | Marketing, blog, glossary, careers, gated downloads, lead capture. | None for content; gated forms hit MongoDB-backed APIs. |
Workspace (apps/workspace) | workspace.matters.ai | Internal admin & content studio across 19 modules. | Clerk session + email domain allowlist + per-route RBAC. |
Docs (apps/webdocs) | webdocs.matters.ai | This site. Engineer-facing documentation. | Public by default; can be locked behind Clerk if/when needed. |
| Package | What it owns |
|---|---|
@matters/auth | Email domain allowlist. Future: re-exports of lib/auth/rbac*. |
@matters/lib | Errors, logger, env (Zod-validated), Sentry config, cn Tailwind helper. |
@matters/ui | Scaffold today — destination for the Radix-based primitives in components/ui/. |
@matters/config | Shared tsconfig.base.json and tsconfig.next.json. |
@matters/theme | Runtime multi-variant theme system (12 variants, light + dark). Consumed by workspace, partners, webdocs. |
The public website still consumes the root
components/,lib/,hooks/directories directly. The workspace consumes the same paths via a tsconfig path bridge until those modules graduate into shared packages — see Monorepo → Migration History for context.
workspace.matters.ai/<route>.apps/workspace.apps/workspace/proxy.ts runs:
/auth/*, /api/webhooks/clerk, /api/health) pass through.route.ts or page.tsx runs. Pages re-check the allowlist + fetch RBAC roles in
their layout (defense-in-depth). API handlers call checkRole(...) against
lib/auth/rbac-shared.ts.matters.ai/<route>.proxy.ts runs: AI-crawler tracking + security headers. No auth gate (the protected
matcher is intentionally empty — protected routes live on the workspace subdomain).app/api/* handlers which themselves don't require auth but do server-side validation and
write to MongoDB.