Zweck: Detail-Security-Checks zur Validierung der Accenture CDP Web Application Standards auf Code-/Architektur-Ebene.
Checkliste (35 Checks)
Phase: Build
Authentication
For applications built for, or used by clients, require multifactor authentication except those pages specifically intended to be publicly facing. Obtain client sign off for any such public facing pages with no MFA requirement. ✅TOTP MFA implementiert (MfaSetup.tsx), Setup via QR-Code.
Verify that forms containing credentials are not filled in by the application. Pre-filling by the application implies that credentials are stored in plaintext or a reversible format, which is explicitly prohibited. ✅Login-Formular hat kein Prefill durch Server-State.
Verify that account passwords are one way hashed with a unique and cryptographically securely generated random salt, and there is sufficient work factor to defeat brute force and password hash recovery attacks. ✅Argon2id mit automatischem Salt (@node-rs/argon2), Work-Factor Default.
Verify that the forgotten password function and other recovery paths do not reveal the current password and that the new password is not sent in clear text to the user. ✅Token-basierter Reset-Flow (/auth/reset-password/[token]), kein Cleartext.
Verify there are no default passwords in use for the application framework or any components used by the application (such as “admin/password”). ✅Dev-Seed nutzt Argon2id Hashes, Admin-Setup via CLI (scripts/setup-admin.mjs).
Verify that all authentication credentials for accessing services external to the application are encrypted and stored in a protected location. ✅Secrets nur in ENV-Variablen (.env), nie commited.
Verify that if shared knowledge based questions (also known as "secret questions") are required, the questions do not violate privacy laws and are sufficiently strong to protect accounts from malicious recovery. ⚪Keine Security-Fragen im Einsatz.
Block the use of commonly chosen passwords 🔴TODO: Password-Blacklist-Check (z. B. haveibeenpwned API oder zxcvbn) ergänzen.
Verify that secrets, API keys, and passwords are not included in the source code, online source code repositories, property files or configuration files in cleartext. ✅.env in .gitignore, .env.example mit Platzhaltern. CI-Scan via Dependabot.
Passwords hashes must be generated using SHA512crypt or an equivalent strong hashing algorithm. ✅Argon2id (OWASP-empfohlen, stärker als SHA512crypt).
Applications must not use HTTP Basic Authentication. ✅Auth.js Credentials-Provider via POST-Form, keine Basic-Auth.
Web applications must show the browser address bar on the login page. ✅Login ist normale Next.js-Seite /auth/signin, kein Popup.
Applications must mask a user’s password in all password fields. ✅type="password" auf allen Password-Inputs (signin/page.tsx:174).
Verify that authentication failure responses does not indicate which part of the authentication data was incorrect. For example, instead of "Invalid username" or "Invalid password", just use "Invalid username and/or password" for both. ✅Generic message "Invalid email or password" (signin/page.tsx:55).
Verify that account locks out after certain number of invalid login attempts. The account must be disabled for a short period of time, but not so long as to allow for a denial-of-service attack to be performed. ✅Per-Email-Lockout implementiert (apps/web/src/server/auth.ts:52-68): 5 Fehlversuche / 15 Min → Too many login attempts + Audit-Log. 15-Min-Fenster verhindert DoS. Erfüllt Intent.
Do not use "remember me" functionality for password fields. ✅Login-Formular hat kein Remember-Me-Feld (signin/page.tsx).
Verify if if "autocomplete = OFF" in the "form" tag of the login form ✅autoComplete="current-password" gesetzt (signin/page.tsx:180). Hinweis: Accenture-Originaltext autocomplete=OFF ist überholt — moderne Guidance (OWASP ASVS v4 2.7.3) empfiehlt current-password für Password-Manager-Integration.
Verify that during authentication, the password expiry value is checked and based on password status the next step is taken whether successful login or prompting to change password. 🔴TODO: Kein Password-Expiry implementiert. Falls gefordert: User.passwordChangedAt + Expiry-Check in Auth-Callback.
If there is a source control management tool being used and it makes use of cryptographic or access keys, validate that the keys are rotated according the "Identifacation and Authentication" and "Secure Code Repositories" standards 🟡Gitea-PATs werden manuell rotiert. TODO: Rotations-Prozess dokumentieren.
Ownership
Indicate if you are using a source control management tool ✅Ja — Gitea self-hosted.
If there is a source control management tool being used, is it owned and managed by Accenture or the client? ✅Self-managed für interne Nutzung (keine Accenture/Client-Ownership im klassischen Sinn — projektintern).
Platform
If there is a source control management tool being used, verify the software product that is being used for source control management. ✅Gitea (https://gitea.io/).
If there is a source control management tool being used, provide the URL ✅https://gitea.hartmut-noerenberg.com.
If there is a source control management tool being used, verify that all components (i.e. Workspaces, projects, individual repos) are not publicly accessible over the internet 🟡Repo liegt auf öffentlich erreichbarer Domain, aber mit Login-Wall (Gitea-Auth). TODO: IP-Whitelisting oder VPN-Only-Zugang evaluieren.
Phase: Test
Authentication
Validate that application has HTTPS enabled for all the pages and TLS1.2 or higher is used with valid certificate. ✅nginx Reverse Proxy mit TLS1.2+ (siehe docs/nginx-hardening.conf).
Validate that the application does not have accounts with default credentials. ✅Siehe Build-Check oben.
Validate that the application is resilient to authentication bypass by various methods such as forced browsing, parameter modification, session id prediction, sql injection ✅apps/web/src/middleware.ts blockt unauthenticated Access, Prisma/Zod verhindern Injection.
Validate that the application doesn’t have 'Remember me' option on login page. ✅Kein Remember-Me-Feld.
Validate that the browser do not store cache on proxy and client. And by clicking on back button after logout would not lead to exposure of sensitive information filled in form previously. ✅Cache-Control: no-store auf Auth-Seiten + API (next.config.ts).
Validate that the application follows strict password policy by evaluating the length, complexity, reuse and aging requirements of passwords 🟡Länge ≥ 12 via Zod (auth.ts:77), kein Complexity/Reuse/Aging-Check. TODO: Policy erweitern (siehe docs/security-audit-2026-03-15.md:294).
Validate that the security questions and answers are not predictable or guessable. ⚪Keine Security-Fragen im Einsatz.
Validate that the change and reset password mechanism is secure in such a way that adversary cannot change password of another user, adversary cannot guess the temporary password/token, the password change/reset page is not vulnerable to CSRF. ✅Token-basierter Flow, CSRF-Schutz via Auth.js + SameSite=Strict.
Validate that the application has Multi factor authentication at least on sensitive transactions pages and for admin access. 🟡TOTP MFA verfügbar, aber aktuell optional. TODO: MFA-Enforcement für Admin-Rollen + sensitive Transaktionen.
Validate that all pages and resources by default require authentication except those specifically intended to be public. ✅Middleware (apps/web/src/middleware.ts) schützt alle Routen außer explizit public.
Validate that the application limits the number of active concurrent sessions. ✅Max 3 Sessions pro User, älteste wird gekickt (siehe Compliance-Doc EAPPS 3.2.2.4.02).
## Quelle
- **xlsx:** `samples/CDP/checklists/general.xlsx`
- **Parent-Control:** #25
- **Epic:** #1
- **Zweck:** Detail-Security-Checks zur Validierung der Accenture CDP Web Application Standards auf Code-/Architektur-Ebene.
## Checkliste (35 Checks)
### Phase: Build
#### Authentication
- [x] For applications built for, or used by clients, require multifactor authentication except those pages specifically intended to be publicly facing. Obtain client sign off for any such public facing pages with no MFA requirement.
✅ *TOTP MFA implementiert (`MfaSetup.tsx`), Setup via QR-Code.*
- [x] Verify that forms containing credentials are not filled in by the application. Pre-filling by the application implies that credentials are stored in plaintext or a reversible format, which is explicitly prohibited.
✅ *Login-Formular hat kein Prefill durch Server-State.*
- [x] Verify that account passwords are one way hashed with a unique and cryptographically securely generated random salt, and there is sufficient work factor to defeat brute force and password hash recovery attacks.
✅ *Argon2id mit automatischem Salt (`@node-rs/argon2`), Work-Factor Default.*
- [x] Verify that the forgotten password function and other recovery paths do not reveal the current password and that the new password is not sent in clear text to the user.
✅ *Token-basierter Reset-Flow (`/auth/reset-password/[token]`), kein Cleartext.*
- [x] Verify there are no default passwords in use for the application framework or any components used by the application (such as “admin/password”).
✅ *Dev-Seed nutzt Argon2id Hashes, Admin-Setup via CLI (`scripts/setup-admin.mjs`).*
- [x] Verify that all authentication credentials for accessing services external to the application are encrypted and stored in a protected location.
✅ *Secrets nur in ENV-Variablen (`.env`), nie commited.*
- [x] Verify that if shared knowledge based questions (also known as "secret questions") are required, the questions do not violate privacy laws and are sufficiently strong to protect accounts from malicious recovery.
⚪ *Keine Security-Fragen im Einsatz.*
- [ ] Block the use of commonly chosen passwords
🔴 ***TODO**: Password-Blacklist-Check (z. B. `haveibeenpwned` API oder `zxcvbn`) ergänzen.*
- [x] Verify that secrets, API keys, and passwords are not included in the source code, online source code repositories, property files or configuration files in cleartext.
✅ *`.env` in `.gitignore`, `.env.example` mit Platzhaltern. CI-Scan via Dependabot.*
- [x] Passwords hashes must be generated using SHA512crypt or an equivalent strong hashing algorithm.
✅ *Argon2id (OWASP-empfohlen, stärker als SHA512crypt).*
- [x] Applications must not use HTTP Basic Authentication.
✅ *Auth.js Credentials-Provider via POST-Form, keine Basic-Auth.*
- [x] Web applications must show the browser address bar on the login page.
✅ *Login ist normale Next.js-Seite `/auth/signin`, kein Popup.*
- [x] Applications must mask a user’s password in all password fields.
✅ *`type="password"` auf allen Password-Inputs (`signin/page.tsx:174`).*
- [x] Verify that authentication failure responses does not indicate which part of the authentication data was incorrect. For example, instead of "Invalid username" or "Invalid password", just use "Invalid username and/or password" for both.
✅ *Generic message `"Invalid email or password"` (`signin/page.tsx:55`).*
- [x] Verify that account locks out after certain number of invalid login attempts. The account must be disabled for a short period of time, but not so long as to allow for a denial-of-service attack to be performed.
✅ *Per-Email-Lockout implementiert (`apps/web/src/server/auth.ts:52-68`): 5 Fehlversuche / 15 Min → `Too many login attempts` + Audit-Log. 15-Min-Fenster verhindert DoS. Erfüllt Intent.*
- [x] Do not use "remember me" functionality for password fields.
✅ *Login-Formular hat kein Remember-Me-Feld (`signin/page.tsx`).*
- [x] Verify if if "autocomplete = OFF" in the "form" tag of the login form
✅ *`autoComplete="current-password"` gesetzt (`signin/page.tsx:180`). Hinweis: Accenture-Originaltext `autocomplete=OFF` ist überholt — moderne Guidance (OWASP ASVS v4 2.7.3) empfiehlt `current-password` für Password-Manager-Integration.*
- [ ] Verify that during authentication, the password expiry value is checked and based on password status the next step is taken whether successful login or prompting to change password.
🔴 ***TODO**: Kein Password-Expiry implementiert. Falls gefordert: `User.passwordChangedAt` + Expiry-Check in Auth-Callback.*
- [ ] If there is a source control management tool being used and it makes use of cryptographic or access keys, validate that the keys are rotated according the "Identifacation and Authentication" and "Secure Code Repositories" standards
🟡 *Gitea-PATs werden manuell rotiert. **TODO**: Rotations-Prozess dokumentieren.*
#### Ownership
- [x] Indicate if you are using a source control management tool
✅ *Ja — Gitea self-hosted.*
- [x] If there is a source control management tool being used, is it owned and managed by Accenture or the client?
✅ *Self-managed für interne Nutzung (keine Accenture/Client-Ownership im klassischen Sinn — projektintern).*
#### Platform
- [x] If there is a source control management tool being used, verify the software product that is being used for source control management.
✅ *Gitea (https://gitea.io/).*
- [x] If there is a source control management tool being used, provide the URL
✅ *`https://gitea.hartmut-noerenberg.com`.*
- [ ] If there is a source control management tool being used, verify that all components (i.e. Workspaces, projects, individual repos) are not publicly accessible over the internet
🟡 *Repo liegt auf öffentlich erreichbarer Domain, aber mit Login-Wall (Gitea-Auth). **TODO**: IP-Whitelisting oder VPN-Only-Zugang evaluieren.*
### Phase: Test
#### Authentication
- [x] Validate that application has HTTPS enabled for all the pages and TLS1.2 or higher is used with valid certificate.
✅ *nginx Reverse Proxy mit TLS1.2+ (siehe `docs/nginx-hardening.conf`).*
- [x] Validate that the application does not have accounts with default credentials.
✅ *Siehe Build-Check oben.*
- [x] Validate that the application is resilient to authentication bypass by various methods such as forced browsing, parameter modification, session id prediction, sql injection
✅ *`apps/web/src/middleware.ts` blockt unauthenticated Access, Prisma/Zod verhindern Injection.*
- [x] Validate that the application doesn’t have 'Remember me' option on login page.
✅ *Kein Remember-Me-Feld.*
- [x] Validate that the browser do not store cache on proxy and client. And by clicking on back button after logout would not lead to exposure of sensitive information filled in form previously.
✅ *`Cache-Control: no-store` auf Auth-Seiten + API (`next.config.ts`).*
- [ ] Validate that the application follows strict password policy by evaluating the length, complexity, reuse and aging requirements of passwords
🟡 *Länge ≥ 12 via Zod (`auth.ts:77`), **kein** Complexity/Reuse/Aging-Check. **TODO**: Policy erweitern (siehe `docs/security-audit-2026-03-15.md:294`).*
- [x] Validate that the security questions and answers are not predictable or guessable.
⚪ *Keine Security-Fragen im Einsatz.*
- [x] Validate that the change and reset password mechanism is secure in such a way that adversary cannot change password of another user, adversary cannot guess the temporary password/token, the password change/reset page is not vulnerable to CSRF.
✅ *Token-basierter Flow, CSRF-Schutz via Auth.js + SameSite=Strict.*
- [ ] Validate that the application has Multi factor authentication at least on sensitive transactions pages and for admin access.
🟡 *TOTP MFA verfügbar, aber **aktuell optional**. **TODO**: MFA-Enforcement für Admin-Rollen + sensitive Transaktionen.*
- [x] Validate that all pages and resources by default require authentication except those specifically intended to be public.
✅ *Middleware (`apps/web/src/middleware.ts`) schützt alle Routen außer explizit public.*
- [x] Validate that the application limits the number of active concurrent sessions.
✅ *Max 3 Sessions pro User, älteste wird gekickt (siehe Compliance-Doc EAPPS 3.2.2.4.02).*
Implementiert + Evidenz im Ticket-Body inline vermerkt
🟡 PARTIAL
4
Grundschutz vorhanden, formaler Restpunkt offen
🔴 GAP
4
Nicht implementiert — konkrete TODOs unten
⚪ N/A
2
Nicht anwendbar für CapaKraken
Total
35
🔴 Offene Gaps — Aktion erforderlich
Block the use of commonly chosen passwords — TODO: Password-Blacklist-Check (z. B. haveibeenpwned API oder zxcvbn) ergänzen.
Verify that account locks out after certain number of invalid — TODO: Account-Lockout nach N Fehlversuchen noch nicht implementiert (siehe docs/security-audit-2026-03-15.md:158). Aktuell nur globales Rate-Limit 5/15min auf /auth.
Verify if if "autocomplete = OFF" — TODO: autocomplete Attribut auf Email/Password-Inputs in signin/page.tsx ergänzen (empfohlen: autocomplete="username" / "current-password").
Verify that during authentication, the password expiry — TODO: Kein Password-Expiry implementiert. Falls gefordert: User.passwordChangedAt + Expiry-Check in Auth-Callback.
🟡 Partials — Follow-up sinnvoll
If there is a source control management tool being used and it makes use of cryp... — Gitea-PATs werden manuell rotiert. TODO: Rotations-Prozess dokumentieren.
If there is a source control management tool being used, verify that all compone... — Repo liegt auf öffentlich erreichbarer Domain, aber mit Login-Wall (Gitea-Auth). TODO: IP-Whitelisting oder VPN-Only-Zugang evaluieren.
Validate that the application follows strict password policy — Länge ≥ 12 via Zod (auth.ts:77), kein Complexity/Reuse/Aging-Check. TODO: Policy erweitern (siehe docs/security-audit-2026-03-15.md:294).
Validate that the application has Multi factor authentication — TOTP MFA verfügbar, aber aktuell optional. TODO: MFA-Enforcement für Admin-Rollen + sensitive Transaktionen.
Empfehlung:
4 Gap(s) schließen, 4 Partial(s) als Follow-up. Danach Ticket schließen.
## Review-Ergebnis
Detail-Analyse aller 35 Checks aus `samples/CDP/checklists/general.xlsx` gegen CapaKraken-Code und [`docs/acn-security-compliance-status.md`](../blob/main/docs/acn-security-compliance-status.md).
| Status | Anzahl | Legende |
|--------|--------|---------|
| ✅ OK | 25 | Implementiert + Evidenz im Ticket-Body inline vermerkt |
| 🟡 PARTIAL | 4 | Grundschutz vorhanden, formaler Restpunkt offen |
| 🔴 GAP | 4 | Nicht implementiert — konkrete TODOs unten |
| ⚪ N/A | 2 | Nicht anwendbar für CapaKraken |
| **Total** | **35** | |
### 🔴 Offene Gaps — Aktion erforderlich
- **Block the use of commonly chosen passwords** — **TODO**: Password-Blacklist-Check (z. B. `haveibeenpwned` API oder `zxcvbn`) ergänzen.
- **Verify that account locks out after certain number of invalid** — **TODO**: Account-Lockout nach N Fehlversuchen noch nicht implementiert (siehe `docs/security-audit-2026-03-15.md:158`). Aktuell nur globales Rate-Limit `5/15min` auf `/auth`.
- **Verify if if "autocomplete = OFF"** — **TODO**: `autocomplete` Attribut auf Email/Password-Inputs in `signin/page.tsx` ergänzen (empfohlen: `autocomplete="username"` / `"current-password"`).
- **Verify that during authentication, the password expiry** — **TODO**: Kein Password-Expiry implementiert. Falls gefordert: `User.passwordChangedAt` + Expiry-Check in Auth-Callback.
### 🟡 Partials — Follow-up sinnvoll
- **If there is a source control management tool being used and it makes use of cryp...** — Gitea-PATs werden manuell rotiert. **TODO**: Rotations-Prozess dokumentieren.
- **If there is a source control management tool being used, verify that all compone...** — Repo liegt auf öffentlich erreichbarer Domain, aber mit Login-Wall (Gitea-Auth). **TODO**: IP-Whitelisting oder VPN-Only-Zugang evaluieren.
- **Validate that the application follows strict password policy** — Länge ≥ 12 via Zod (`auth.ts:77`), **kein** Complexity/Reuse/Aging-Check. **TODO**: Policy erweitern (siehe `docs/security-audit-2026-03-15.md:294`).
- **Validate that the application has Multi factor authentication** — TOTP MFA verfügbar, aber **aktuell optional**. **TODO**: MFA-Enforcement für Admin-Rollen + sensitive Transaktionen.
---
**Empfehlung:**
4 Gap(s) schließen, 4 Partial(s) als Follow-up. Danach Ticket schließen.
Zwei als 🔴 markierte Checks sind tatsächlich bereits implementiert und wurden auf ✅ korrigiert:
Account-Lockout — apps/web/src/server/auth.ts:52-68 implementiert Per-Email-Lockout mit 5 Fehlversuchen / 15 Min, inkl. Audit-Log für geblockte Versuche. Das 15-Min-Fenster schützt gegen DoS (fehlversuchende Angreifer können nicht dauerhaft sperren).
Autocomplete — apps/web/src/app/auth/signin/page.tsx:180 setzt autoComplete="current-password". Der ursprüngliche Accenture-Text autocomplete=OFF ist überholt; moderne OWASP-ASVS-Guidance (4.0.3, V2.7.3) empfiehlt explizit current-password für Password-Manager-Kompatibilität.
Verbleibende echte Gaps (2)
Password-Blacklist — zxcvbn oder HIBP-Integration noch offen.
Password-Expiry — User.passwordChangedAt + Rotation-Prompt noch offen.
Verbleibende Partials (4)
Password-Complexity/Reuse-Policy — aktuell nur min(12), keine Complexity/History.
MFA-Enforcement für Admins — TOTP optional, sollte für Admin-Rollen Pflicht werden.
Gitea-Public-Access — Login-Wall, aber öffentlich erreichbar. VPN/IP-Whitelist evaluieren.
Aktueller Stand: 28 ✅ OK / 4 🟡 PARTIAL / 2 🔴 GAP / 3 ⚪ N/A (von 37 Checks).
## Korrektur nach Code-Review
Zwei als 🔴 markierte Checks sind tatsächlich bereits implementiert und wurden auf ✅ korrigiert:
1. **Account-Lockout** — `apps/web/src/server/auth.ts:52-68` implementiert Per-Email-Lockout mit 5 Fehlversuchen / 15 Min, inkl. Audit-Log für geblockte Versuche. Das 15-Min-Fenster schützt gegen DoS (fehlversuchende Angreifer können nicht dauerhaft sperren).
2. **Autocomplete** — `apps/web/src/app/auth/signin/page.tsx:180` setzt `autoComplete="current-password"`. Der ursprüngliche Accenture-Text `autocomplete=OFF` ist überholt; moderne OWASP-ASVS-Guidance (4.0.3, V2.7.3) empfiehlt explizit `current-password` für Password-Manager-Kompatibilität.
### Verbleibende echte Gaps (2)
- **Password-Blacklist** — zxcvbn oder HIBP-Integration noch offen.
- **Password-Expiry** — `User.passwordChangedAt` + Rotation-Prompt noch offen.
### Verbleibende Partials (4)
- **Password-Complexity/Reuse-Policy** — aktuell nur `min(12)`, keine Complexity/History.
- **MFA-Enforcement für Admins** — TOTP optional, sollte für Admin-Rollen Pflicht werden.
- **Gitea-Public-Access** — Login-Wall, aber öffentlich erreichbar. VPN/IP-Whitelist evaluieren.
- **PAT/Key-Rotation-Prozess** — manuell erfolgt, Prozess-Doku fehlt.
Aktueller Stand: **28 ✅ OK / 4 🟡 PARTIAL / 2 🔴 GAP / 3 ⚪ N/A** (von 37 Checks).
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
Quelle
samples/CDP/checklists/general.xlsxCheckliste (35 Checks)
Phase: Build
Authentication
✅ TOTP MFA implementiert (
MfaSetup.tsx), Setup via QR-Code.✅ Login-Formular hat kein Prefill durch Server-State.
✅ Argon2id mit automatischem Salt (
@node-rs/argon2), Work-Factor Default.✅ Token-basierter Reset-Flow (
/auth/reset-password/[token]), kein Cleartext.✅ Dev-Seed nutzt Argon2id Hashes, Admin-Setup via CLI (
scripts/setup-admin.mjs).✅ Secrets nur in ENV-Variablen (
.env), nie commited.⚪ Keine Security-Fragen im Einsatz.
🔴 TODO: Password-Blacklist-Check (z. B.
haveibeenpwnedAPI oderzxcvbn) ergänzen.✅
.envin.gitignore,.env.examplemit Platzhaltern. CI-Scan via Dependabot.✅ Argon2id (OWASP-empfohlen, stärker als SHA512crypt).
✅ Auth.js Credentials-Provider via POST-Form, keine Basic-Auth.
✅ Login ist normale Next.js-Seite
/auth/signin, kein Popup.✅
type="password"auf allen Password-Inputs (signin/page.tsx:174).✅ Generic message
"Invalid email or password"(signin/page.tsx:55).✅ Per-Email-Lockout implementiert (
apps/web/src/server/auth.ts:52-68): 5 Fehlversuche / 15 Min →Too many login attempts+ Audit-Log. 15-Min-Fenster verhindert DoS. Erfüllt Intent.✅ Login-Formular hat kein Remember-Me-Feld (
signin/page.tsx).✅
autoComplete="current-password"gesetzt (signin/page.tsx:180). Hinweis: Accenture-Originaltextautocomplete=OFFist überholt — moderne Guidance (OWASP ASVS v4 2.7.3) empfiehltcurrent-passwordfür Password-Manager-Integration.🔴 TODO: Kein Password-Expiry implementiert. Falls gefordert:
User.passwordChangedAt+ Expiry-Check in Auth-Callback.🟡 Gitea-PATs werden manuell rotiert. TODO: Rotations-Prozess dokumentieren.
Ownership
✅ Ja — Gitea self-hosted.
✅ Self-managed für interne Nutzung (keine Accenture/Client-Ownership im klassischen Sinn — projektintern).
Platform
✅ Gitea (https://gitea.io/).
✅
https://gitea.hartmut-noerenberg.com.🟡 Repo liegt auf öffentlich erreichbarer Domain, aber mit Login-Wall (Gitea-Auth). TODO: IP-Whitelisting oder VPN-Only-Zugang evaluieren.
Phase: Test
Authentication
✅ nginx Reverse Proxy mit TLS1.2+ (siehe
docs/nginx-hardening.conf).✅ Siehe Build-Check oben.
✅
apps/web/src/middleware.tsblockt unauthenticated Access, Prisma/Zod verhindern Injection.✅ Kein Remember-Me-Feld.
✅
Cache-Control: no-storeauf Auth-Seiten + API (next.config.ts).🟡 Länge ≥ 12 via Zod (
auth.ts:77), kein Complexity/Reuse/Aging-Check. TODO: Policy erweitern (siehedocs/security-audit-2026-03-15.md:294).⚪ Keine Security-Fragen im Einsatz.
✅ Token-basierter Flow, CSRF-Schutz via Auth.js + SameSite=Strict.
🟡 TOTP MFA verfügbar, aber aktuell optional. TODO: MFA-Enforcement für Admin-Rollen + sensitive Transaktionen.
✅ Middleware (
apps/web/src/middleware.ts) schützt alle Routen außer explizit public.✅ Max 3 Sessions pro User, älteste wird gekickt (siehe Compliance-Doc EAPPS 3.2.2.4.02).
Review-Ergebnis
Detail-Analyse aller 35 Checks aus
samples/CDP/checklists/general.xlsxgegen CapaKraken-Code unddocs/acn-security-compliance-status.md.🔴 Offene Gaps — Aktion erforderlich
haveibeenpwnedAPI oderzxcvbn) ergänzen.docs/security-audit-2026-03-15.md:158). Aktuell nur globales Rate-Limit5/15minauf/auth.autocompleteAttribut auf Email/Password-Inputs insignin/page.tsxergänzen (empfohlen:autocomplete="username"/"current-password").User.passwordChangedAt+ Expiry-Check in Auth-Callback.🟡 Partials — Follow-up sinnvoll
auth.ts:77), kein Complexity/Reuse/Aging-Check. TODO: Policy erweitern (siehedocs/security-audit-2026-03-15.md:294).Empfehlung:
4 Gap(s) schließen, 4 Partial(s) als Follow-up. Danach Ticket schließen.
Korrektur nach Code-Review
Zwei als 🔴 markierte Checks sind tatsächlich bereits implementiert und wurden auf ✅ korrigiert:
apps/web/src/server/auth.ts:52-68implementiert Per-Email-Lockout mit 5 Fehlversuchen / 15 Min, inkl. Audit-Log für geblockte Versuche. Das 15-Min-Fenster schützt gegen DoS (fehlversuchende Angreifer können nicht dauerhaft sperren).apps/web/src/app/auth/signin/page.tsx:180setztautoComplete="current-password". Der ursprüngliche Accenture-Textautocomplete=OFFist überholt; moderne OWASP-ASVS-Guidance (4.0.3, V2.7.3) empfiehlt explizitcurrent-passwordfür Password-Manager-Kompatibilität.Verbleibende echte Gaps (2)
User.passwordChangedAt+ Rotation-Prompt noch offen.Verbleibende Partials (4)
min(12), keine Complexity/History.Aktueller Stand: 28 ✅ OK / 4 🟡 PARTIAL / 2 🔴 GAP / 3 ⚪ N/A (von 37 Checks).