Security Posture¶
This document defines UCCA's security standards across all web surfaces. It is the single source of truth for what headers are required, how surfaces are classified, what data classification levels exist, and the critical rule governing engine visibility on world surfaces.
Data Classification¶
All UCCA systems operate under four classification levels:
| Level | Label | Description | Examples |
|---|---|---|---|
| L1 | PUBLIC | Visible to anyone on the internet. No authentication required. | Marketing site, API status endpoint |
| L2 | INTERNAL | UCCA team only. Protected by Cloudflare Access or equivalent. | Ops console, docs, knowledge base |
| L3 | RESTRICTED | Named individuals. Elevated access controls. | Terraform state, financial records, legal documents |
| L4 | CONTROLLED | Cryptographically bound. Full audit trail. Immutable once sealed. | Engine outputs, fingerprinted artefacts, signed compliance reports |
Data at L3 and L4 must never be exposed through web surfaces without explicit access control. L4 data carries its own provenance chain and is verified independently of the transport layer.
Surface Classification¶
UCCA operates two categories of web surface with fundamentally different security postures:
Internal Surfaces¶
Surfaces owned and branded by UCCA. These carry full UCCA provenance and identity.
| Surface | Domain | Classification | Stack |
|---|---|---|---|
| Marketing | ucca.online | L1 — PUBLIC | Next.js via OpenNext on Cloudflare Pages |
| API | api.ucca.online | L1 — PUBLIC | Bare Cloudflare Worker |
| Ops Console | ops.ucca.online | L2 — INTERNAL | Next.js via OpenNext on Cloudflare Pages + Access |
| Documentation | docs.ucca.online | L2 — INTERNAL | MkDocs on Cloudflare Pages + Access |
| Knowledge Base | knowledge.ucca.online | L2 — INTERNAL | MkDocs on Cloudflare Pages + Access |
World Surfaces¶
Surfaces serving client-facing products ("worlds"). These are branded as their own product — not as UCCA.
| Surface | Domain | Classification | Stack |
|---|---|---|---|
| RTOpacks | rtopacks.com.au | L1 — PUBLIC | Next.js via OpenNext on Cloudflare Pages |
| (future worlds) | (client domains) | L1 — PUBLIC | Various |
The Engine Invisibility Rule¶
Critical Rule
The engine is invisible. World surfaces must carry zero UCCA fingerprinting. No X-UCCA-* headers. No ucca:* meta tags. No UCCA branding in security.txt, robots.txt, or any other public-facing file. The world surface is the product — the engine behind it is not visible to the outside.
This rule exists because:
- Client sovereignty — each world is the client's product, not an "UCCA-powered" product.
- Competitive protection — the engine architecture is not disclosed through HTTP headers or metadata.
- Clean separation — the engine processes and returns; it does not stamp its identity on the output.
What this means in practice:
- Internal surfaces (ucca.online, ops, docs, knowledge, api): Full UCCA provenance headers, UCCA meta tags, UCCA-branded security.txt.
- World surfaces (rtopacks.com.au, future client domains): Standard security headers only. Product-branded security.txt and robots.txt. Zero reference to UCCA anywhere in the HTTP response.
Security Header Standard¶
All UCCA surfaces must achieve Grade A on security header audits. The following headers are required on every HTTP response, regardless of surface classification.
Required Headers (All Surfaces)¶
Content-Security-Policy: default-src 'self'; script-src 'self' 'unsafe-inline' 'unsafe-eval';
style-src 'self' 'unsafe-inline'; font-src 'self';
img-src 'self' data: blob:; connect-src 'self';
frame-ancestors 'none'; base-uri 'self';
form-action 'self'; object-src 'none';
upgrade-insecure-requests
Strict-Transport-Security: max-age=63072000; includeSubDomains; preload
X-Content-Type-Options: nosniff
X-Frame-Options: DENY
Referrer-Policy: strict-origin-when-cross-origin
Cross-Origin-Resource-Policy: same-origin
Cross-Origin-Opener-Policy: same-origin
X-DNS-Prefetch-Control: off
Permissions-Policy: camera=(), microphone=(), geolocation=(),
interest-cohort=(), payment=(), usb=(),
bluetooth=(), magnetometer=(), gyroscope=(),
accelerometer=(), autoplay=(self),
fullscreen=(self), display-capture=()
CSP varies by surface
API-only surfaces (no HTML rendering) should use default-src 'none'; frame-ancestors 'none' — a stricter policy since no scripts, styles, or images are needed. MkDocs surfaces may need script-src 'self' 'unsafe-inline' for search and theme functionality.
Deprecated Headers¶
Do not include these headers — they are obsolete or counterproductive:
| Header | Reason |
|---|---|
X-XSS-Protection |
Deprecated by all major browsers. Can introduce vulnerabilities in older engines. CSP supersedes it. |
X-Powered-By: Express / X-Powered-By: Next.js |
Framework fingerprinting. Disable via framework config (poweredByHeader: false). |
UCCA Provenance Headers (Internal Surfaces Only)¶
These headers are added only on internal surfaces (ucca.online, api.ucca.online, ops.ucca.online, docs.ucca.online, knowledge.ucca.online):
X-UCCA-Version: 1.0.1
X-UCCA-Schema: v2.4.1
X-UCCA-Integrity: sha256-31a4fb7fe545bb60
X-UCCA-Gate: enforced
X-UCCA-Audit: immutable
X-UCCA-Corpus: active
X-Powered-By: UCCA/1.0.1 — Hardened
These provenance headers identify the surface as a UCCA asset and provide a machine-readable identity chain. They must never appear on world surfaces.
Implementation by Stack¶
Next.js Surfaces (Marketing, Ops, RTOpacks)¶
Security headers are set in two layers:
next.config.js/next.config.ts— browser security policies (CSP, HSTS, Permissions-Policy, etc.). Set via theheaders()function.middleware.ts— UCCA provenance headers (X-UCCA-*). Internal surfaces only.
Configuration:
poweredByHeader: false— suppresses the defaultX-Powered-By: Next.jsheader.- World surfaces omit the middleware provenance layer entirely.
MkDocs Surfaces (Docs, Knowledge)¶
MkDocs on Cloudflare Pages has no server-side header control within the framework. Headers are set via:
public/_headers— Cloudflare Pages headers file. Applied at the CDN edge. This is the only mechanism for custom HTTP headers on Pages-hosted MkDocs sites.
Bare Workers (API)¶
Full header control in the Worker response constructor. All headers — security and provenance — are set directly in the Response object.
Well-Known Files¶
| File | Internal Surfaces | World Surfaces |
|---|---|---|
/.well-known/security.txt |
UCCA-branded, RFC 9116 compliant, PGP-signed | Product-branded (e.g. "RTOpacks Security"), RFC 9116 compliant, no UCCA reference |
/robots.txt |
Standard allow/disallow | Product-branded, no UCCA reference |
/humans.txt |
Optional | Not used |
/favicon.ico |
UCCA favicon | Product favicon |
Access Control¶
L2 (INTERNAL) surfaces are protected by Cloudflare Access:
- ops.ucca.online — Access-gated
- docs.ucca.online — Access-gated
- knowledge.ucca.online — Access-gated
Cloudflare Access provides authentication before the request reaches the application. This means security headers on these surfaces are defence-in-depth — the primary access control is at the network edge.
L1 (PUBLIC) surfaces have no access gating. Security headers are the primary defence layer for browser-side policy enforcement.
Audit Checklist¶
When auditing a UCCA surface, verify:
- All required security headers present on every response
- No deprecated headers (
X-XSS-Protection) - No framework fingerprinting (
X-Powered-By: Next.js) - HSTS max-age >= 63072000 (2 years)
- CSP has zero external origins (no CDN fonts, no external scripts)
-
security.txtexists and is RFC 9116 compliant -
robots.txtexists - Favicon present and correct for the surface
- Page title and meta description are surface-appropriate (not "Create Next App")
- Internal surfaces: UCCA provenance headers present
- World surfaces: Zero UCCA fingerprinting in headers, meta tags, and public files
Version History¶
| Version | Date | Change | Author |
|---|---|---|---|
| 1.0 | 2026-03-02 | Initial creation — baseline standards from security audit | Claude Code |