Configuration Sécurité - ProbatioVault Infrastructure¶
Ce document décrit la configuration des règles de sécurité (firewall UFW) pour l'infrastructure ProbatioVault.
⚠️ Note : Cette configuration sécurise l'architecture actuelle (Phase 0 - VPS classiques).
Pour l'architecture cible (Phase 4 - VPC OVH Cloud) avec Security Groups OpenStack natifs, voir
ROADMAP.md.
📋 Vue d'ensemble¶
La sécurité réseau est gérée via une approche hybride Terraform + Ansible :
- Terraform (
security_groups.tf) : Définit les règles de sécurité selon l'architecture - Ansible (
roles/security) : Applique les règles UFW sur les VPS
🏗️ Architecture actuelle¶
DEV (1 VPS tout-en-un)¶
- Rôle :
all-in-one - Composants : Backend + API + SGBD + SonarQube + GitLab Runner
- Ports ouverts :
22: SSH80: HTTP443: HTTPS3000: API NestJS9000: SonarQube9100: Prometheus node-exporter5432: PostgreSQL (localhost uniquement)6379: Redis (localhost uniquement)
TEST (1 VPS)¶
- Rôle :
all-in-one - Composants : Backend + API + SGBD
- Ports ouverts :
22: SSH80: HTTP443: HTTPS3000: API NestJS9100: Prometheus node-exporter5432: PostgreSQL (localhost uniquement)6379: Redis (localhost uniquement)
PROD (4 VPS séparés)¶
VPS Backend (server_role = "backend")¶
- Ports ouverts :
22: SSH (IPs restreintes)80: HTTP443: HTTPS3000: API NestJS9100: Prometheus node-exporter
VPS API (server_role = "api")¶
- Ports ouverts :
22: SSH (IPs restreintes)80: HTTP443: HTTPS3000: API9100: Prometheus node-exporter
VPS Database (server_role = "database")¶
- Ports ouverts :
22: SSH (IPs restreintes via bastion)5432: PostgreSQL (UNIQUEMENT depuis IP Backend)9100: Prometheus node-exporter (réseau interne)- Isolation : Aucun accès Internet direct
VPS GitLab Runner (server_role = "runner")¶
- Ports ouverts :
22: SSH (IPs restreintes)5000: Docker Registry (réseau interne)9100: Prometheus node-exporter
🔐 Configuration¶
1. Variables Terraform¶
Éditer le fichier environments/{env}.tfvars :
# Rôle du serveur
server_role = "backend" # ou "api", "database", "runner", "all-in-one"
# IPs autorisées pour SSH (PRODUCTION UNIQUEMENT)
allowed_ssh_cidrs = [
"203.0.113.50/32", # Bureau
"198.51.100.10/32", # VPN
]
# IPs autorisées pour SonarQube (DEV uniquement)
allowed_sonarqube_cidrs = []
# Monitoring
monitoring_cidr = "10.0.0.5/32"
# IPs des autres serveurs (PROD uniquement)
backend_server_ip = "203.0.113.10" # Pour autoriser Backend → DB
database_server_ip = "203.0.113.20" # Pour connexion depuis Backend
2. Générer la configuration¶
cd terraform
# Pour l'environnement dev
terraform apply -var-file="environments/dev.tfvars"
# Cela génère automatiquement :
# - ../ansible/inventory/dev/group_vars/all/firewall.json
# - ../ansible/inventory/dev/group_vars/all/firewall.yml
3. Appliquer avec Ansible¶
cd ../ansible
# Appliquer les règles firewall
ansible-playbook -i inventory/dev/hosts.ini playbook.yml --tags firewall
# Ou appliquer toute la sécurité (firewall + fail2ban + hardening)
ansible-playbook -i inventory/dev/hosts.ini playbook.yml --tags security
🛡️ Règles de sécurité¶
Principe du moindre privilège¶
Chaque serveur n'a accès qu'aux services strictement nécessaires :
DEV (tout-en-un)
├── Internet → Ports publics (22, 80, 443, 3000, 9000)
├── Localhost → PostgreSQL (5432), Redis (6379)
└── Monitoring → Prometheus (9100)
PROD Backend
├── Internet → Ports publics (22*, 80, 443, 3000)
├── Database → PostgreSQL (5432)
└── Monitoring → Prometheus (9100)
*SSH restreint aux IPs autorisées
PROD Database
├── Backend UNIQUEMENT → PostgreSQL (5432)
├── SSH (bastion) → Port 22
└── AUCUN accès Internet direct
Fail2ban¶
Configuration automatique selon l'environnement :
Développement : - maxretry : 5 tentatives - bantime : 3600s (1h)
Production : - maxretry : 3 tentatives - bantime : 7200s (2h) - Ban immédiat après 2 échecs consécutifs
Hardening système¶
Paramètres sysctl appliqués automatiquement :
- Protection contre IP spoofing (
rp_filter) - Blocage des redirects ICMP
- Protection SYN flood (SYN cookies)
- Logging des paquets martiens
- Blocage du source routing
📊 Vérification¶
Afficher les règles UFW actives¶
# SSH vers le serveur
ssh ubuntu@51.68.126.160
# Afficher le status UFW
sudo ufw status verbose
# Afficher les logs
sudo tail -f /var/log/ufw.log
Vérifier fail2ban¶
# Status fail2ban
sudo fail2ban-client status
# Status SSH jail
sudo fail2ban-client status sshd
# Débannir une IP
sudo fail2ban-client set sshd unbanip 203.0.113.50
Tester la connectivité¶
# Depuis le serveur Backend vers Database
nc -zv <database_ip> 5432
# Attendu : Connection succeeded
# Depuis Internet vers Database (doit échouer)
nc -zv <database_ip> 5432
# Attendu : Connection refused ou timeout
🔄 Workflow¶
Ajout d'une nouvelle règle¶
-
Modifier
security_groups.tf: -
Appliquer Terraform :
-
Appliquer Ansible :
Modification pour production¶
- Éditer
environments/prod.tfvarsselon le VPS : - Backend :
server_role = "backend" - API :
server_role = "api" - Database :
server_role = "database" -
Runner :
server_role = "runner" -
Appliquer la configuration :
🚨 Sécurité Production¶
⚠️ Checklist avant mise en production¶
- Restreindre
allowed_ssh_cidrsaux IPs de confiance uniquement - Configurer
backend_server_ipetdatabase_server_ip - Activer le monitoring (
monitoring_cidr) - Vérifier que Database n'a PAS d'accès Internet
- Tester la connectivité Backend → Database
- Vérifier les logs fail2ban
- Configurer les alertes Prometheus/Grafana
- Documenter les IPs autorisées
🔐 Bonnes pratiques¶
- SSH :
- Utiliser des clés SSH (pas de mot de passe)
- Restreindre aux IPs de confiance en production
-
Activer fail2ban (automatique)
-
Database :
- JAMAIS exposer PostgreSQL sur Internet
- Autoriser UNIQUEMENT l'IP du serveur Backend
-
Utiliser un bastion pour l'administration
-
Monitoring :
- Surveiller les tentatives de connexion échouées
- Alerter sur saturation de connexions
- Logger tous les événements firewall
📚 Ressources¶
🔄 Future : VPC OVH Cloud¶
Pour l'architecture future avec VPC OVH Cloud (OpenStack), voir : - Spec PD-1 : Provisionner VPC OVH Cloud avec Terraform - Module terraform/ovh-cloud/ (à créer) - Security Groups OpenStack natifs