# ☁️ Cloud Security Hardening — Hetzner **Версія:** 1.0.0 **Provider:** Hetzner Dedicated (GEX44) **Server:** NODE1 (144.76.224.179) --- ## 🎯 Критичні налаштування ### 1. Egress Firewall (№1 Priority) **Блокування внутрішніх мереж Hetzner:** ```bash #!/bin/bash # /root/firewall-egress.sh # Block Hetzner internal networks (prevent scanning) iptables -I OUTPUT -d 10.0.0.0/8 -j DROP iptables -I OUTPUT -d 172.16.0.0/12 -j DROP iptables -I OUTPUT -d 192.168.0.0/16 -j DROP # Allow necessary internal traffic iptables -I OUTPUT -d 10.0.0.0/8 -p tcp --dport 443 -j ACCEPT iptables -I OUTPUT -d 10.0.0.0/8 -p tcp --dport 80 -j ACCEPT # Log blocked attempts iptables -I OUTPUT -d 10.0.0.0/8 -j LOG --log-prefix "BLOCKED_INTERNAL: " # Block known mining pool ports MINING_PORTS="3333 5555 7777 14433 45700 45560 14444 9999" for port in $MINING_PORTS; do iptables -A OUTPUT -p tcp --dport $port -j DROP iptables -A OUTPUT -p tcp --dport $port -j LOG --log-prefix "BLOCKED_MINING: " done # Save rules iptables-save > /etc/iptables/rules.v4 ``` ### 2. SSH Hardening ```bash # /etc/ssh/sshd_config # Disable root login with password PermitRootLogin prohibit-password # Use only SSH keys PasswordAuthentication no PubkeyAuthentication yes # Limit authentication attempts MaxAuthTries 3 MaxSessions 5 # Idle timeout ClientAliveInterval 300 ClientAliveCountMax 2 # Disable unused features X11Forwarding no AllowAgentForwarding no AllowTcpForwarding no # Allow only specific users AllowUsers root # Use strong ciphers Ciphers chacha20-poly1305@openssh.com,aes256-gcm@openssh.com MACs hmac-sha2-512-etm@openssh.com,hmac-sha2-256-etm@openssh.com ``` ### 3. Fail2ban Configuration ```ini # /etc/fail2ban/jail.local [DEFAULT] bantime = 3600 findtime = 600 maxretry = 3 [sshd] enabled = true port = ssh filter = sshd logpath = /var/log/auth.log maxretry = 3 bantime = 86400 [docker-abuse] enabled = true filter = docker-abuse logpath = /var/log/syslog maxretry = 5 bantime = 3600 ``` --- ## 🔒 Network Security ### UFW Configuration ```bash #!/bin/bash # /root/setup-ufw.sh # Reset UFW ufw --force reset # Default policies ufw default deny incoming ufw default deny outgoing # Allow SSH (from specific IPs if possible) ufw allow in 22/tcp # Allow HTTP/HTTPS ufw allow in 80/tcp ufw allow in 443/tcp # Allow outbound DNS ufw allow out 53/tcp ufw allow out 53/udp # Allow outbound HTTP/HTTPS ufw allow out 80/tcp ufw allow out 443/tcp # Allow outbound to Docker registry ufw allow out to any port 443 proto tcp # Block mining pools (additional layer) # Add rules from firewall-egress.sh # Enable UFW ufw --force enable ``` ### Port Exposure Rules | Port | Service | Binding | Notes | |------|---------|---------|-------| | 22 | SSH | 0.0.0.0 | With fail2ban | | 80 | Nginx | 0.0.0.0 | Redirect to 443 | | 443 | Nginx | 0.0.0.0 | HTTPS only | | 3000 | daarion-web | 127.0.0.1 | Via Nginx | | 9102 | Router | 127.0.0.1 | Internal | | 9300 | Gateway | 127.0.0.1 | Via Nginx | | * | Other services | 127.0.0.1 | Never public | --- ## 📊 Monitoring ### System Monitoring Script ```bash #!/bin/bash # /root/security-monitor.sh # Run via cron every 5 minutes LOG_FILE="/var/log/security-monitor.log" ALERT_THRESHOLD_CPU=80 ALERT_THRESHOLD_LOAD=10 timestamp() { date '+%Y-%m-%d %H:%M:%S' } # Check load average LOAD=$(cat /proc/loadavg | awk '{print $1}') LOAD_INT=${LOAD%.*} if [ "$LOAD_INT" -gt "$ALERT_THRESHOLD_LOAD" ]; then echo "[$(timestamp)] ALERT: High load average: $LOAD" >> $LOG_FILE # Send alert (implement your notification) fi # Check for mining processes MINING=$(ps aux | grep -iE "xmrig|catcal|softirq|vrarhpb|miner" | grep -v grep) if [ -n "$MINING" ]; then echo "[$(timestamp)] CRITICAL: Mining process detected!" >> $LOG_FILE echo "$MINING" >> $LOG_FILE # Kill the process echo "$MINING" | awk '{print $2}' | xargs -r kill -9 fi # Check outbound connections to mining ports MINING_CONN=$(ss -antp | grep -E ":(3333|5555|7777|14433)") if [ -n "$MINING_CONN" ]; then echo "[$(timestamp)] CRITICAL: Mining pool connection!" >> $LOG_FILE echo "$MINING_CONN" >> $LOG_FILE fi # Check Docker containers CPU docker stats --no-stream --format "{{.Name}}: {{.CPUPerc}}" | while read line; do CPU=$(echo "$line" | grep -oE '[0-9]+' | head -1) if [ -n "$CPU" ] && [ "$CPU" -gt "$ALERT_THRESHOLD_CPU" ]; then echo "[$(timestamp)] WARNING: High CPU container: $line" >> $LOG_FILE fi done ``` ### Cron Setup ```bash # /etc/cron.d/security-monitor # Run security monitor every 5 minutes */5 * * * * root /root/security-monitor.sh # Run persistence scan daily 0 3 * * * root /opt/microdao-daarion/security/persistence-scan.sh >> /var/log/persistence-scan.log 2>&1 # Log rotation 0 0 * * * root find /var/log -name "*.log" -mtime +30 -delete ``` --- ## 🚨 Incident Response (Hetzner) ### При отриманні Abuse Report: 1. **Негайно:** ```bash # Заблокувати весь вихідний трафік iptables -I OUTPUT -j DROP # Зберегти стан для аналізу ps auxf > /root/incident/ps_$(date +%s).txt ss -antp > /root/incident/ss_$(date +%s).txt docker ps -a > /root/incident/docker_$(date +%s).txt ``` 2. **Знайти джерело:** ```bash # Запустити forensics /opt/microdao-daarion/security/persistence-scan.sh /opt/microdao-daarion/security/runtime-detector.sh ``` 3. **Усунути загрозу:** ```bash # Kill процеси killall -9 # Видалити контейнер ТА образ docker stop docker rm docker rmi # КРИТИЧНО! ``` 4. **Відповісти Hetzner:** - URL: https://statement-abuse.hetzner.com/statements/?token= - Описати причину та вжиті заходи - Зареєструвати retry test 5. **Задокументувати:** - Оновити INFRASTRUCTURE.md - Створити incident report --- ## 🔐 Secrets Management ### Environment Variables ```bash # /opt/microdao-daarion/.env # NEVER commit to git! # Use .env.example as template # Generate secure passwords openssl rand -base64 32 # Store secrets securely chmod 600 .env chown root:root .env ``` ### SSH Keys ```bash # Generate strong SSH key ssh-keygen -t ed25519 -a 100 -f ~/.ssh/id_ed25519 # Rotate keys periodically # Keep backup of old keys until rotation complete ``` --- ## ✅ Hetzner Security Checklist - [ ] Egress firewall blocking internal networks - [ ] Mining pool ports blocked - [ ] SSH hardened (key-only, fail2ban) - [ ] UFW configured (deny by default) - [ ] All services bound to 127.0.0.1 except Nginx - [ ] Security monitoring cron active - [ ] Log rotation configured - [ ] .env file secured (chmod 600) - [ ] Rescue mode access documented - [ ] Hetzner Robot access secured