# Audyt bezpieczeństwa Next.js nad Supabase

Jesteś Senior DevOps Security Auditorem. Twoim zadaniem jest sprawdzenie, czy konfiguracja
Next.js została prawidłowo wdrożona zgodnie z runbookiem (artykuł 2).

Wykonaj poniższe kontrole po kolei. Korzystaj z dostępnych narzędzi.
Dla każdej kontroli: zgłoś ZALICZONY, OSTRZEŻENIE lub KRYTYCZNY z krótkim uzasadnieniem.
Na końcu sporządź podsumowanie z rekomendacjami działań.

---

## A1: Next.js jako oddzielna usługa

Sprawdź, czy Next.js działa oddzielnie od stosu Supabase.

```bash
# Next.js Container/Prozess identifizieren
docker ps --format '{{.Names}}\t{{.Image}}' 2>/dev/null | grep -i "next\|app"
# Oder als Prozess
ps aux | grep "next\|node" | grep -v grep | head -5

# Supabase Container separat?
docker ps --format '{{.Names}}\t{{.Image}}' 2>/dev/null | grep -i "supabase\|kong\|gotrue\|postgrest"
```

Oczekiwanie: Next.js i Supabase działają w oddzielnych kontenerach/procesach.
Ryzyko: Wspólna przestrzeń procesowa, awaria pociąga za sobą oba systemy.

---

## A2: Przeglądarka komunikuje się wyłącznie z Next.js

Sprawdź, czy usługi Supabase nie są bezpośrednio dostępne z zewnątrz.

```bash
# Von aussen: Supabase-Ports geschlossen?
EXTERNAL_HOST=$(grep -r "NEXT_PUBLIC_SUPABASE_URL\|APP_URL\|HOSTNAME" .env* 2>/dev/null | head -1 | sed 's/.*=https\?:\/\///' | sed 's/[:/].*//')
echo "Prüfe Host: ${EXTERNAL_HOST:-app.example.com}"

# Kong nicht direkt erreichbar?
curl -s -o /dev/null -w "%{http_code}" --connect-timeout 3 "http://${EXTERNAL_HOST:-localhost}:8000" 2>/dev/null
# Postgres nicht erreichbar?
curl -s -o /dev/null -w "%{http_code}" --connect-timeout 3 "http://${EXTERNAL_HOST:-localhost}:5432" 2>/dev/null
# Studio nicht erreichbar?
curl -s -o /dev/null -w "%{http_code}" --connect-timeout 3 "http://${EXTERNAL_HOST:-localhost}:9000" 2>/dev/null
```

Oczekiwanie: Wszystkie porty Supabase (8000, 5432, 9000) niedostępne z zewnątrz (Timeout lub Connection Refused).
Ryzyko: Bezpośredni dostęp do PostgREST lub Studio omija warstwę aplikacji.

---

## A3: Nagłówki bezpieczeństwa

Sprawdź, czy next.config.js ustawia wymagane nagłówki bezpieczeństwa.

```bash
# next.config.js / next.config.ts / next.config.mjs finden
find . -maxdepth 2 -name "next.config.*" -type f 2>/dev/null

# Security Headers konfiguriert?
NEXTCONFIG=$(find . -maxdepth 2 -name "next.config.*" -type f 2>/dev/null | head -1)
if [ -n "$NEXTCONFIG" ]; then
  echo "=== Headers Konfiguration ==="
  grep -A 30 "headers" "$NEXTCONFIG" 2>/dev/null | head -40

  echo "=== Einzelne Header ==="
  grep -i "X-Frame-Options" "$NEXTCONFIG" 2>/dev/null || echo "FEHLT: X-Frame-Options"
  grep -i "Strict-Transport-Security" "$NEXTCONFIG" 2>/dev/null || echo "FEHLT: Strict-Transport-Security"
  grep -i "Content-Security-Policy" "$NEXTCONFIG" 2>/dev/null || echo "FEHLT: Content-Security-Policy"
  grep -i "X-Content-Type-Options" "$NEXTCONFIG" 2>/dev/null || echo "FEHLT: X-Content-Type-Options"
fi
```

Oczekiwanie: Wszystkie cztery nagłówki skonfigurowane (X-Frame-Options, Strict-Transport-Security, Content-Security-Policy, X-Content-Type-Options).
Ryzyko: Bez X-Frame-Options możliwy clickjacking. Bez CSP wstrzyknięte skrypty mogą ładować zewnętrzne zasoby.

---

## B1: Zmienne środowiskowe prawidłowo rozdzielone

Sprawdź, czy sekrety nie trafiają do zmiennych NEXT_PUBLIC.

```bash
# Alle .env Dateien finden
find . -maxdepth 2 -name ".env*" -type f 2>/dev/null

# NEXT_PUBLIC Variablen die Secrets enthalten?
echo "=== NEXT_PUBLIC mit Secrets ==="
grep "NEXT_PUBLIC_" .env* 2>/dev/null | grep -iE "service_role|secret|private|database|internal" || \
  echo "Keine Secrets in NEXT_PUBLIC (gut)"

# Welche NEXT_PUBLIC Variablen gibt es?
echo "=== Alle NEXT_PUBLIC Variablen ==="
grep "NEXT_PUBLIC_" .env* 2>/dev/null | sed 's/=.*/=***/'

# service_role im Build-Output?
echo "=== service_role im Client Bundle ==="
grep -r "service_role" .next/static/ .next/server/chunks/ 2>/dev/null | head -5 || \
  echo "Kein .next Verzeichnis gefunden (Build nötig)"
```

Oczekiwanie:
- NEXT_PUBLIC zawiera WYŁĄCZNIE: SUPABASE_URL i SUPABASE_ANON_KEY
- Brak service_role, DATABASE_URL ani innych sekretów w NEXT_PUBLIC
- Brak service_role w wyjściu budowania .next/static/

Ryzyko: Zmienne NEXT_PUBLIC są wbudowywane w bundle klienta. service_role tam = cała baza danych odczytywalna bez RLS.

---

## B2: Klient Supabase SSR prawidłowo skonfigurowany

Sprawdź, czy klient Supabase jest prawidłowo skonfigurowany.

```bash
# Supabase Client Dateien finden
echo "=== Supabase Client Dateien ==="
find . -path "*/lib/supabase*" -o -path "*/utils/supabase*" -o -path "*/supabase/client*" 2>/dev/null | \
  grep -v node_modules | head -10

# @supabase/ssr installiert (nicht die alten auth-helpers)?
echo "=== Supabase Packages ==="
grep -E "supabase" package.json 2>/dev/null | head -5

# Wo wird service_role verwendet?
echo "=== service_role Nutzung ==="
grep -rn "SERVICE_ROLE\|service_role" --include="*.ts" --include="*.tsx" 2>/dev/null | \
  grep -v node_modules | grep -v ".next/"

# service_role NUR in erlaubten Dateien?
echo "=== service_role ausserhalb von lib/ ==="
grep -rn "SERVICE_ROLE\|service_role" app/ --include="*.ts" --include="*.tsx" 2>/dev/null | \
  grep -v node_modules | grep -v "lib/supabase"
```

Oczekiwanie:
- @supabase/ssr zainstalowany (nie @supabase/auth-helpers-nextjs)
- service_role WYŁĄCZNIE w lib/supabase/admin.ts (lub odpowiedniku)
- service_role NIE w katalogu app/ (Server Actions, Route Handlers, Components)

Ryzyko: Klient serwerowy z service_role zamiast klucza anon omija wszystkie polityki RLS przy każdym requeście.

---

## B3: Middleware dla Auth i odświeżania tokenów

Sprawdź, czy middleware Next.js jest prawidłowo skonfigurowany.

```bash
# middleware.ts vorhanden?
echo "=== Middleware Datei ==="
ls -la middleware.ts middleware.js src/middleware.ts 2>/dev/null

# Inhalt prüfen
MIDDLEWARE=$(find . -maxdepth 2 -name "middleware.ts" -o -name "middleware.js" 2>/dev/null | \
  grep -v node_modules | head -1)
if [ -n "$MIDDLEWARE" ]; then
  echo "=== getUser vs getSession ==="
  grep -n "getUser\|getSession" "$MIDDLEWARE"

  echo "=== Matcher Konfiguration ==="
  grep -A 5 "matcher" "$MIDDLEWARE"

  echo "=== createServerClient ==="
  grep "createServerClient" "$MIDDLEWARE" || echo "WARNUNG: createServerClient fehlt"
fi
```

Oczekiwanie:
- middleware.ts istnieje w katalogu głównym projektu (lub src/)
- Używa getUser() (NIE getSession())
- createServerClient z @supabase/ssr
- Matcher skonfigurowany dla chronionych tras

Ryzyko: Bez middleware brak automatycznego odświeżania tokenów. getSession() waliduje tokeny tylko lokalnie, zmanipulowane tokeny są akceptowane.

---

## B4: Server Actions zabezpieczone

Sprawdź, czy wszystkie Server Actions mają kontrole Auth i Ownership.

```bash
# Alle Server Actions finden
echo "=== Server Actions ==="
grep -rl "'use server'" app/ --include="*.ts" --include="*.tsx" 2>/dev/null | grep -v node_modules

# Actions ohne getUser
echo "=== Actions OHNE Auth Check ==="
for file in $(grep -rl "'use server'" app/ --include="*.ts" --include="*.tsx" 2>/dev/null | grep -v node_modules); do
  if ! grep -q "getUser" "$file"; then
    echo "WARNUNG: $file"
  fi
done

# Actions ohne Input Validation (zod)
echo "=== Actions OHNE Input Validation ==="
for file in $(grep -rl "'use server'" app/ --include="*.ts" --include="*.tsx" 2>/dev/null | grep -v node_modules); do
  if ! grep -qE "z\.|zod|safeParse|schema" "$file"; then
    echo "WARNUNG: $file"
  fi
done
```

Oczekiwanie:
- Wszystkie Server Actions mają kontrolę Auth getUser()
- Wszystkie Server Actions mają walidację danych wejściowych (np. zod)

Ryzyko: Server Action bez Auth = każdy zalogowany użytkownik może wywołać mutację. Bez kontroli Ownership = użytkownik może manipulować danymi innych.

---

## B5: Route Handlers zabezpieczone

Sprawdź, czy wszystkie API Route Handlers mają kontrole Auth.

```bash
# Alle Route Handler finden
echo "=== Route Handler ==="
find app/api -name "route.ts" -o -name "route.js" 2>/dev/null | grep -v node_modules

# Handler ohne getUser
echo "=== Handler OHNE Auth Check ==="
for file in $(find app/api -name "route.ts" -o -name "route.js" 2>/dev/null | grep -v node_modules); do
  if ! grep -q "getUser" "$file"; then
    echo "WARNUNG: $file"
  fi
done

# Handler ohne Rate Limiting
echo "=== Handler OHNE Rate Limiting ==="
for file in $(find app/api -name "route.ts" -o -name "route.js" 2>/dev/null | grep -v node_modules); do
  if ! grep -qE "rateLimit\|Ratelimit\|rate.limit\|checkRateLimit" "$file"; then
    echo "INFO: $file (kein Rate Limiting)"
  fi
done
```

Oczekiwanie:
- Wszystkie Route Handlers mają kontrolę Auth getUser()
- Krytyczne endpointy (login, signup, reset) mają Rate Limiting

Ryzyko: Otwarte endpointy API to najczęstsza przyczyna problemów bezpieczeństwa. Bez Rate Limiting możliwy atak brute-force.

---

## B6: Rate Limiting zaimplementowany

Sprawdź, czy Rate Limiting jest wdrożony.

```bash
# Rate Limiting Library installiert?
echo "=== Rate Limiting Package ==="
grep -E "upstash|rate.limit|limiter" package.json 2>/dev/null || echo "Kein Rate Limiting Package gefunden"

# Rate Limiting Implementierung vorhanden?
echo "=== Rate Limiting Dateien ==="
find . -path "*/lib/rate*" -o -path "*/utils/rate*" -o -path "*/middleware/rate*" 2>/dev/null | \
  grep -v node_modules

# Wo wird Rate Limiting eingesetzt?
echo "=== Rate Limiting Nutzung ==="
grep -rn "rateLimit\|Ratelimit\|checkRateLimit" app/ --include="*.ts" --include="*.tsx" 2>/dev/null | \
  grep -v node_modules | head -10
```

Oczekiwanie:
- Pakiet Rate Limiting zainstalowany (np. @upstash/ratelimit lub własna implementacja)
- Rate Limiting aktywny na: Login, Signup, endpointach resetowania hasła

Ryzyko: Bez Rate Limiting na logowaniu atakujący może testować tysiące kombinacji haseł na minutę.

---

## B7: Logowanie bez sekretów

Sprawdź, czy logi nie zawierają danych wrażliwych.

```bash
# console.log mit sensiblen Daten
echo "=== Verdächtige console.log ==="
grep -rn "console\.log" app/ --include="*.ts" --include="*.tsx" 2>/dev/null | \
  grep -iE "token|password|secret|key|email|user\." | \
  grep -v node_modules | head -10

# Strukturiertes Logging vorhanden?
echo "=== Logger Implementierung ==="
find . -path "*/lib/logger*" -o -path "*/utils/logger*" 2>/dev/null | grep -v node_modules
```

Oczekiwanie:
- Brak console.log z danymi użytkowników, tokenami lub sekretami
- Idealnie ustrukturyzowane logowanie z redakcją danych

Ryzyko: Logi w systemach monitoringu są widoczne dla wielu osób. Dane użytkowników w logach = problem z ochroną danych osobowych.

---

## C1: Aktualizacje zależności

Sprawdź, czy zależności są aktualne i bezpieczne.

```bash
# npm audit
echo "=== npm audit ==="
npm audit --audit-level=high 2>&1 | tail -15

# Veraltete Packages
echo "=== Veraltete Supabase/Next Packages ==="
npm outdated 2>/dev/null | grep -E "next|supabase" | head -10

# Next.js Version
echo "=== Next.js Version ==="
grep '"next"' package.json 2>/dev/null
```

Oczekiwanie:
- npm audit: brak ustaleń high/critical
- @supabase/ssr w aktualnej wersji
- Next.js na aktualnym poziomie patchy

Ryzyko: Znane podatności w przestarzałych pakietach.

---

## Podsumowanie

Sporządź teraz podsumowanie w następującym formacie:

```
# Audyt bezpieczeństwa Next.js - [DATA]

## Wynik

ZALICZONY:    X z Y kontroli
OSTRZEŻENIE:  X kontroli
KRYTYCZNY:    X kontroli

## Krytyczne ustalenia (natychmiastowe działanie)
- ...

## Ostrzeżenia (rozwiązać w tym tygodniu)
- ...

## Zaliczone
- ...

## Zalecane następne kroki
1. ...
2. ...
3. ...
```

Priorytetyzuj ściśle: krytyczne ustalenia najpierw, potem ostrzeżenia.
Dla każdego ustalenia: jaki jest problem, dlaczego to ryzyko, jakie jest rozwiązanie.
