veza/veza-backend-api/docs/runbooks/db_down.md

171 lines
4.4 KiB
Markdown
Raw Normal View History

2025-12-16 16:23:49 +00:00
# Runbook: Database Down / DB Pool Exhausted
## Signal
**Alertes déclenchées**:
- `VezaDBPoolHighUsage` - DB pool > 80% (20/25 connexions)
- `VezaDBPoolExhausted` - DB pool épuisé (wait count augmente)
- `/readyz` retourne `503 Service Unavailable` avec `status: "not_ready"`
**Symptômes observables**:
- Erreurs 5xx sur endpoints nécessitant la DB
- Logs: `database connection failed`, `connection pool exhausted`
- Métriques: `veza_db_pool_open_connections` proche de 25, `veza_db_pool_wait_count_total` augmente
## Hypothèses
1. **DB down** - PostgreSQL ne répond plus
2. **DB pool saturé** - Trop de connexions ouvertes, pool épuisé
3. **Réseau** - Problème de connectivité entre app et DB
4. **DB lente** - Requêtes bloquantes, connexions non libérées
## Vérifications
### 1. Vérifier l'état de la DB
```bash
# Depuis le serveur DB
sudo systemctl status postgresql
# ou
docker ps | grep postgres
# Tester connexion directe
psql -h localhost -U veza -d veza_db -c "SELECT 1;"
```
### 2. Vérifier métriques Prometheus
```bash
# Pool connexions
curl -s http://localhost:9090/api/v1/query?query=veza_db_pool_open_connections
# Wait count (doit être stable, pas augmenter)
curl -s http://localhost:9090/api/v1/query?query=rate(veza_db_pool_wait_count_total[5m])
# Connexions en cours d'utilisation
curl -s http://localhost:9090/api/v1/query?query=veza_db_pool_in_use
```
### 3. Vérifier logs application
```bash
# Chercher erreurs DB
grep -i "database\|connection\|pool" /var/log/veza-backend-api/*.log | tail -50
# Chercher requêtes lentes (si logging activé)
grep "slow query" /var/log/veza-backend-api/*.log
```
### 4. Vérifier connexions actives DB
```sql
-- Depuis psql
SELECT count(*) FROM pg_stat_activity WHERE datname = 'veza_db';
SELECT pid, usename, application_name, state, query_start, query
FROM pg_stat_activity
WHERE datname = 'veza_db'
ORDER BY query_start;
```
## Actions Correctives
### Si DB down
1. **Redémarrer PostgreSQL**:
```bash
sudo systemctl restart postgresql
# ou
docker restart veza-postgres
```
2. **Vérifier logs PostgreSQL**:
```bash
tail -100 /var/log/postgresql/postgresql-*.log
# ou
docker logs veza-postgres --tail 100
```
3. **Vérifier espace disque**:
```bash
df -h /var/lib/postgresql
```
4. **Vérifier mémoire**:
```bash
free -h
```
### Si DB pool saturé
1. **Identifier requêtes bloquantes**:
```sql
SELECT pid, usename, application_name, state, wait_event_type, wait_event, query_start, query
FROM pg_stat_activity
WHERE datname = 'veza_db' AND state != 'idle'
ORDER BY query_start;
```
2. **Tuer requêtes bloquantes** (si nécessaire):
```sql
SELECT pg_terminate_backend(pid)
FROM pg_stat_activity
WHERE datname = 'veza_db'
AND state = 'active'
AND query_start < NOW() - INTERVAL '5 minutes';
```
3. **Augmenter pool temporairement** (si configurable):
- Modifier `internal/config/config.go:446` (MaxOpenConns)
- Redémarrer application
- **⚠️ Attention**: Augmenter le pool peut masquer le problème réel
4. **Vérifier connexions non fermées**:
- Auditer code pour `defer db.Close()` manquants
- Vérifier transactions non commitées/rollbackées
### Si réseau
1. **Tester connectivité**:
```bash
telnet <DB_HOST> 5432
# ou
nc -zv <DB_HOST> 5432
```
2. **Vérifier firewall**:
```bash
sudo iptables -L -n | grep 5432
```
3. **Vérifier DNS**:
```bash
nslookup <DB_HOST>
```
## Post-Mortem Notes
### À documenter après résolution
- **Cause racine**: DB down / Pool saturé / Réseau / Autre
- **Durée de l'incident**: De [heure début] à [heure fin]
- **Impact**: Endpoints affectés, utilisateurs impactés
- **Actions prises**: Liste des actions correctives
- **Actions préventives**:
- [ ] Augmenter monitoring DB pool
- [ ] Ajouter alertes sur requêtes lentes
- [ ] Auditer code pour connexions non fermées
- [ ] Configurer connection pooling côté DB (PgBouncer)
### Métriques à surveiller post-incident
- `veza_db_pool_open_connections` - Doit rester < 20
- `veza_db_pool_wait_count_total` - Doit rester stable
- `veza_db_pool_in_use` - Doit être < `open_connections`
- `/readyz` - Doit retourner `200 ready`
## Références
- Configuration DB pool: `internal/config/config.go:446` (MaxOpenConns: 25)
- Health check: `internal/handlers/health.go:124-140`
- Métriques DB: `internal/metrics/db_pool.go`