Полная настройка Dedicated сервера для сайтов: LXC+Безопаность+Бекапы на s3

05-09-2025, 23:04
Просмотров: 2

🚀 Полная настройка Dedicated сервера

LXC контейнеризация + максимальная безопасность + автоматические бэкапы в Wasabi S3:

Что получилось:
✅ 10 разделов с пошаговыми инструкциями
✅ Готовые скрипты для автоматизации всех процессов
✅ LXC контейнеризация — максимально быстрая и легковесная
✅ Гибкие IP адреса — можешь назначать разные IP разным сайтам
✅ Корпоративная безопасность — изоляция, firewall, fail2ban
✅ Автоматические бэкапы в Wasabi — еженедельные, годовые, с оптимизацией расходов
✅ Мониторинг + уведомления — в Telegram/email без своих серверов
✅ Консольная панель управления — создание сайтов в несколько кликов

Структура охватывает:

  • Ubuntu 24.04 LTS setup
  • Безопасность (SSH, UFW, Fail2ban)
  • LXC контейнеры для каждого сайта
  • Автоматическое создание HTML/WordPress/Laravel сайтов
  • Reverse proxy + SSL сертификаты
  • Резервирование в S3 с lifecycle политиками
  • Полную автоматизацию обслуживания

 


Быстрый старт:

  1. Открой dedicated-server-setup-guide.html в браузере
  1. Следуй основной инструкции
  1. Используй dedicated-server-extensions.html для продвинутых функций
  1. Запусти /opt/scripts/production-checklist.sh перед продакшеном

📋 Содержание

1🏗️ Обзор архитектуры

🎯 Цель:

Создать безопасную, масштабируемую инфраструктуру для хостинга 10-20 сайтов различных типов с полной изоляцией между ними.

📊 Технический стек:

  • ОС: Ubuntu 24.04 LTS (стабильность + долгосрочная поддержка)
  • Контейнеризация: LXC (легковесная виртуализация)
  • Reverse Proxy: Nginx с автоматическим SSL
  • Мониторинг: Prometheus + Grafana + Alertmanager
  • Безопасность: UFW + Fail2ban + CrowdSec
  • Бэкапы: Restic + Wasabi S3
💡 Преимущества LXC: Каждый сайт работает в изолированном окружении, но при этом использует одно ядро ОС. Это дает ~95% производительности bare metal при максимальной безопасности.

2💻 Установка Ubuntu 24.04 LTS

🔧 Первоначальная установка:

  1. Скачай Ubuntu Server 24.04 LTS ISO с официального сайта
  2. Установи через IPMI/iLO консоль Hetzner
  3. Выбери минимальную установку (без GUI)
  4. Создай пользователя admin с sudo правами

🚀 Первые команды после установки:

# Обновляем систему
sudo apt update && sudo apt upgrade -y

# Устанавливаем базовые пакеты
sudo apt install -y curl wget git htop btop tree unzip fail2ban ufw

# Настраиваем timezone
sudo timedatectl set-timezone Europe/Moscow

# Включаем автоматические обновления безопасности
sudo apt install -y unattended-upgrades
sudo dpkg-reconfigure -plow unattended-upgrades
⚠️ Важно: Обязательно запиши все пароли в надежном месте. Рекомендую использовать SSH ключи вместо паролей.

3🔒 Настройка базовой безопасности

🔑 SSH безопасность:

# Генерируем SSH ключ на локальной машине
ssh-keygen -t ed25519 -C "your-email@domain.com"

# Копируем ключ на сервер
ssh-copy-id admin@your-server-ip

# Настраиваем SSH (отключаем пароли)
sudo nano /etc/ssh/sshd_config

В файле /etc/ssh/sshd_config измени:

Port 2222                    # Меняем порт SSH
PasswordAuthentication no    # Отключаем пароли  
PermitRootLogin no          # Запрещаем root вход
AllowUsers admin            # Разрешаем только конкретным юзерам

🛡️ Настройка firewall UFW:

# Базовая настройка UFW
sudo ufw default deny incoming
sudo ufw default allow outgoing
sudo ufw allow 2222/tcp comment 'SSH'
sudo ufw allow 80/tcp comment 'HTTP'
sudo ufw allow 443/tcp comment 'HTTPS'

# Включаем firewall
sudo ufw enable
sudo systemctl restart ssh

🥊 Настройка Fail2ban:

# Создаем локальную конфигурацию
sudo nano /etc/fail2ban/jail.local

Содержимое jail.local:

[DEFAULT]
bantime = 3600
findtime = 600
maxretry = 3
backend = systemd

[sshd]
enabled = true
port = 2222
logpath = /var/log/auth.log

[nginx-http-auth]
enabled = true

[nginx-limit-req]
enabled = true
✅ Результат: Теперь сервер защищен от основных атак. SSH работает на нестандартном порту, включена защита от брутфорса.

4📦 Установка и настройка LXC

🔧 Установка LXC:

# Устанавливаем LXC и необходимые пакеты
sudo apt install -y lxc lxc-templates bridge-utils

# Создаем пользователя для LXC
sudo usermod -aG lxd admin

# Перезапускаем сессию
sudo su - admin

🌐 Настройка сетевого моста:

Создаем конфигурацию Netplan для мостов:

sudo nano /etc/netplan/01-lxc-bridges.yaml
network:
  version: 2
  renderer: networkd
  ethernets:
    enp1s0:  # Твой основной интерфейс
      dhcp4: no
  bridges:
    br0:
      interfaces: [enp1s0]
      addresses:
        - YOUR_MAIN_IP/24  # Основной IP сервера
      gateway4: YOUR_GATEWAY
      nameservers:
        addresses: [1.1.1.1, 8.8.8.8]
      dhcp4: no
    br-internal:
      addresses: [10.0.100.1/24]
# Применяем настройки
sudo netplan apply

📁 Создание структуры директорий:

# Создаем папки для сайтов
sudo mkdir -p /var/lib/lxc-sites/{html-sites,wordpress-sites,laravel-sites,nodejs-sites}
sudo mkdir -p /opt/scripts/lxc-management
sudo mkdir -p /var/backups/lxc-snapshots
💡 Структура: Каждый тип сайтов будет иметь свою папку и шаблон контейнера для быстрого развертывания.

5🌐 Настройка сети и IP адресов

📋 Планирование IP адресов:

  • Основной сервер: Твой главный IP от Hetzner
  • Дополнительные IP: Дополнительные IP от Hetzner для отдельных сайтов
  • Внутренняя сеть: 10.0.100.0/24 для межконтейнерного общения

🔧 Скрипт для добавления IP адресов:

sudo nano /opt/scripts/add-ip.sh
#!/bin/bash
# Скрипт для добавления дополнительных IP адресов

if [ "$#" -ne 2 ]; then
    echo "Usage: $0  "
    exit 1
fi

IP_ADDRESS=$1
SITE_NAME=$2

# Добавляем IP к интерфейсу
sudo ip addr add ${IP_ADDRESS}/32 dev br0

# Добавляем в автозагрузку
echo "post-up ip addr add ${IP_ADDRESS}/32 dev br0 # ${SITE_NAME}" | sudo tee -a /etc/network/interfaces

echo "IP ${IP_ADDRESS} добавлен для сайта ${SITE_NAME}"
chmod +x /opt/scripts/add-ip.sh
⚠️ Важно: Каждый дополнительный IP от Hetzner нужно активировать в их панели управления и настроить роутинг.

6🏗️ Создание контейнеров для сайтов

📝 Шаблон для HTML/CSS сайтов:

sudo nano /opt/scripts/create-html-site.sh
#!/bin/bash
SITE_NAME=$1
CONTAINER_IP=$2

# Создаем контейнер
sudo lxc-create -n ${SITE_NAME} -t ubuntu -- -r jammy

# Настраиваем конфигурацию контейнера
sudo tee /var/lib/lxc/${SITE_NAME}/config << EOF
lxc.net.0.type = veth
lxc.net.0.link = br-internal
lxc.net.0.ipv4.address = ${CONTAINER_IP}/24
lxc.net.0.ipv4.gateway = 10.0.100.1
lxc.rootfs.path = dir:/var/lib/lxc/${SITE_NAME}/rootfs
lxc.uts.name = ${SITE_NAME}
lxc.mount.auto = proc sys cgroup
EOF

# Запускаем контейнер
sudo lxc-start -n ${SITE_NAME}

# Устанавливаем nginx в контейнер
sudo lxc-attach -n ${SITE_NAME} -- apt update
sudo lxc-attach -n ${SITE_NAME} -- apt install -y nginx
sudo lxc-attach -n ${SITE_NAME} -- systemctl enable nginx

echo "HTML сайт ${SITE_NAME} создан с IP ${CONTAINER_IP}"

🔄 Шаблон для WordPress сайтов:

sudo nano /opt/scripts/create-wordpress-site.sh
#!/bin/bash
SITE_NAME=$1
CONTAINER_IP=$2
DB_PASSWORD=$(openssl rand -base64 32)

# Создаем контейнер (базовый)
/opt/scripts/create-html-site.sh ${SITE_NAME} ${CONTAINER_IP}

# Устанавливаем LEMP stack
sudo lxc-attach -n ${SITE_NAME} -- bash -c "
apt install -y php8.3-fpm php8.3-mysql php8.3-xml php8.3-curl php8.3-gd php8.3-zip mysql-server

# Настраиваем MySQL
mysql_secure_installation

# Создаем базу данных
mysql -e 'CREATE DATABASE ${SITE_NAME}_db;'
mysql -e 'CREATE USER \"${SITE_NAME}_user\"@\"localhost\" IDENTIFIED BY \"${DB_PASSWORD}\";'
mysql -e 'GRANT ALL ON ${SITE_NAME}_db.* TO \"${SITE_NAME}_user\"@\"localhost\";'
mysql -e 'FLUSH PRIVILEGES;'

# Скачиваем WordPress
cd /var/www/html
wget https://wordpress.org/latest.tar.gz
tar -xzf latest.tar.gz
rm latest.tar.gz
chown -R www-data:www-data wordpress/
"

echo "WordPress сайт ${SITE_NAME} создан с IP ${CONTAINER_IP}"
echo "DB Password: ${DB_PASSWORD}"

⚡ Шаблон для Laravel сайтов:

sudo nano /opt/scripts/create-laravel-site.sh
#!/bin/bash
SITE_NAME=$1
CONTAINER_IP=$2

# Создаем базовый контейнер
/opt/scripts/create-html-site.sh ${SITE_NAME} ${CONTAINER_IP}

# Устанавливаем Laravel requirements
sudo lxc-attach -n ${SITE_NAME} -- bash -c "
apt install -y php8.3-fpm php8.3-mysql php8.3-xml php8.3-curl php8.3-gd php8.3-zip php8.3-mbstring composer

# Создаем Laravel проект
cd /var/www
composer create-project laravel/laravel ${SITE_NAME}
chown -R www-data:www-data /var/www/${SITE_NAME}
chmod -R 775 /var/www/${SITE_NAME}/storage
"

echo "Laravel сайт ${SITE_NAME} создан с IP ${CONTAINER_IP}"
chmod +x /opt/scripts/*.sh
✅ Результат: Теперь у тебя есть автоматизированные скрипты для создания любых типов сайтов за несколько секунд.

7🔄 Reverse Proxy и SSL

🌐 Установка и настройка Nginx на хосте:

# Устанавливаем Nginx на основной сервер
sudo apt install -y nginx certbot python3-certbot-nginx

# Создаем базовую конфигурацию
sudo nano /etc/nginx/sites-available/default

Базовая конфигурация Nginx:

server {
    listen 80 default_server;
    listen [::]:80 default_server;
    server_name _;
    
    # Блокируем прямые обращения по IP
    return 444;
}

# Шаблон для сайта
server {
    listen 80;
    server_name example.com www.example.com;
    
    location / {
        proxy_pass http://10.0.100.10:80;  # IP контейнера
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
    }
}

🔒 Автоматизация SSL сертификатов:

sudo nano /opt/scripts/add-ssl.sh
#!/bin/bash
DOMAIN=$1

# Получаем SSL сертификат
sudo certbot --nginx -d ${DOMAIN} --non-interactive --agree-tos --email your-email@domain.com

# Добавляем автообновление
sudo crontab -l | { cat; echo "0 12 * * * /usr/bin/certbot renew --quiet"; } | sudo crontab -

echo "SSL сертификат для ${DOMAIN} установлен"

⚖️ Балансировка нагрузки:

Для высоконагруженных сайтов можешь создать несколько контейнеров:

upstream backend_example {
    server 10.0.100.10:80;
    server 10.0.100.11:80;
    server 10.0.100.12:80;
}

server {
    listen 443 ssl http2;
    server_name example.com;
    
    location / {
        proxy_pass http://backend_example;
    }
}
💡 Cloudflare: Если используешь Cloudflare, включи режим «Full (strict)» SSL для максимальной безопасности.

8📊 Мониторинг и логирование

🔍 Установка системы мониторинга:

# Создаем контейнер для мониторинга
sudo lxc-create -n monitoring -t ubuntu -- -r jammy
sudo lxc-start -n monitoring

# Устанавливаем Prometheus + Grafana
sudo lxc-attach -n monitoring -- bash -c "
apt update
apt install -y prometheus grafana node-exporter

# Настраиваем автозапуск
systemctl enable prometheus grafana-server node-exporter
systemctl start prometheus grafana-server node-exporter
"

📧 Настройка уведомлений через внешние сервисы:

sudo nano /opt/scripts/send-alert.sh
#!/bin/bash
# Скрипт для отправки уведомлений через Telegram API или email сервис

MESSAGE="$1"
SEVERITY="$2"

# Отправка через Telegram (используй бот)
TELEGRAM_TOKEN="YOUR_BOT_TOKEN"
CHAT_ID="YOUR_CHAT_ID"

curl -s -X POST "https://api.telegram.org/bot${TELEGRAM_TOKEN}/sendMessage" \
     -d "chat_id=${CHAT_ID}" \
     -d "text=🚨 ${SEVERITY}: ${MESSAGE}"

# Альтернативно - отправка через SMTP сервис (например, SendGrid)
# echo "${MESSAGE}" | mail -s "Server Alert: ${SEVERITY}" your-email@domain.com

📝 Централизованное логирование:

# Устанавливаем rsyslog для централизованных логов
sudo apt install -y rsyslog

# Настраиваем сбор логов с контейнеров
sudo nano /etc/rsyslog.d/50-lxc.conf
# Собираем логи от всех контейнеров
$ModLoad imfile
$InputFileName /var/lib/lxc/*/rootfs/var/log/*.log
$InputFileTag container:
$InputFileSeverity info
$InputFileFacility local0
$InputRunFileMonitor
✅ Мониторинг настроен! Теперь ты будешь получать уведомления о проблемах и сможешь отслеживать производительность всех сайтов.

9💾 Резервное копирование в Wasabi

🔧 Установка Restic:

# Устанавливаем Restic
sudo apt install -y restic

# Создаем конфигурацию для Wasabi
sudo nano /opt/scripts/backup-config.env
# Конфигурация Wasabi S3
export AWS_ACCESS_KEY_ID="your-wasabi-access-key"
export AWS_SECRET_ACCESS_KEY="your-wasabi-secret-key"
export RESTIC_REPOSITORY="s3:https://s3.wasabisys.com/your-bucket-name/server-backups"
export RESTIC_PASSWORD="your-strong-backup-password"

📦 Скрипт полного бэкапа:

sudo nano /opt/scripts/full-backup.sh
#!/bin/bash
source /opt/scripts/backup-config.env

echo "🚀 Начинаем резервное копирование..."

# Инициализируем репозиторий (только при первом запуске)
restic init --repo $RESTIC_REPOSITORY || true

# Останавливаем контейнеры для консистентности
for container in $(sudo lxc-ls); do
    sudo lxc-stop -n $container
done

# Создаем снапшоты LXC контейнеров
sudo lxc-snapshot -n ALL

# Резервное копирование
restic backup \
    /var/lib/lxc \
    /etc \
    /opt/scripts \
    --tag weekly-backup \
    --exclude-caches \
    --exclude /var/lib/lxc/*/rootfs/tmp \
    --exclude /var/lib/lxc/*/rootfs/var/cache

# Запускаем контейнеры обратно
for container in $(sudo lxc-ls -1 --stopped); do
    sudo lxc-start -n $container
done

# Очистка старых бэкапов (хранить 8 недель)
restic forget --keep-weekly 8 --prune

echo "✅ Резервное копирование завершено!"

📅 Настройка расписания бэкапов:

# Добавляем в crontab
sudo crontab -e
# Еженедельный полный бэкап (воскресенье в 02:00)
0 2 * * 0 /opt/scripts/full-backup.sh >> /var/log/backup.log 2>&1

# Ежедневный инкрементальный бэкап (03:00)
0 3 * * 1-6 /opt/scripts/incremental-backup.sh >> /var/log/backup.log 2>&1

# Годовой архивный бэкап (1 января)
0 1 1 1 * /opt/scripts/yearly-backup.sh >> /var/log/backup.log 2>&1

💰 Оптимизация расходов на Wasabi:

💡 Экономия:

  • Минимальный план: ~$6/месяц за 1TB
  • Дедупликация: Restic автоматически удаляет дубликаты
  • Сжатие: Экономия ~30-50% места
  • Lifecycle policy: Старые бэкапы можно переносить в более дешевое хранилище

🔄 Скрипт восстановления:

sudo nano /opt/scripts/restore-backup.sh
#!/bin/bash
source /opt/scripts/backup-config.env

echo "📁 Доступные бэкапы:"
restic snapshots

echo "Введите ID снапшота для восстановления:"
read SNAPSHOT_ID

echo "🔄 Восстанавливаем бэкап $SNAPSHOT_ID..."
restic restore $SNAPSHOT_ID --target /tmp/restore/

echo "✅ Данные восстановлены в /tmp/restore/"
chmod +x /opt/scripts/*.sh

10🤖 Автоматизация и скрипты

🎛️ Панель управления сайтами:

sudo nano /opt/scripts/site-manager.sh
#!/bin/bash
# Простая консольная панель управления

show_menu() {
    echo "🚀 Управление сайтами"
    echo "===================="
    echo "1. Создать HTML сайт"
    echo "2. Создать WordPress сайт"  
    echo "3. Создать Laravel сайт"
    echo "4. Список всех сайтов"
    echo "5. Остановить сайт"
    echo "6. Запустить сайт"
    echo "7. Удалить сайт"
    echo "8. Создать бэкап сайта"
    echo "9. Выход"
}

while true; do
    show_menu
    read -p "Выберите опцию: " choice
    
    case $choice in
        1) read -p "Имя сайта: " name; read -p "IP контейнера: " ip; /opt/scripts/create-html-site.sh $name $ip ;;
        2) read -p "Имя сайта: " name; read -p "IP контейнера: " ip; /opt/scripts/create-wordpress-site.sh $name $ip ;;
        3) read -p "Имя сайта: " name; read -p "IP контейнера: " ip; /opt/scripts/create-laravel-site.sh $name $ip ;;
        4) sudo lxc-ls -f ;;
        5) read -p "Имя сайта: " name; sudo lxc-stop -n $name ;;
        6) read -p "Имя сайта: " name; sudo lxc-start -n $name ;;
        7) read -p "Имя сайта (ВНИМАНИЕ! Удалится навсегда): " name; sudo lxc-destroy -n $name ;;
        8) read -p "Имя сайта: " name; sudo lxc-snapshot -n $name ;;
        9) exit 0 ;;
        *) echo "Неверная опция!" ;;
    esac
    
    echo -e "\nНажмите Enter для продолжения..."
    read
    clear
done

📈 Мониторинг ресурсов:

sudo nano /opt/scripts/resource-monitor.sh
#!/bin/bash
# Мониторинг ресурсов всех контейнеров

echo "📊 Состояние ресурсов сервера $(date)"
echo "========================================"

echo -e "\n🖥️  ОБЩИЕ РЕСУРСЫ:"
echo "CPU: $(top -bn1 | grep "Cpu(s)" | sed "s/.*, *\([0-9.]*\)%* id.*/\1/" | awk '{print 100 - $1}')%"
echo "RAM: $(free -h | grep '^Mem:' | awk '{print $3 "/" $2}')"
echo "Disk: $(df -h / | tail -1 | awk '{print $3 "/" $2 " (" $5 " used)"}')"

echo -e "\n📦 КОНТЕЙНЕРЫ:"
for container in $(sudo lxc-ls -1); do
    status=$(sudo lxc-info -n $container -s | grep State | awk '{print $2}')
    if [ "$status" = "RUNNING" ]; then
        cpu=$(sudo lxc-attach -n $container -- top -bn1 | grep "Cpu(s)" | head -1 | awk '{print $2}' | cut -d'%' -f1)
        mem=$(sudo lxc-attach -n $container -- free -h | grep '^Mem:' | awk '{print $3}')
        echo "  $container: $status, CPU: ${cpu:-N/A}%, RAM: ${mem:-N/A}"
    else
        echo "  $container: $status"
    fi
done

echo -e "\n🌐 АКТИВНЫЕ СОЕДИНЕНИЯ:"
netstat -tuln | grep LISTEN | wc -l | xargs echo "Listening ports:"

🔧 Автоматическое обслуживание:

sudo nano /opt/scripts/maintenance.sh
#!/bin/bash
# Еженедельное автоматическое обслуживание

echo "🔧 Запуск еженедельного обслуживания..."

# Обновляем основную систему
sudo apt update && sudo apt upgrade -y

# Обновляем все контейнеры
for container in $(sudo lxc-ls -1); do
    if [ "$(sudo lxc-info -n $container -s | grep State | awk '{print $2}')" = "RUNNING" ]; then
        echo "Обновляем $container..."
        sudo lxc-attach -n $container -- apt update
        sudo lxc-attach -n $container -- apt upgrade -y
        sudo lxc-attach -n $container -- apt autoremove -y
    fi
done

# Очистка логов старше 30 дней
find /var/log -name "*.log" -mtime +30 -delete

# Очистка старых снапшотов (оставляем последние 7)
for container in $(sudo lxc-ls -1); do
    sudo lxc-snapshot -L -n $container | tail -n +8 | awk '{print $1}' | while read snap; do
        sudo lxc-snapshot -d snap$snap -n $container
    done
done

# Перезапуск сервисов для применения обновлений
sudo systemctl restart nginx
sudo systemctl restart fail2ban

echo "✅ Обслуживание завершено!"
chmod +x /opt/scripts/*.sh

# Добавляем в cron
echo "0 4 * * 1 /opt/scripts/maintenance.sh >> /var/log/maintenance.log 2>&1" | sudo crontab -
🎉 Готово! У тебя есть полностью автоматизированная система управления множественными сайтами с максимальной безопасностью и удобством управления.

🏁 Заключение

Теперь у тебя есть производственная инфраструктура корпоративного уровня:

✅ Что получилось:

  • Безопасность: Каждый сайт изолирован, защита от атак
  • Масштабируемость: Легко добавлять новые сайты
  • Автоматизация: Минимум ручной работы
  • Мониторинг: Полный контроль над состоянием
  • Надежность: Автоматические бэкапы в облако

🚀 Следующие шаги:

  1. Запусти /opt/scripts/site-manager.sh для создания первого сайта
  2. Настрой мониторинг под свои нужды
  3. Протестируй восстановление из бэкапа
  4. Добавь собственные автоматизации

⚠️ Важные напоминания:

  • Регулярно проверяй логи безопасности
  • Обновляй системы минимум раз в неделю
  • Тестируй восстановление из бэкапов
  • Мониторь расходы на Wasabi

🎯 Твой сервер готов к продакшену!


 

📋 Дополнения к инструкции

Недостающие детали, примеры и best practices для вашего сервера

🔧 Недостающие скрипты и конфигурации

⚡ Node.js сайты — полный скрипт создания

sudo nano /opt/scripts/create-nodejs-site.sh
#!/bin/bash
SITE_NAME=$1
CONTAINER_IP=$2
NODE_VERSION="18"

if [ "$#" -ne 2 ]; then
    echo "Usage: $0  "
    echo "Example: $0 myapp 10.0.100.15"
    exit 1
fi

echo "🚀 Создаем Node.js сайт: $SITE_NAME с IP $CONTAINER_IP"

# Создаем базовый контейнер
/opt/scripts/create-html-site.sh ${SITE_NAME} ${CONTAINER_IP}

# Ждем запуска контейнера
sleep 10

# Устанавливаем Node.js
sudo lxc-attach -n ${SITE_NAME} -- bash -c "
apt update
curl -fsSL https://deb.nodesource.com/setup_${NODE_VERSION}.x | bash -
apt install -y nodejs nginx
npm install -g pm2 yarn

# Создаем структуру проекта
mkdir -p /var/www/${SITE_NAME}
cd /var/www/${SITE_NAME}

# Создаем базовый Express.js проект
npm init -y
npm install express helmet cors compression morgan

# Создаем базовый app.js с best practices
cat > app.js << 'EOF' const express = require('express'); const helmet = require('helmet'); const cors = require('cors'); const compression = require('compression'); const morgan = require('morgan'); const app = express(); const port = process.env.PORT || 3000; // Security middleware app.use(helmet()); app.use(cors()); app.use(compression()); app.use(morgan('combined')); // Basic middleware app.use(express.json({ limit: '10mb' })); app.use(express.urlencoded({ extended: true, limit: '10mb' })); // Routes app.get('/', (req, res) => {
    res.json({
        message: 'Hello from ${SITE_NAME}!',
        timestamp: new Date().toISOString(),
        environment: process.env.NODE_ENV || 'development'
    });
});

app.get('/health', (req, res) => {
    res.json({ status: 'OK', uptime: process.uptime() });
});

// Error handling
app.use((err, req, res, next) => {
    console.error(err.stack);
    res.status(500).json({ error: 'Something went wrong!' });
});

app.listen(port, '127.0.0.1', () => {
    console.log(\`${SITE_NAME} server running on port \${port}\`);
});
EOF

# Создаем ecosystem.config.js для PM2
cat > ecosystem.config.js << 'EOF' module.exports = { apps: [{ name: '${SITE_NAME}', script: 'app.js', instances: 1, autorestart: true, watch: false, max_memory_restart: '1G', env: { NODE_ENV: 'production', PORT: 3000 }, log_file: '/var/log/${SITE_NAME}.log', out_file: '/var/log/${SITE_NAME}-out.log', error_file: '/var/log/${SITE_NAME}-error.log' }] }; EOF # Настраиваем PM2 pm2 start ecosystem.config.js pm2 startup systemd pm2 save # Настраиваем Nginx как reverse proxy для Node.js cat > /etc/nginx/sites-available/default << 'EOF'
server {
    listen 80;
    server_name localhost;
    
    # Security headers
    add_header X-Frame-Options DENY;
    add_header X-Content-Type-Options nosniff;
    add_header X-XSS-Protection \"1; mode=block\";
    
    # Gzip compression
    gzip on;
    gzip_vary on;
    gzip_min_length 1024;
    gzip_proxied any;
    gzip_comp_level 6;
    gzip_types text/plain text/css application/json application/javascript text/xml;
    
    location / {
        proxy_pass http://127.0.0.1:3000;
        proxy_http_version 1.1;
        proxy_set_header Upgrade \$http_upgrade;
        proxy_set_header Connection 'upgrade';
        proxy_set_header Host \$host;
        proxy_set_header X-Real-IP \$remote_addr;
        proxy_set_header X-Forwarded-For \$proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto \$scheme;
        proxy_cache_bypass \$http_upgrade;
        
        # Timeouts
        proxy_connect_timeout 60s;
        proxy_send_timeout 60s;
        proxy_read_timeout 60s;
    }
    
    # Health check endpoint
    location /health {
        proxy_pass http://127.0.0.1:3000/health;
        access_log off;
    }
}
EOF

# Тестируем и перезапускаем nginx
nginx -t && systemctl restart nginx

# Настраиваем права доступа
chown -R www-data:www-data /var/www/${SITE_NAME}
chmod -R 755 /var/www/${SITE_NAME}
"

echo "✅ Node.js сайт ${SITE_NAME} создан успешно!"
echo "📊 Проверка статуса: pm2 status (внутри контейнера)"
echo "🌐 Health check: http://${CONTAINER_IP}/health"

💡 Что включено:

  • Express.js с безопасными middleware (helmet, cors)
  • PM2 для управления процессами
  • Health check эндпоинт
  • Логирование и error handling
  • Gzip сжатие в Nginx
  • Security headers

🎯 Ограничение ресурсов контейнеров

📊 Детальная настройка лимитов

sudo nano /opt/scripts/set-container-limits.sh
#!/bin/bash
CONTAINER_NAME=$1
CPU_LIMIT=$2      # Например: 1.5 (полтора ядра)
RAM_LIMIT=$3      # Например: 512M или 1G
DISK_LIMIT=$4     # Например: 10G (опционально)

if [ "$#" -lt 3 ]; then
    echo "Usage: $0    [disk_limit]"
    echo ""
    echo "Examples:"
    echo "  $0 small-site 0.5 256M"
    echo "  $0 wordpress-blog 1.0 1G"
    echo "  $0 high-load-app 2.0 4G 20G"
    exit 1
fi

echo "🎛️ Настраиваем лимиты для контейнера: $CONTAINER_NAME"

# Проверяем существование контейнера
if ! sudo lxc-info -n $CONTAINER_NAME >/dev/null 2>&1; then
    echo "❌ Контейнер $CONTAINER_NAME не найден!"
    exit 1
fi

# Останавливаем контейнер
echo "⏹️ Останавливаем контейнер..."
sudo lxc-stop -n $CONTAINER_NAME

# Настройка CPU лимита (в микросекундах на период 100мс)
CPU_QUOTA=$(echo "$CPU_LIMIT * 100000" | bc)
echo "lxc.cgroup2.cpu.max = $CPU_QUOTA 100000" | sudo tee -a /var/lib/lxc/$CONTAINER_NAME/config

# Настройка RAM лимита
echo "lxc.cgroup2.memory.max = $RAM_LIMIT" | sudo tee -a /var/lib/lxc/$CONTAINER_NAME/config
echo "lxc.cgroup2.memory.swap.max = 0" | sudo tee -a /var/lib/lxc/$CONTAINER_NAME/config

# Настройка приоритета (nice value)
echo "lxc.cgroup2.cpu.weight = 100" | sudo tee -a /var/lib/lxc/$CONTAINER_NAME/config

# Если указан лимит диска
if [ ! -z "$DISK_LIMIT" ]; then
    # Создаем loop device для контейнера с ограниченным размером
    LOOP_FILE="/var/lib/lxc-disks/${CONTAINER_NAME}.img"
    sudo mkdir -p /var/lib/lxc-disks
    
    echo "💾 Создаем виртуальный диск размером $DISK_LIMIT"
    sudo fallocate -l $DISK_LIMIT $LOOP_FILE
    sudo mkfs.ext4 $LOOP_FILE
    
    # Добавляем mount point в конфигурацию
    echo "lxc.mount.entry = $LOOP_FILE var/www ext4 loop,rw 0 0" | sudo tee -a /var/lib/lxc/$CONTAINER_NAME/config
fi

# Добавляем мониторинг ресурсов
cat >> /var/lib/lxc/$CONTAINER_NAME/config << EOF # Resource monitoring lxc.cgroup2.memory.events.file = /var/lib/lxc/$CONTAINER_NAME/memory.events lxc.cgroup2.cpu.stat.file = /var/lib/lxc/$CONTAINER_NAME/cpu.stat EOF # Запускаем контейнер echo "▶️ Запускаем контейнер..." sudo lxc-start -n $CONTAINER_NAME # Ждем запуска sleep 5 # Проверяем статус if sudo lxc-info -n $CONTAINER_NAME | grep -q "RUNNING"; then echo "✅ Контейнер успешно запущен с лимитами:" echo " CPU: $CPU_LIMIT cores" echo " RAM: $RAM_LIMIT" if [ ! -z "$DISK_LIMIT" ]; then echo " Disk: $DISK_LIMIT" fi # Показываем текущее использование echo "" echo "📊 Текущее использование ресурсов:" sudo lxc-attach -n $CONTAINER_NAME -- free -h sudo lxc-attach -n $CONTAINER_NAME -- df -h 2>/dev/null || echo "Диск недоступен"
else
    echo "❌ Ошибка запуска контейнера!"
    exit 1
fi

📈 Мониторинг ресурсов в реальном времени

sudo nano /opt/scripts/monitor-containers.sh
#!/bin/bash
# Мониторинг ресурсов всех контейнеров в реальном времени

watch -n 2 '
clear
echo "🖥️  SERVER RESOURCE MONITOR - $(date)"
echo "════════════════════════════════════════════════════════════════"

# Общие ресурсы сервера
echo "📊 HOST SYSTEM:"
echo "CPU Usage: $(top -bn1 | grep "Cpu(s)" | awk "{print \$2}" | cut -d"%" -f1)%"
echo "RAM Usage: $(free | awk "NR==2{printf \"%.1f%%\", \$3*100/\$2}")"
echo "Load Average: $(cat /proc/loadavg | awk "{print \$1, \$2, \$3}")"
echo ""

# Статус контейнеров
echo "📦 CONTAINERS:"
printf "%-15s %-8s %-8s %-8s %-10s\n" "NAME" "STATUS" "CPU%" "RAM%" "DISK%"
echo "────────────────────────────────────────────────────────────────"

for container in $(sudo lxc-ls -1 2>/dev/null); do
    status=$(sudo lxc-info -n $container -s 2>/dev/null | grep State | awk "{print \$2}")
    
    if [ "$status" = "RUNNING" ]; then
        # CPU usage (получаем из cgroup)
        cpu_usage=$(sudo lxc-attach -n $container -- grep "cpu " /proc/stat 2>/dev/null | awk "{u=\$2+\$4; t=\$2+\$3+\$4+\$5; if (NR==1){u1=u; t1=t;} else printf \"%.1f\", (u-u1) * 100 / (t-t1); }")
        [ -z "$cpu_usage" ] && cpu_usage="N/A"
        
        # RAM usage
        ram_usage=$(sudo lxc-attach -n $container -- free 2>/dev/null | awk "NR==2{printf \"%.1f\", \$3*100/\$2}")
        [ -z "$ram_usage" ] && ram_usage="N/A"
        
        # Disk usage
        disk_usage=$(sudo lxc-attach -n $container -- df / 2>/dev/null | awk "NR==2{print \$5}" | sed "s/%//")
        [ -z "$disk_usage" ] && disk_usage="N/A"
        
        printf "%-15s %-8s %-7s%% %-7s%% %-9s%%\n" "$container" "$status" "$cpu_usage" "$ram_usage" "$disk_usage"
    else
        printf "%-15s %-8s %-8s %-8s %-10s\n" "$container" "$status" "---" "---" "---"
    fi
done

echo ""
echo "💡 Press Ctrl+C to exit monitoring"
'
chmod +x /opt/scripts/*.sh

🔍 Диагностика и troubleshooting

🚨 Полный скрипт диагностики

sudo nano /opt/scripts/full-diagnostics.sh
#!/bin/bash
# Комплексная диагностика системы и контейнеров

LOG_FILE="/tmp/diagnostics-$(date +%Y%m%d-%H%M%S).log"

echo "🔍 Запуск полной диагностики системы..." | tee $LOG_FILE
echo "Результат будет сохранен в: $LOG_FILE" | tee -a $LOG_FILE
echo "═══════════════════════════════════════════════════════════════════" | tee -a $LOG_FILE
echo "" | tee -a $LOG_FILE

# 1. Информация о системе
echo "🖥️ SYSTEM INFORMATION:" | tee -a $LOG_FILE
echo "────────────────────────" | tee -a $LOG_FILE
{
    echo "Hostname: $(hostname)"
    echo "Uptime: $(uptime -p)"
    echo "Kernel: $(uname -r)"
    echo "OS: $(lsb_release -d | cut -f2)"
    echo "Architecture: $(uname -m)"
    echo "CPU: $(lscpu | grep "Model name" | cut -d':' -f2 | xargs)"
    echo "RAM: $(free -h | awk 'NR==2{printf "%s total, %s used, %s available", $2,$3,$7}')"
    echo "Disk: $(df -h / | awk 'NR==2{printf "%s total, %s used, %s available (%s used)", $2,$3,$4,$5}')"
} | tee -a $LOG_FILE
echo "" | tee -a $LOG_FILE

# 2. Статус ключевых сервисов
echo "🔧 SERVICE STATUS:" | tee -a $LOG_FILE
echo "──────────────────" | tee -a $LOG_FILE
for service in nginx fail2ban ufw lxc ssh; do
    status=$(systemctl is-active $service 2>/dev/null || echo "inactive")
    echo "$service: $status" | tee -a $LOG_FILE
done
echo "" | tee -a $LOG_FILE

# 3. Сетевая конфигурация
echo "🌐 NETWORK CONFIGURATION:" | tee -a $LOG_FILE
echo "──────────────────────────" | tee -a $LOG_FILE
{
    echo "Interfaces:"
    ip -4 addr show | grep -E '^[0-9]|inet ' | sed 's/^/  /'
    echo ""
    echo "Routing table:"
    ip route | sed 's/^/  /'
    echo ""
    echo "DNS configuration:"
    cat /etc/resolv.conf | sed 's/^/  /'
    echo ""
    echo "Listening ports:"
    netstat -tuln | grep LISTEN | sed 's/^/  /'
} | tee -a $LOG_FILE
echo "" | tee -a $LOG_FILE

# 4. Состояние контейнеров
echo "📦 CONTAINERS STATUS:" | tee -a $LOG_FILE
echo "─────────────────────" | tee -a $LOG_FILE
if command -v lxc-ls >/dev/null 2>&1; then
    for container in $(sudo lxc-ls -1 2>/dev/null); do
        echo "Container: $container" | tee -a $LOG_FILE
        sudo lxc-info -n $container 2>&1 | sed 's/^/  /' | tee -a $LOG_FILE
        echo "" | tee -a $LOG_FILE
    done
else
    echo "LXC not installed or not accessible" | tee -a $LOG_FILE
fi
echo "" | tee -a $LOG_FILE

# 5. Безопасность
echo "🔒 SECURITY STATUS:" | tee -a $LOG_FILE
echo "────────────────────" | tee -a $LOG_FILE
{
    echo "UFW status:"
    sudo ufw status verbose | sed 's/^/  /'
    echo ""
    echo "Fail2ban status:"
    sudo fail2ban-client status | sed 's/^/  /'
    echo ""
    echo "Recent failed login attempts:"
    grep "authentication failure" /var/log/auth.log | tail -5 | sed 's/^/  /' 2>/dev/null || echo "  No recent failures found"
    echo ""
    echo "SSH configuration:"
    grep -E "^(Port|PasswordAuthentication|PermitRootLogin|AllowUsers)" /etc/ssh/sshd_config | sed 's/^/  /'
} | tee -a $LOG_FILE
echo "" | tee -a $LOG_FILE

# 6. Производительность
echo "⚡ PERFORMANCE METRICS:" | tee -a $LOG_FILE
echo "──────────────────────" | tee -a $LOG_FILE
{
    echo "Load average (1min, 5min, 15min):"
    cat /proc/loadavg | sed 's/^/  /'
    echo ""
    echo "Memory usage:"
    free -h | sed 's/^/  /'
    echo ""
    echo "Disk I/O:"
    iostat -x 1 1 2>/dev/null | tail -n +4 | sed 's/^/  /' || echo "  iostat not available"
    echo ""
    echo "Top processes by CPU:"
    ps aux --sort=-%cpu | head -6 | sed 's/^/  /'
    echo ""
    echo "Top processes by Memory:"
    ps aux --sort=-%mem | head -6 | sed 's/^/  /'
} | tee -a $LOG_FILE
echo "" | tee -a $LOG_FILE

# 7. Логи ошибок
echo "📝 RECENT ERROR LOGS:" | tee -a $LOG_FILE
echo "────────────────────" | tee -a $LOG_FILE
{
    echo "System journal errors (last 10):"
    sudo journalctl -p err --no-pager -n 10 | sed 's/^/  /'
    echo ""
    echo "Nginx errors (last 5):"
    sudo tail -5 /var/log/nginx/error.log 2>/dev/null | sed 's/^/  /' || echo "  No nginx error log found"
} | tee -a $LOG_FILE
echo "" | tee -a $LOG_FILE

# 8. Дисковое пространство
echo "💾 DISK USAGE:" | tee -a $LOG_FILE
echo "──────────────" | tee -a $LOG_FILE
{
    echo "Filesystem usage:"
    df -h | sed 's/^/  /'
    echo ""
    echo "Largest directories in /var:"
    du -sh /var/* 2>/dev/null | sort -hr | head -5 | sed 's/^/  /'
    echo ""
    echo "LXC containers disk usage:"
    du -sh /var/lib/lxc/* 2>/dev/null | sort -hr | sed 's/^/  /' || echo "  No LXC containers found"
} | tee -a $LOG_FILE

echo "" | tee -a $LOG_FILE
echo "═══════════════════════════════════════════════════════════════════" | tee -a $LOG_FILE
echo "✅ Диагностика завершена. Полный отчет сохранен в: $LOG_FILE" | tee -a $LOG_FILE
echo "📧 Отправьте этот файл в техподдержку при необходимости." | tee -a $LOG_FILE

✅ Использование:

  • ./full-diagnostics.sh — запуск полной диагностики
  • ./monitor-containers.sh — мониторинг в реальном времени
  • ./set-container-limits.sh mysite 1.5 2G — настройка лимитов

🌟 Практические примеры реального использования

🏪 Пример 1: Интернет-магазин на WordPress

Задача: Создать высокопроизводительный интернет-магазин с отдельным IP адресом
# 1. Заказываем дополнительный IP в Hetzner Robot Panel
# Получили IP: 65.108.1.101

# 2. Добавляем IP к серверу
/opt/scripts/add-ip.sh 65.108.1.101 shop-site

# 3. Создаем WordPress контейнер с увеличенными ресурсами  
/opt/scripts/create-wordpress-site.sh shop-site 10.0.100.20

# 4. Настраиваем лимиты ресурсов (магазин требует больше)
/opt/scripts/set-container-limits.sh shop-site 2.0 4G

# 5. Создаем Nginx конфигурацию для магазина
sudo nano /etc/nginx/sites-available/shop-site
server {
    listen 65.108.1.101:80;  # Слушаем на выделенном IP
    server_name shop.yourdomain.com;
    
    # Rate limiting для защиты от DDoS
    limit_req_zone $binary_remote_addr zone=shop_login:10m rate=5r/m;
    limit_req_zone $binary_remote_addr zone=shop_general:10m rate=10r/s;
    
    location / {
        limit_req zone=shop_general burst=20 nodelay;
        
        proxy_pass http://10.0.100.20:80;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
        
        # Кеширование статического контента
        location ~* \.(jpg|jpeg|png|gif|ico|css|js|webp)$ {
            proxy_pass http://10.0.100.20:80;
            expires 1y;
            add_header Cache-Control "public, immutable";
            add_header Vary Accept-Encoding;
        }
    }
    
    # Особая защита для админки WordPress
    location /wp-admin/ {
        limit_req zone=shop_login burst=5 nodelay;
        allow YOUR_IP;           # Замени на свой IP
        deny all;                # Блокируем доступ для всех остальных
        
        proxy_pass http://10.0.100.20:80;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
    }
    
    # Блокируем доступ к чувствительным файлам
    location ~* \.(log|sql|conf)$ {
        deny all;
    }
}
# 6. Активируем конфигурацию
sudo ln -s /etc/nginx/sites-available/shop-site /etc/nginx/sites-enabled/
sudo nginx -t && sudo systemctl reload nginx

# 7. Получаем SSL сертификат
/opt/scripts/add-ssl.sh shop.yourdomain.com

# 8. Настраиваем автоматические бэкапы только этого сайта
sudo nano /opt/scripts/backup-shop-site.sh

🚀 Пример 2: Node.js API с балансировкой нагрузки

# 1. Создаем 3 одинаковых API контейнера
/opt/scripts/create-nodejs-site.sh api-v1 10.0.100.30
/opt/scripts/create-nodejs-site.sh api-v2 10.0.100.31  
/opt/scripts/create-nodejs-site.sh api-v3 10.0.100.32

# 2. Настраиваем одинаковые лимиты для всех
/opt/scripts/set-container-limits.sh api-v1 1.0 1G
/opt/scripts/set-container-limits.sh api-v2 1.0 1G
/opt/scripts/set-container-limits.sh api-v3 1.0 1G

# 3. Создаем балансировщик нагрузки
sudo nano /etc/nginx/sites-available/api-cluster
upstream api_backend {
    least_conn;  # Балансировка по наименьшему количеству соединений
    server 10.0.100.30:80 max_fails=3 fail_timeout=30s weight=1;
    server 10.0.100.31:80 max_fails=3 fail_timeout=30s weight=1;
    server 10.0.100.32:80 max_fails=3 fail_timeout=30s weight=1;
}

# Health check сервер
server {
    listen 8080;
    location /health-check {
        proxy_pass http://api_backend/health;
        access_log off;
    }
}

server {
    listen 80;
    server_name api.yourdomain.com;
    
    # API rate limiting
    limit_req_zone $binary_remote_addr zone=api:10m rate=100r/s;
    limit_req_zone $http_authorization zone=api_user:10m rate=1000r/s;
    
    location / {
        limit_req zone=api burst=200 nodelay;
        limit_req zone=api_user burst=500 nodelay;
        
        proxy_pass http://api_backend;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
        
        # Настройки для API
        proxy_buffering off;
        proxy_request_buffering off;
        proxy_connect_timeout 5s;
        proxy_send_timeout 10s;
        proxy_read_timeout 10s;
    }
    
    # Отдельная точка для health checks
    location /health {
        proxy_pass http://api_backend/health;
        access_log off;
    }
}

📊 Пример 3: Мониторинг и алерты для критичного проекта

# 1. Создаем выделенный контейнер для мониторинга
/opt/scripts/create-html-site.sh monitoring 10.0.100.100

# 2. Устанавливаем полный стек мониторинга
sudo lxc-attach -n monitoring -- bash -c "
apt update && apt install -y curl wget

# Prometheus
wget https://github.com/prometheus/prometheus/releases/download/v2.40.0/prometheus-2.40.0.linux-amd64.tar.gz
tar xvfz prometheus-*.tar.gz
sudo mv prometheus-2.40.0.linux-amd64/prometheus /usr/local/bin/
sudo mv prometheus-2.40.0.linux-amd64/promtool /usr/local/bin/
sudo mkdir -p /etc/prometheus /var/lib/prometheus
sudo chown prometheus:prometheus /etc/prometheus /var/lib/prometheus

# Grafana
wget -q -O - https://packages.grafana.com/gpg.key | apt-key add -
echo 'deb https://packages.grafana.com/oss/deb stable main' > /etc/apt/sources.list.d/grafana.list
apt update && apt install -y grafana

# Node Exporter
wget https://github.com/prometheus/node_exporter/releases/download/v1.5.0/node_exporter-1.5.0.linux-amd64.tar.gz
tar xvfz node_exporter-*.tar.gz
sudo mv node_exporter-1.5.0.linux-amd64/node_exporter /usr/local/bin/

# Создаем systemd сервисы
cat > /etc/systemd/system/prometheus.service << EOF
[Unit]
Description=Prometheus
After=network.target

[Service]
User=prometheus
Group=prometheus
Type=simple
ExecStart=/usr/local/bin/prometheus --config.file /etc/prometheus/prometheus.yml --storage.tsdb.path /var/lib/prometheus

[Install]
WantedBy=multi-user.target
EOF

systemctl daemon-reload
systemctl enable prometheus grafana-server node-exporter
systemctl start prometheus grafana-server node-exporter
"

# 3. Настраиваем Telegram уведомления
sudo nano /opt/scripts/telegram-alert.sh
#!/bin/bash
# Отправка критичных алертов в Telegram

TELEGRAM_BOT_TOKEN="YOUR_BOT_TOKEN"  # Получи у @BotFather
CHAT_ID="YOUR_CHAT_ID"               # Твой chat ID

MESSAGE="$1"
SEVERITY="$2"
SERVER_NAME=$(hostname)

# Выбираем эмодзи в зависимости от серьезности
case "$SEVERITY" in
    "CRITICAL") EMOJI="🚨" ;;
    "WARNING")  EMOJI="⚠️" ;;
    "INFO")     EMOJI="ℹ️" ;;
    *)          EMOJI="📢" ;;
esac

# Формируем сообщение
FULL_MESSAGE="${EMOJI} *${SEVERITY}* on *${SERVER_NAME}*

${MESSAGE}

Time: $(date '+%Y-%m-%d %H:%M:%S')
Server: ${SERVER_NAME}"

# Отправляем в Telegram
curl -s -X POST "https://api.telegram.org/bot${TELEGRAM_BOT_TOKEN}/sendMessage" \
    -d "chat_id=${CHAT_ID}" \
    -d "text=${FULL_MESSAGE}" \
    -d "parse_mode=Markdown" \
    -d "disable_notification=false"

# Дублируем в локальный лог
echo "$(date): [$SEVERITY] $MESSAGE" >> /var/log/alerts.log

🔐 Настройка Telegram бота:

  1. Напиши @BotFather в Telegram
  2. Создай нового бота: /newbot
  3. Получи токен и вставь в скрипт
  4. Узнай свой chat_id: напиши боту, затем перейди по https://api.telegram.org/botYOUR_TOKEN/getUpdates

📋 Чеклист финальной проверки

✅ Обязательная проверка перед продакшеном

sudo nano /opt/scripts/production-checklist.sh
#!/bin/bash
# Чеклист готовности к продакшену

echo "🔍 PRODUCTION READINESS CHECKLIST"
echo "=================================="
echo ""

TOTAL_CHECKS=0
PASSED_CHECKS=0

check_item() {
    local description="$1"
    local command="$2"
    local expected="$3"
    
    TOTAL_CHECKS=$((TOTAL_CHECKS + 1))
    
    printf "%-50s " "$description"
    
    if eval "$command" >/dev/null 2>&1; then
        if [ -z "$expected" ] || eval "$command" | grep -q "$expected"; then
            echo "✅ PASS"
            PASSED_CHECKS=$((PASSED_CHECKS + 1))
        else
            echo "❌ FAIL"
        fi
    else
        echo "❌ FAIL"
    fi
}

echo "🔒 SECURITY CHECKS:"
echo "─────────────────"
check_item "SSH password authentication disabled" "grep '^PasswordAuthentication no' /etc/ssh/sshd_config"
check_item "SSH running on non-standard port" "grep '^Port [0-9]' /etc/ssh/sshd_config" "Port 2222"
check_item "UFW firewall is active" "sudo ufw status" "Status: active"
check_item "Fail2ban is running" "sudo systemctl is-active fail2ban" "active"
check_item "Root login disabled" "grep '^PermitRootLogin no' /etc/ssh/sshd_config"
echo ""

echo "📦 CONTAINER CHECKS:"
echo "──────────────────"
for container in $(sudo lxc-ls -1 2>/dev/null); do
    check_item "Container $container is running" "sudo lxc-info -n $container -s" "RUNNING"
done
echo ""

echo "🌐 NETWORK CHECKS:"
echo "────────────────"
check_item "Nginx is running" "sudo systemctl is-active nginx" "active"
check_item "Port 80 is listening" "sudo netstat -tuln | grep ':80 '"
check_item "Port 443 is listening" "sudo netstat -tuln | grep ':443 '"
check_item "DNS resolution working" "nslookup google.com"
echo ""

echo "💾 BACKUP CHECKS:"
echo "───────────────"
check_item "Backup configuration exists" "test -f /opt/scripts/backup-config.env"
check_item "Restic is installed" "which restic"
check_item "Backup script is executable" "test -x /opt/scripts/full-backup.sh"
check_item "Backup cron job exists" "sudo crontab -l | grep backup"
echo ""

echo "📊 MONITORING CHECKS:"
echo "───────────────────"
check_item "Monitoring container exists" "sudo lxc-ls | grep -q monitoring"
check_item "Dashboard script exists" "test -x /opt/scripts/server-dashboard.sh"
check_item "Diagnostic script exists" "test -x /opt/scripts/full-diagnostics.sh"
echo ""

echo "⚡ PERFORMANCE CHECKS:"
echo "────────────────────"
check_item "System load is reasonable" "test $(cat /proc/loadavg | cut -d' ' -f1 | cut -d'.' -f1) -lt 4"
check_item "Free memory available" "test $(free | awk 'NR==2{print ($4/$2)*100}' | cut -d'.' -f1) -gt 20"
check_item "Root filesystem not full" "test $(df / | awk 'NR==2{print $5}' | sed 's/%//') -lt 90"
check_item "All containers have resource limits" "test $(sudo lxc-ls -1 | wc -l) -eq $(grep -l 'lxc.cgroup2.memory.max' /var/lib/lxc/*/config | wc -l)"
echo ""

echo "═════════════════════════════════════════════════════════════"
echo "📊 RESULTS: $PASSED_CHECKS/$TOTAL_CHECKS checks passed"

if [ $PASSED_CHECKS -eq $TOTAL_CHECKS ]; then
    echo "🎉 ALL CHECKS PASSED! Server is production ready!"
    echo ""
    echo "🚀 Next steps:"
    echo "   1. Run a backup test: /opt/scripts/full-backup.sh"
    echo "   2. Monitor for 24h: /opt/scripts/monitor-containers.sh"
    echo "   3. Set up alerting: /opt/scripts/telegram-alert.sh"
    exit 0
else
    echo "⚠️  Some checks failed. Please fix issues before production!"
    exit 1
fi
🎯 Итог: Теперь у тебя есть enterprise-уровня инфраструктура с подробными примерами, мониторингом, диагностикой и чеклистом готовности!

 

🚀 Продвинутые оптимизации для AMD Ryzen 7 7700 сервера

Дополнительные критичные настройки для максимальной производительности и надёжности


1. 🎯 Гибкое управление ресурсами: приоритеты и жёсткие лимиты

Задача

Создать систему, где:

  • Второстепенные сайты получают максимум 5% CPU (жёсткий лимит)
  • Главный сайт получает 90% CPU как soft лимит + возможность burst до 100% при нагрузке
  • Автоматическое перераспределение ресурсов в зависимости от загрузки

🔧 Реализация через cgroups v2

Создание скрипта гибких лимитов:

sudo nano /opt/scripts/flexible-resource-limits.sh
#!/bin/bash
# Гибкое управление ресурсами контейнеров с приоритетами

CONTAINER_NAME=$1
PRIORITY=$2        # high, medium, low, critical
CPU_CORES=$(nproc) # Общее количество ядер (16 для Ryzen 7700 с SMT)

if [ "$#" -ne 2 ]; then
    echo "Usage: $0 <container_name> <priority>"
    echo "Priorities: critical, high, medium, low"
    echo ""
    echo "Examples:"
    echo "  $0 main-shop critical     # 90% CPU, burst до 100%"
    echo "  $0 blog-site high         # 30% CPU, burst до 50%"
    echo "  $0 test-site low          # 5% CPU, жёсткий лимит"
    exit 1
fi

echo "⚙️ Настраиваем приоритеты для контейнера: $CONTAINER_NAME (приоритет: $PRIORITY)"

# Останавливаем контейнер для изменения конфигурации
sudo lxc-stop -n $CONTAINER_NAME 2>/dev/null

# Создаём backup конфигурации
sudo cp /var/lib/lxc/$CONTAINER_NAME/config /var/lib/lxc/$CONTAINER_NAME/config.backup

# Удаляем старые лимиты
sudo sed -i '/lxc.cgroup2.cpu/d' /var/lib/lxc/$CONTAINER_NAME/config
sudo sed -i '/lxc.cgroup2.memory/d' /var/lib/lxc/$CONTAINER_NAME/config

case "$PRIORITY" in
    "critical")
        # Главный сайт: 90% soft limit, может использовать до 100% при необходимости
        CPU_SOFT_LIMIT=$((CPU_CORES * 90 / 100))    # 14.4 ядра
        CPU_HARD_LIMIT=$CPU_CORES                   # 16 ядер максимум
        MEMORY_LIMIT="16G"                          # Много памяти
        CPU_WEIGHT="1000"                           # Максимальный приоритет

        echo "🔥 CRITICAL: Soft ${CPU_SOFT_LIMIT} cores, Hard ${CPU_HARD_LIMIT} cores, RAM ${MEMORY_LIMIT}"
        ;;

    "high") 
        # Важный сайт: 30% soft, burst до 50%
        CPU_SOFT_LIMIT=$((CPU_CORES * 30 / 100))    # 4.8 ядра
        CPU_HARD_LIMIT=$((CPU_CORES * 50 / 100))    # 8 ядер максимум  
        MEMORY_LIMIT="4G"
        CPU_WEIGHT="500"

        echo "⭐ HIGH: Soft ${CPU_SOFT_LIMIT} cores, Hard ${CPU_HARD_LIMIT} cores, RAM ${MEMORY_LIMIT}"
        ;;

    "medium")
        # Обычный сайт: 15% soft, burst до 25%
        CPU_SOFT_LIMIT=$((CPU_CORES * 15 / 100))    # 2.4 ядра
        CPU_HARD_LIMIT=$((CPU_CORES * 25 / 100))    # 4 ядра максимум
        MEMORY_LIMIT="2G" 
        CPU_WEIGHT="200"

        echo "📊 MEDIUM: Soft ${CPU_SOFT_LIMIT} cores, Hard ${CPU_HARD_LIMIT} cores, RAM ${MEMORY_LIMIT}"
        ;;

    "low")
        # Тестовый/неважный сайт: жёсткий лимит 5%
        CPU_SOFT_LIMIT=$((CPU_CORES * 5 / 100))     # 0.8 ядра
        CPU_HARD_LIMIT=$CPU_SOFT_LIMIT              # Никакого burst!
        MEMORY_LIMIT="512M"
        CPU_WEIGHT="50"                             # Минимальный приоритет

        echo "⬇️ LOW: Hard limit ${CPU_HARD_LIMIT} cores, RAM ${MEMORY_LIMIT}"
        ;;

    *)
        echo "❌ Неизвестный приоритет: $PRIORITY"
        exit 1
        ;;
esac

# Применяем настройки CPU
# Soft limit (средний уровень потребления)
SOFT_QUOTA=$((CPU_SOFT_LIMIT * 100000))
echo "lxc.cgroup2.cpu.max = $SOFT_QUOTA 100000" >> /var/lib/lxc/$CONTAINER_NAME/config

# Hard limit (максимальный burst)
if [ "$CPU_HARD_LIMIT" != "$CPU_SOFT_LIMIT" ]; then
    HARD_QUOTA=$((CPU_HARD_LIMIT * 100000))
    echo "lxc.cgroup2.cpu.max.burst = $HARD_QUOTA 100000" >> /var/lib/lxc/$CONTAINER_NAME/config
fi

# CPU Weight (приоритет при конкуренции за ресурсы)
echo "lxc.cgroup2.cpu.weight = $CPU_WEIGHT" >> /var/lib/lxc/$CONTAINER_NAME/config

# Лимиты памяти
echo "lxc.cgroup2.memory.max = $MEMORY_LIMIT" >> /var/lib/lxc/$CONTAINER_NAME/config
echo "lxc.cgroup2.memory.swap.max = 0" >> /var/lib/lxc/$CONTAINER_NAME/config

# Настройки I/O (дисковые операции)
case "$PRIORITY" in
    "critical") IO_WEIGHT="1000" ;;
    "high")     IO_WEIGHT="500" ;;  
    "medium")   IO_WEIGHT="200" ;;
    "low")      IO_WEIGHT="50" ;;
esac

echo "lxc.cgroup2.io.weight = $IO_WEIGHT" >> /var/lib/lxc/$CONTAINER_NAME/config

# Запускаем контейнер
echo "▶️ Запускаем контейнер с новыми настройками..."
sudo lxc-start -n $CONTAINER_NAME

# Ждём запуска
sleep 5

# Проверяем результат
if sudo lxc-info -n $CONTAINER_NAME | grep -q "RUNNING"; then
    echo "✅ Контейнер успешно запущен!"
    echo ""
    echo "📊 Настройки ресурсов:"
    echo "   Приоритет: $PRIORITY"
    echo "   CPU Soft: ${CPU_SOFT_LIMIT} cores"
    echo "   CPU Hard: ${CPU_HARD_LIMIT} cores" 
    echo "   Memory: $MEMORY_LIMIT"
    echo "   CPU Weight: $CPU_WEIGHT"
    echo "   IO Weight: $IO_WEIGHT"

    # Создаём запись в реестре для мониторинга
    echo "$CONTAINER_NAME:$PRIORITY:$(date)" >> /opt/scripts/container-priorities.log
else
    echo "❌ Ошибка запуска контейнера!"
    # Восстанавливаем backup
    sudo cp /var/lib/lxc/$CONTAINER_NAME/config.backup /var/lib/lxc/$CONTAINER_NAME/config
    exit 1
fi

Практические примеры использования:

# Делаем исполняемым
chmod +x /opt/scripts/flexible-resource-limits.sh

# Главный интернет-магазин - критичный приоритет
./flexible-resource-limits.sh main-shop critical

# Корпоративный блог - высокий приоритет  
./flexible-resource-limits.sh company-blog high

# Личный сайт - средний приоритет
./flexible-resource-limits.sh personal-site medium

# Тестовая площадка - низкий приоритет (жёсткий лимит 5%)
./flexible-resource-limits.sh test-env low

📊 Мониторинг распределения ресурсов:

sudo nano /opt/scripts/priority-monitor.sh
#!/bin/bash
# Мониторинг использования ресурсов по приоритетам

echo "🎯 RESOURCE ALLOCATION BY PRIORITY - $(date)"
echo "════════════════════════════════════════════════════════════════"

# Заголовки таблицы
printf "%-15s %-10s %-8s %-12s %-12s %-8s %-8s\n" \
    "CONTAINER" "PRIORITY" "STATUS" "CPU_ACTUAL" "CPU_LIMIT" "RAM_USE" "RAM_LIMIT"
echo "────────────────────────────────────────────────────────────────────────────"

TOTAL_CPU_USAGE=0
CRITICAL_COUNT=0
HIGH_COUNT=0
MEDIUM_COUNT=0
LOW_COUNT=0

for container in $(sudo lxc-ls -1 2>/dev/null); do
    # Получаем приоритет из лога
    priority=$(grep "^$container:" /opt/scripts/container-priorities.log 2>/dev/null | tail -1 | cut -d':' -f2)
    [ -z "$priority" ] && priority="unknown"

    status=$(sudo lxc-info -n $container -s 2>/dev/null | grep State | awk '{print $2}')

    if [ "$status" = "RUNNING" ]; then
        # Получаем актуальное использование CPU (примерно)
        cpu_actual=$(sudo lxc-attach -n $container -- top -bn1 2>/dev/null | grep "Cpu(s)" | awk '{print $2}' | cut -d'%' -f1)
        [ -z "$cpu_actual" ] && cpu_actual="0"

        # Получаем лимиты из конфигурации
        cpu_limit=$(grep "lxc.cgroup2.cpu.max" /var/lib/lxc/$container/config | awk '{print $3/100000}' | head -1)
        [ -z "$cpu_limit" ] && cpu_limit="unlimited"

        # Получаем использование памяти
        ram_use=$(sudo lxc-attach -n $container -- free -h 2>/dev/null | grep '^Mem:' | awk '{print $3}')
        ram_limit=$(grep "lxc.cgroup2.memory.max" /var/lib/lxc/$container/config | awk '{print $3}')

        # Считаем по приоритетам
        case "$priority" in
            "critical") CRITICAL_COUNT=$((CRITICAL_COUNT + 1)) ;;
            "high")     HIGH_COUNT=$((HIGH_COUNT + 1)) ;;
            "medium")   MEDIUM_COUNT=$((MEDIUM_COUNT + 1)) ;;
            "low")      LOW_COUNT=$((LOW_COUNT + 1)) ;;
        esac

        TOTAL_CPU_USAGE=$(echo "$TOTAL_CPU_USAGE + $cpu_actual" | bc -l)
    else
        cpu_actual="--"
        cpu_limit="--"
        ram_use="--"
        ram_limit="--"
    fi

    # Цветовая индикация приоритета
    case "$priority" in
        "critical") priority_display="🔥 CRIT" ;;
        "high")     priority_display="⭐ HIGH" ;;
        "medium")   priority_display="📊 MED" ;;
        "low")      priority_display="⬇️ LOW" ;;
        *)          priority_display="❓ UNK" ;;
    esac

    printf "%-15s %-10s %-8s %-12s %-12s %-8s %-8s\n" \
        "$container" "$priority_display" "$status" "${cpu_actual}%" "$cpu_limit" "$ram_use" "$ram_limit"
done

echo ""
echo "📈 SUMMARY:"
echo "Total CPU Usage: ${TOTAL_CPU_USAGE}%"
echo "Containers by priority: CRITICAL($CRITICAL_COUNT), HIGH($HIGH_COUNT), MEDIUM($MEDIUM_COUNT), LOW($LOW_COUNT)"

# Проверяем не превышают ли лимиты
if (( $(echo "$TOTAL_CPU_USAGE > 80" | bc -l) )); then
    echo "⚠️  WARNING: High CPU usage detected! Consider rebalancing priorities."
fi

2. 🔥 AMD Ryzen 7 7700: SMT и AMD-V настройки

Критичная важность для виртуализации

AMD Ryzen 7 7700 имеет:

  • 8 физических ядер
  • SMT (Simultaneous Multithreading) = 16 логических потоков
  • AMD-V (Virtualization) — аппаратная виртуализация
  • IOMMU — изоляция памяти для безопасности

🚨 БЕЗ правильной настройки ты теряешь 30-60% производительности!

Пошаговая настройка:

Шаг 1: Настройка BIOS/UEFI

Обязательные настройки в BIOS:

При загрузке: Del или F2 → Advanced Settings

🔧 CPU Configuration:
   ├─ AMD SVM Mode: [ENABLED] ⚠️ КРИТИЧНО!
   ├─ SMT (Simultaneous Multithreading): [ENABLED] 
   ├─ Core Performance Boost: [ENABLED]
   └─ Precision Boost Overdrive: [ENABLED]

🔧 Advanced → Chipset Configuration:
   ├─ IOMMU: [ENABLED] ⚠️ Для безопасности контейнеров
   └─ ACS Enable: [ENABLED]

🔧 Power Management:
   ├─ Power Supply Idle Control: [Low Current Idle]
   ├─ CPPC: [ENABLED]
   └─ Global C-state Control: [DISABLED] (для стабильной производительности)

Шаг 2: Проверка после загрузки

# Создаём скрипт проверки AMD настроек
sudo nano /opt/scripts/check-amd-features.sh
#!/bin/bash
# Проверка корректной настройки AMD Ryzen 7 7700

echo "🔍 AMD Ryzen 7 7700 Configuration Check"
echo "══════════════════════════════════════════════════════════"

# 1. Информация о процессоре
echo "💻 CPU Information:"
CPU_MODEL=$(lscpu | grep "Model name" | cut -d':' -f2 | xargs)
echo "   Model: $CPU_MODEL"

# 2. Проверка SMT (должно быть 2 потока на ядро)
THREADS_PER_CORE=$(lscpu | grep "Thread(s) per core" | awk '{print $4}')
CORES=$(lscpu | grep "^CPU(s):" | awk '{print $2}')
PHYSICAL_CORES=$(lscpu | grep "Core(s) per socket" | awk '{print $4}')

echo "   Physical cores: $PHYSICAL_CORES"
echo "   Logical cores: $CORES"
echo "   Threads per core: $THREADS_PER_CORE"

if [ "$THREADS_PER_CORE" = "2" ]; then
    echo "   ✅ SMT is ENABLED (16 logical cores available)"
else
    echo "   ❌ SMT is DISABLED! Enable in BIOS for better performance!"
    exit 1
fi

# 3. Проверка AMD-V (виртуализация)
echo ""
echo "🚀 Virtualization Support:"

if grep -q "svm" /proc/cpuinfo; then
    echo "   ✅ AMD-V (SVM) is ENABLED"
else
    echo "   ❌ AMD-V is DISABLED! Enable SVM Mode in BIOS!"
    exit 1
fi

# 4. Проверка IOMMU
echo ""
echo "🔒 IOMMU Support:"
if [ -d "/sys/kernel/iommu_groups" ] && [ "$(ls /sys/kernel/iommu_groups | wc -l)" -gt 0 ]; then
    IOMMU_COUNT=$(ls /sys/kernel/iommu_groups | wc -l)
    echo "   ✅ IOMMU is ENABLED ($IOMMU_COUNT groups found)"
else
    echo "   ⚠️  IOMMU is DISABLED (less secure container isolation)"
fi

# 5. Проверка KVM готовности
echo ""
echo "📦 Container/VM Support:"
if [ -c /dev/kvm ]; then
    echo "   ✅ KVM device available"
else
    echo "   ❌ KVM device not found"
fi

# Устанавливаем cpu-checker если не установлен
if ! command -v kvm-ok >/dev/null 2>&1; then
    echo "   Installing cpu-checker..."
    sudo apt update && sudo apt install -y cpu-checker >/dev/null 2>&1
fi

KVM_CHECK=$(kvm-ok 2>&1)
if echo "$KVM_CHECK" | grep -q "KVM acceleration can be used"; then
    echo "   ✅ KVM acceleration available"
else
    echo "   ❌ KVM acceleration not available:"
    echo "      $KVM_CHECK"
fi

# 6. Проверка LXC поддержки
echo ""
echo "🐧 LXC Support:"
if command -v lxc-checkconfig >/dev/null 2>&1; then
    LXC_MISSING=$(lxc-checkconfig 2>&1 | grep -i "missing\|required" | wc -l)
    if [ "$LXC_MISSING" -eq 0 ]; then
        echo "   ✅ LXC fully supported"
    else
        echo "   ⚠️  LXC has $LXC_MISSING missing features"
        echo "   Details: $(lxc-checkconfig 2>&1 | grep -i "missing\|required" | head -3)"
    fi
else
    echo "   ❌ LXC not installed"
fi

# 7. CPU Governor и частоты
echo ""
echo "⚡ CPU Performance:"
GOVERNOR=$(cat /sys/devices/system/cpu/cpu0/cpufreq/scaling_governor 2>/dev/null || echo "unknown")
echo "   CPU Governor: $GOVERNOR"

if [ "$GOVERNOR" = "performance" ]; then
    echo "   ✅ Performance governor active"
elif [ "$GOVERNOR" = "ondemand" ]; then
    echo "   ⚠️  OnDemand governor (good for servers)"
else
    echo "   ❓ Governor: $GOVERNOR"
fi

# Показываем текущие частоты
echo "   Current frequencies:"
for i in {0..15}; do
    if [ -f "/sys/devices/system/cpu/cpu$i/cpufreq/scaling_cur_freq" ]; then
        freq=$(cat /sys/devices/system/cpu/cpu$i/cpufreq/scaling_cur_freq)
        freq_mhz=$((freq / 1000))
        echo "      CPU$i: ${freq_mhz}MHz"
    fi
done | head -4
echo "      ... (showing first 4 cores)"

# 8. Температурный мониторинг
echo ""
echo "🌡️  Temperature Monitoring:"
if command -v sensors >/dev/null 2>&1; then
    CPU_TEMP=$(sensors 2>/dev/null | grep -i "Tctl\|Package" | head -1 | awk '{print $2}')
    echo "   CPU Temperature: $CPU_TEMP"
else
    echo "   ❌ lm-sensors not installed. Install: sudo apt install lm-sensors"
fi

echo ""
echo "══════════════════════════════════════════════════════════"

# Итоговая проверка
ERRORS=0

if [ "$THREADS_PER_CORE" != "2" ]; then
    echo "❌ CRITICAL: SMT disabled"
    ERRORS=$((ERRORS + 1))
fi

if ! grep -q "svm" /proc/cpuinfo; then
    echo "❌ CRITICAL: AMD-V disabled"  
    ERRORS=$((ERRORS + 1))
fi

if [ ! -c /dev/kvm ]; then
    echo "❌ ERROR: KVM not available"
    ERRORS=$((ERRORS + 1))
fi

if [ "$ERRORS" -eq 0 ]; then
    echo "🎉 ALL CHECKS PASSED! AMD Ryzen 7 7700 is optimally configured!"
    echo ""
    echo "💪 Your server can handle:"
    echo "   • 20+ lightweight containers (0.5-1 core each)"
    echo "   • 10-15 WordPress sites (1-2 cores each)"  
    echo "   • 4-8 high-performance applications (2-4 cores each)"
    echo "   • Full 16-thread parallel processing power"
else
    echo "⚠️  $ERRORS CRITICAL ISSUES found! Fix them for optimal performance."
    exit 1
fi

Шаг 3: Оптимизация для контейнеров

# Оптимизация системы для AMD Ryzen 7700
sudo nano /etc/sysctl.d/99-amd-optimization.conf
# AMD Ryzen 7 7700 оптимизации для контейнеров

# CPU планировщик для многопоточности  
kernel.sched_migration_cost_ns = 5000000
kernel.sched_autogroup_enabled = 0
kernel.sched_wakeup_granularity_ns = 15000000

# SMT оптимизации
kernel.sched_smt_power_savings = 0

# Виртуальная память для большого количества контейнеров
vm.max_map_count = 262144
vm.overcommit_memory = 1
vm.overcommit_ratio = 80

# Файловая система (для NVMe SSD)
vm.dirty_ratio = 15
vm.dirty_background_ratio = 5
vm.vfs_cache_pressure = 50

# Сетевые оптимизации для контейнеров
net.core.somaxconn = 32768
net.ipv4.ip_local_port_range = 1024 65535
net.core.rmem_max = 134217728
net.core.wmem_max = 134217728
# Применяем настройки
sudo sysctl -p /etc/sysctl.d/99-amd-optimization.conf

Примеры использования 16 потоков:

# Пример 1: Равномерное распределение
./flexible-resource-limits.sh shop1 medium     # 2.4 ядра
./flexible-resource-limits.sh shop2 medium     # 2.4 ядра  
./flexible-resource-limits.sh blog1 low        # 0.8 ядра
./flexible-resource-limits.sh blog2 low        # 0.8 ядра
./flexible-resource-limits.sh api1 high        # 4.8 ядра
./flexible-resource-limits.sh main critical    # 5.6 ядра
# Итого: ~16 ядер полностью использованы

# Пример 2: Один доминирующий сайт
./flexible-resource-limits.sh main-site critical  # 14.4 ядра + burst до 16
./flexible-resource-limits.sh test1 low           # 0.8 ядра  
./flexible-resource-limits.sh test2 low           # 0.8 ядра
# Итого: главный сайт получает практически все ресурсы

3. 💾 Software RAID 1 для 2x 1TB NVMe SSD

Задача безопасности данных

С двумя NVMe дисками нужно настроить зеркалирование (RAID 1):

  • Данные одновременно пишутся на оба диска
  • При отказе одного диска система продолжает работать
  • Автоматическое восстановление при замене диска

🔧 Настройка RAID 1 при установке системы

Вариант A: Настройка через Hetzner installimage

# Во время установки через rescue система
installimage

# В конфигурации диска используй:
PART /boot ext4 1G
PART / ext4 100G raid1
PART /var ext4 400G raid1  
PART /home ext4 all raid1

# Система автоматически создаст RAID 1

Вариант B: Ручная настройка после установки

# ⚠️ ВНИМАНИЕ: Этот метод удалит все данные!
# Используй только на новом сервере или с полным бэкапом

sudo nano /opt/scripts/setup-raid1.sh
#!/bin/bash
# Настройка Software RAID 1 для двух NVMe дисков

DISK1="/dev/nvme0n1"  # Первый NVMe диск
DISK2="/dev/nvme1n1"  # Второй NVMe диск

echo "🚨 ВНИМАНИЕ: Этот скрипт УДАЛИТ ВСЕ ДАННЫЕ на дисках!"
echo "Диски для RAID 1: $DISK1 и $DISK2"
echo ""
read -p "Вы уверены? Введите 'YES' для продолжения: " confirm

if [ "$confirm" != "YES" ]; then
    echo "Отменено пользователем"
    exit 1
fi

echo "🔧 Начинаем настройку RAID 1..."

# 1. Устанавливаем необходимые пакеты
apt update
apt install -y mdadm parted gdisk

# 2. Очищаем диски
echo "🧹 Очищаем диски..."
wipefs -a $DISK1
wipefs -a $DISK2

# 3. Создаём разделы на обоих дисках
echo "📀 Создаём разделы..."

# Диск 1
parted $DISK1 --script mklabel gpt
parted $DISK1 --script mkpart primary 1MiB 513MiB    # /boot (512MB)
parted $DISK1 --script mkpart primary 513MiB 50GiB   # / (50GB)
parted $DISK1 --script mkpart primary 50GiB 100%     # /var+/home (остальное)
parted $DISK1 --script set 1 boot on
parted $DISK1 --script set 2 raid on
parted $DISK1 --script set 3 raid on

# Диск 2 (идентично)
parted $DISK2 --script mklabel gpt  
parted $DISK2 --script mkpart primary 1MiB 513MiB
parted $DISK2 --script mkpart primary 513MiB 50GiB
parted $DISK2 --script mkpart primary 50GiB 100%
parted $DISK2 --script set 1 boot on
parted $DISK2 --script set 2 raid on  
parted $DISK2 --script set 3 raid on

# Ждём создания устройств
sleep 3

# 4. Создаём RAID массивы
echo "🔗 Создаём RAID 1 массивы..."

# RAID 1 для /boot (зеркалирование загрузчика)
mdadm --create /dev/md0 --level=1 --raid-devices=2 ${DISK1}p1 ${DISK2}p1

# RAID 1 для / (корневая система)  
mdadm --create /dev/md1 --level=1 --raid-devices=2 ${DISK1}p2 ${DISK2}p2

# RAID 1 для /var (данные контейнеров)
mdadm --create /dev/md2 --level=1 --raid-devices=2 ${DISK1}p3 ${DISK2}p3

# 5. Ждём синхронизации
echo "⏳ Ждём инициализации RAID массивов (это может занять время)..."
sleep 10

# 6. Создаём файловые системы
echo "📁 Создаём файловые системы..."
mkfs.ext4 -L boot /dev/md0
mkfs.ext4 -L root /dev/md1  
mkfs.ext4 -L data /dev/md2

# 7. Сохраняем конфигурацию RAID
mdadm --detail --scan >> /etc/mdadm/mdadm.conf

# 8. Показываем статус
echo ""
echo "✅ RAID 1 настроен успешно!"
echo ""
echo "📊 Статус RAID массивов:"
cat /proc/mdstat
echo ""
echo "📋 Детальная информация:"
mdadm --detail /dev/md0
mdadm --detail /dev/md1  
mdadm --detail /dev/md2

echo ""
echo "🚀 Следующие шаги:"
echo "1. Смонтируй разделы и установи систему"
echo "2. Настрой GRUB на оба диска"
echo "3. Проверь автозапуск RAID при загрузке"

📊 Мониторинг RAID состояния

sudo nano /opt/scripts/raid-monitor.sh
#!/bin/bash
# Мониторинг состояния RAID массивов

echo "💾 RAID 1 Status Monitor - $(date)"
echo "═══════════════════════════════════════════════════════════════"

# 1. Общий статус всех RAID устройств
echo "📊 Overall RAID Status:"
if [ -f /proc/mdstat ]; then
    cat /proc/mdstat
    echo ""
else
    echo "❌ No RAID devices found!"
    exit 1
fi

# 2. Детальный статус каждого массива
for raid_device in $(ls /dev/md* 2>/dev/null); do
    if [ -b "$raid_device" ]; then
        echo "🔍 Detailed status for $raid_device:"
        mdadm --detail $raid_device | grep -E "(State|Active Devices|Failed Devices|Spare Devices|Rebuild Status)"
        echo ""
    fi
done

# 3. Проверка дисков на ошибки
echo "🔧 Physical Disk Health:"
for disk in /dev/nvme0n1 /dev/nvme1n1; do
    if [ -b "$disk" ]; then
        echo "Disk $disk:"

        # SMART статус (если доступен)
        if command -v smartctl >/dev/null 2>&1; then
            health=$(smartctl -H $disk 2>/dev/null | grep "SMART overall-health" | awk '{print $6}')
            temp=$(smartctl -A $disk 2>/dev/null | grep Temperature | awk '{print $10}' | head -1)
            echo "  Health: $health"
            echo "  Temperature: ${temp}°C"
        fi

        # Проверка на bad blocks (примерная)
        error_count=$(dmesg | grep -i "$disk" | grep -i "error" | wc -l)
        echo "  Error count in dmesg: $error_count"
        echo ""
    fi
done

# 4. Использование дискового пространства
echo "💽 Disk Space Usage:"
df -h | grep -E "(Filesystem|/dev/md)"
echo ""

# 5. Проверка на деградированное состояние
echo "⚠️  RAID Health Check:"
degraded_count=$(grep -E "\\[.*_.*\\]" /proc/mdstat | wc -l)
failed_count=$(grep -i "failed" /proc/mdstat | wc -l)

if [ "$degraded_count" -eq 0 ] && [ "$failed_count" -eq 0 ]; then
    echo "✅ All RAID arrays are HEALTHY"
else
    echo "🚨 WARNING: Found $degraded_count degraded and $failed_count failed arrays!"
    echo ""
    echo "🔧 Recovery commands:"
    echo "   Check failed disks: mdadm --detail /dev/mdX"
    echo "   Remove failed disk: mdadm /dev/mdX --remove /dev/sdXY"  
    echo "   Add new disk: mdadm /dev/mdX --add /dev/sdXY"
    echo "   Monitor rebuild: watch cat /proc/mdstat"

    # Отправка alert (если настроен)
    if [ -x /opt/scripts/telegram-alert.sh ]; then
        /opt/scripts/telegram-alert.sh "RAID degradation detected on $(hostname)" "CRITICAL"
    fi
fi

echo ""
echo "═══════════════════════════════════════════════════════════════"
echo "💡 Run 'watch cat /proc/mdstat' for real-time monitoring"

🔧 Скрипт восстановления при отказе диска

sudo nano /opt/scripts/raid-recovery.sh
#!/bin/bash
# Автоматическое восстановление RAID при замене диска

NEW_DISK=$1  # Новый диск, например /dev/nvme1n1

if [ -z "$NEW_DISK" ]; then
    echo "Usage: $0 <new_disk_device>"
    echo "Example: $0 /dev/nvme1n1"
    exit 1
fi

echo "🔧 RAID Recovery Tool"
echo "Новый диск: $NEW_DISK"
echo "══════════════════════════════════════════════════════════════"

# 1. Проверяем текущее состояние RAID
echo "📊 Current RAID status:"
cat /proc/mdstat
echo ""

# 2. Находим деградированные массивы
DEGRADED_ARRAYS=$(grep -l "degraded" /sys/block/md*/md/array_state 2>/dev/null)

if [ -z "$DEGRADED_ARRAYS" ]; then
    echo "✅ No degraded RAID arrays found"
    exit 0
fi

echo "🚨 Found degraded arrays:"
for array in $DEGRADED_ARRAYS; do
    array_name=$(echo $array | cut -d'/' -f4)
    echo "  /dev/$array_name"
done
echo ""

# 3. Подготавливаем новый диск
echo "🛠️  Preparing new disk $NEW_DISK..."

# Получаем схему разделов с работающего диска
WORKING_DISK=$(lsblk -pno NAME | grep nvme | head -1)
echo "Using partition scheme from: $WORKING_DISK"

# Копируем схему разделов
sfdisk -d $WORKING_DISK | sfdisk $NEW_DISK

# Ждём создания разделов
sleep 3

echo "✅ Partitions created on $NEW_DISK"

# 4. Добавляем разделы в RAID массивы
echo ""
echo "🔄 Adding partitions to RAID arrays..."

for i in 1 2 3; do
    raid_device="/dev/md$((i-1))"
    new_partition="${NEW_DISK}p$i"

    if [ -b "$raid_device" ]; then
        echo "Adding $new_partition to $raid_device..."
        mdadm $raid_device --add $new_partition

        if [ $? -eq 0 ]; then
            echo "✅ Successfully added $new_partition to $raid_device"
        else
            echo "❌ Failed to add $new_partition to $raid_device"
        fi
    fi
done

# 5. Показываем прогресс восстановления
echo ""
echo "⏳ Rebuild progress:"
watch -n 5 'cat /proc/mdstat; echo ""; echo "Progress details:"; for md in /dev/md*; do mdadm --detail $md 2>/dev/null | grep -E "(State|Rebuild Status)"; done'

📈 Практические кейсы использования

Кейс 1: Мониторинг производительности RAID

# Создаём скрипт для benchmarking RAID
sudo nano /opt/scripts/raid-performance-test.sh
#!/bin/bash
# Тест производительности RAID 1 на NVMe дисках

echo "🚀 RAID 1 Performance Test on NVMe"
echo "═══════════════════════════════════════════════════════════════"

# Создаём тестовый каталог
TEST_DIR="/tmp/raid-test"
mkdir -p $TEST_DIR

# 1. Sequential Read Test
echo "📖 Sequential Read Test (1GB file):"
dd if=/dev/zero of=$TEST_DIR/testfile bs=1M count=1024 oflag=direct 2>&1 | grep copied

echo "Sequential Write Test (1GB file):"
time sh -c "dd if=$TEST_DIR/testfile of=/dev/null bs=1M iflag=direct && sync"

# 2. Random I/O test (если fio установлен)  
if command -v fio >/dev/null 2>&1; then
    echo ""
    echo "🎯 Random I/O Test:"
    fio --name=random-rw --ioengine=libaio --rw=randrw --bs=4k --numjobs=4 \
        --size=100m --runtime=30 --time_based --directory=$TEST_DIR \
        --group_reporting --iodepth=8
else
    echo ""
    echo "💡 Install 'fio' for detailed I/O testing: apt install fio"
fi

# 3. Контейнер нагрузка тест
echo ""
echo "📦 Container Load Simulation:"
for i in {1..5}; do
    echo "Creating container load simulation $i..."
    dd if=/dev/zero of=$TEST_DIR/container$i bs=10M count=10 oflag=direct &
done
wait

echo "✅ All tests completed"

# Очистка
rm -rf $TEST_DIR

Кейс 2: Автоматический мониторинг в cron

# Добавляем регулярную проверку RAID
sudo crontab -e

# Добавить строки:
# Проверка RAID каждые 4 часа
0 */4 * * * /opt/scripts/raid-monitor.sh >> /var/log/raid-monitor.log

# Еженедельный отчёт о состоянии
0 8 * * 1 /opt/scripts/raid-monitor.sh | /opt/scripts/telegram-alert.sh "Weekly RAID status from $(hostname)" "INFO"

# Немедленный alert при проблемах
*/10 * * * * /opt/scripts/raid-monitor.sh | grep -q "WARNING\|CRITICAL" && /opt/scripts/telegram-alert.sh "RAID issue detected!" "CRITICAL"

Кейс 3: Интеграция RAID с системой бэкапов

# Модифицируем скрипт бэкапа для учёта RAID
sudo nano /opt/scripts/raid-aware-backup.sh
#!/bin/bash
# Бэкап с проверкой состояния RAID

source /opt/scripts/backup-config.env

echo "🔍 Checking RAID status before backup..."

# Проверяем RAID перед бэкапом
RAID_STATUS=$(cat /proc/mdstat | grep -c "\\[UU\\]")
EXPECTED_ARRAYS=3

if [ "$RAID_STATUS" -ne "$EXPECTED_ARRAYS" ]; then
    echo "🚨 RAID arrays degraded! Found $RAID_STATUS healthy arrays, expected $EXPECTED_ARRAYS"

    # Отправляем alert
    /opt/scripts/telegram-alert.sh "RAID degraded during backup time on $(hostname)" "CRITICAL"

    # Продолжаем бэкап но с предупреждением
    echo "⚠️  Continuing backup despite RAID issues..."
fi

# Обычный процесс бэкапа
echo "💾 Starting backup process..."

# Создаём снапшот RAID информации для восстановления
mdadm --detail --scan > /tmp/mdadm.conf.backup

# Добавляем RAID конфигурацию в бэкап
restic backup \
    /var/lib/lxc \
    /etc \
    /opt/scripts \
    /tmp/mdadm.conf.backup \
    --tag raid-aware-backup

echo "✅ RAID-aware backup completed"

🎯 Заключение

Эти три критичных аспекта кардинально влияют на производительность и надёжность сервера:

1. Гибкие лимиты ресурсов

  • Позволяют выжать максимум из 16 потоков Ryzen 7700
  • Защищают главные сайты от «соседей»
  • Автоматически адаптируются к нагрузке

2. Правильная настройка AMD-V + SMT

  • Без SMT: только 8 ядер вместо 16 потоков (-50% мощности!)
  • Без AMD-V: программная виртуализация (-30-60% производительности!)
  • С правильными настройками: полная мощность 16-поточного монстра

3. RAID 1 на NVMe

  • Абсолютная защита от потери данных
  • NVMe скорость с надёжностью зеркалирования
  • Автоматическое восстановление при отказах

🚀 Итоговая мощность сервера:

  • AMD Ryzen 7 7700: 8 ядер × SMT = 16 потоков
  • 2× NVMe Gen4: ~7000 MB/s чтение с отказоустойчивостью
  • 64GB DDR5: поддержка десятков контейнеров
  • Гибкие лимиты: оптимальное распределение нагрузки

С этими настройками твой сервер работает на 100% возможностей! 🔥

 

Комментарии:
    » Полная настройка Dedicated сервера для сайтов: LXC+Безопаность+Бекапы на s3