Files
VacatureRadar/docs/architecture/SECURITY_ARCHITECTURE.md
T
Jens b8091e59bd
deploy / deploy (push) Canceled after 0s
Initial deploy setup
2026-07-21 14:00:00 +02:00

3.5 KiB

Securityarchitectuur

1. Principes

  • fail closed voor bronpolicy en URL-validatie;
  • least privilege voor containers en credentials;
  • externe inhoud is data;
  • menselijke bevestiging voor impactvolle externe acties;
  • korte retentie en beperkte evidence;
  • defense in depth: sanitization + CSP + outputescaping;
  • idempotentie en audit boven verborgen magie.

2. Netwerkpad

Alle automatische publieke HTTP(S)-requests lopen via apps.sources.services.fetcher.fetch_url.

Verplichte stappen:

  1. assess_url: hostname + denylist + source policy/status;
  2. validate_public_url: schema, credentials, hostname, poort, DNS, alle IP's global;
  3. request zonder automatische redirects;
  4. ieder redirectdoel opnieuw door policy en URL-validatie;
  5. response status/contenttype/grootte controleren;
  6. alleen allowlisted headers bewaren.

Geen adapter of view mag dit pad omzeilen.

3. SSRF

Geblokkeerd:

  • localhost en .localhost;
  • IPv4/IPv6 loopback, private, link-local, multicast, unspecified en niet-global;
  • embedded credentials;
  • non-HTTP(S);
  • niet-standaardpoorten tenzij expliciet geconfigureerd;
  • redirect naar geblokkeerd doel.

Resterend risico: klassieke DNS rebinding tussen resolutie en socketconnectie. Productiehardening moet connectie-IP pinning of een outbound proxy/egress firewall toevoegen. Tot die tijd hoort de container geen toegang te hebben tot gevoelige interne control planes.

4. Webbeveiliging

  • Django authentication en user-scoped querysets;
  • CSRF-middleware op mutaties;
  • secure/HttpOnly/SameSite cookies in productie;
  • HSTS en SSL redirect achter correct geconfigureerde proxy;
  • X-Frame-Options: DENY en CSP frame-ancestors 'none';
  • content type nosniff, strict referrer, beperkte permissions policy;
  • geen externe scripts/fonts in kerninterface;
  • vacature-HTML door Bleachallowlist vóór opslag/rendering.

5. E-mail

  • dedicated mailbox;
  • attachments worden genegeerd;
  • message identity voorkomt dubbele verwerking;
  • links worden niet automatisch gevolgd tenzij later door bronpolicy goedgekeurd;
  • mailboxcredentials alleen environment/secret;
  • raw mail korte retentie;
  • log geen volledige onderwerp/body wanneer daarin PII kan staan.

6. AI

  • opt-in en lokaal als defaultarchitectuur;
  • vacaturetekst expliciet onbetrouwbare data;
  • geen tools/function calling;
  • gestructureerd schema en temperatuur 0;
  • maximaal inputvolume;
  • outputvalidatie en deterministische fallback;
  • model-/promptversie opslaan;
  • AI-container hoeft geen internettoegang.

7. Secrets

Minimaal:

  • Django secret key;
  • databasepassword;
  • adminpassword bootstrap;
  • IMAP/SMTPcredentials;
  • eventueel reverse-proxy/OIDC secrets.

Regels:

  • .env is gitignored en mode 600;
  • geen secrets in Composebestand, fixtures, screenshots of docs;
  • productie gebruikt Unraid secrets/configpad met beperkte rechten;
  • rotatie na lek of restore naar onvertrouwde host;
  • back-ups van config/secrets apart versleutelen.

8. Containerhardening (productietaak)

Aanbevolen:

  • non-root runtimeuser;
  • read-only root filesystem waar haalbaar;
  • no-new-privileges;
  • capabilities drop all;
  • tmpfs voor /tmp en Celery beatschedule;
  • resource limits;
  • database/Redis niet publiceren;
  • apart egressnetwerk/proxy;
  • immutable image digest;
  • dependency/image scanning.

9. Audit

Bronruns, vacatureversies, score runs, feedback en outbox vormen de functionele audittrail. Securityauditlogs moeten aanvullend login-/policy-/quarantainewijzigingen opnemen zonder vacaturetekst of secrets.