#!/bin/bash # MY NETWORK UNIVERSAL INSTALLER # Универсальный установщик для любого сервера с автопоиском проекта и полной настройкой set -e echo "==================================================" echo "🚀 MY NETWORK UNIVERSAL INSTALLER" echo "Универсальная установка и восстановление сервера" echo "==================================================" # Определение системы OS_ID=$(lsb_release -i 2>/dev/null | cut -f2 || echo "unknown") OS_VERSION=$(lsb_release -r 2>/dev/null | cut -f2 || echo "unknown") echo "🖥️ Система: $OS_ID $OS_VERSION" echo "👤 Пользователь: $(whoami)" echo "📁 Текущая директория: $(pwd)" # =========================== # ПОИСК ПРОЕКТА # =========================== echo "" echo "=== 1. ПОИСК ПРОЕКТА ===" PROJECT_LOCATIONS=( "/home/myuploader/uploader-bot" "/home/uploader-bot" "/home/myuploader/my-uploader-bot" "/root/uploader-bot" "/root/my-uploader-bot" "/opt/uploader-bot" "/opt/my-uploader-bot" "/var/www/uploader-bot" "/var/www/my-uploader-bot" "$(pwd)" "$(pwd)/../uploader-bot" "$(pwd)/../my-uploader-bot" ) PROJECT_DIR="" COMPOSE_FILE="" echo "🔍 Поиск проекта в стандартных местах..." for dir in "${PROJECT_LOCATIONS[@]}"; do if [ -d "$dir" ]; then for compose in "docker-compose.production.yml" "docker-compose.yml" "docker-compose.new.yml"; do if [ -f "$dir/$compose" ]; then PROJECT_DIR="$dir" COMPOSE_FILE="$compose" echo "✅ Проект найден: $PROJECT_DIR" echo "✅ Compose файл: $COMPOSE_FILE" break 2 fi done fi done if [ -z "$PROJECT_DIR" ]; then echo "🔍 Глобальный поиск проекта..." FOUND_PROJECTS=$(find / -name "docker-compose*.yml" -path "*/uploader-bot*" 2>/dev/null | head -3) if [ -n "$FOUND_PROJECTS" ]; then echo "Найдены проекты:" echo "$FOUND_PROJECTS" FIRST_FOUND=$(echo "$FOUND_PROJECTS" | head -1) PROJECT_DIR=$(dirname "$FIRST_FOUND") COMPOSE_FILE=$(basename "$FIRST_FOUND") echo "✅ Выбран: $PROJECT_DIR" else echo "❌ Проект не найден автоматически!" read -p "📝 Введите полный путь к директории проекта: " PROJECT_DIR if [ ! -d "$PROJECT_DIR" ]; then echo "❌ Директория не существует: $PROJECT_DIR" exit 1 fi # Найти compose файл for compose in "docker-compose.production.yml" "docker-compose.yml" "docker-compose.new.yml"; do if [ -f "$PROJECT_DIR/$compose" ]; then COMPOSE_FILE="$compose" break fi done if [ -z "$COMPOSE_FILE" ]; then echo "❌ Docker compose файл не найден в $PROJECT_DIR" exit 1 fi fi fi cd "$PROJECT_DIR" echo "📁 Работаю в: $(pwd)" # =========================== # УСТАНОВКА ЗАВИСИМОСТЕЙ # =========================== echo "" echo "=== 2. УСТАНОВКА СИСТЕМНЫХ ЗАВИСИМОСТЕЙ ===" # Обновление системы echo "📦 Обновление системы..." sudo apt update && sudo apt upgrade -y # Установка основных пакетов echo "📦 Установка базовых пакетов..." sudo apt install -y curl wget git nginx ufw fail2ban htop nano net-tools # Установка Docker if ! command -v docker &> /dev/null; then echo "🐳 Установка Docker..." curl -fsSL https://get.docker.com -o get-docker.sh sudo sh get-docker.sh sudo usermod -aG docker $USER rm get-docker.sh else echo "✅ Docker уже установлен: $(docker --version)" fi # Установка Docker Compose if ! command -v docker-compose &> /dev/null; then echo "🐳 Установка Docker Compose..." sudo curl -L "https://github.com/docker/compose/releases/latest/download/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose sudo chmod +x /usr/local/bin/docker-compose else echo "✅ Docker Compose уже установлен: $(docker-compose --version)" fi # =========================== # НАСТРОЙКА БЕЗОПАСНОСТИ # =========================== echo "" echo "=== 3. НАСТРОЙКА БЕЗОПАСНОСТИ ===" # Настройка UFW echo "🔥 Настройка файрвола..." sudo ufw --force reset sudo ufw default deny incoming sudo ufw default allow outgoing sudo ufw allow 22/tcp sudo ufw allow 80/tcp sudo ufw allow 443/tcp sudo ufw --force enable # Настройка fail2ban echo "🛡️ Настройка fail2ban..." sudo systemctl enable fail2ban sudo systemctl start fail2ban # =========================== # ОЧИСТКА И ПОДГОТОВКА # =========================== echo "" echo "=== 4. ОЧИСТКА СТАРЫХ КОНТЕЙНЕРОВ ===" echo "🛑 Останавливаю все контейнеры..." docker stop $(docker ps -aq) 2>/dev/null || true echo "🗑️ Удаляю старые контейнеры..." docker rm $(docker ps -aq) 2>/dev/null || true echo "🧹 Очистка системы Docker..." docker system prune -af --volumes # =========================== # ПОДГОТОВКА ФАЙЛОВ # =========================== echo "" echo "=== 5. ПОДГОТОВКА КОНФИГУРАЦИИ ===" # Создание .env файла если нет if [ ! -f ".env" ]; then echo "📝 Создание .env файла..." if [ -f "env.example" ]; then cp env.example .env else cat > .env << 'EOF' # Database Configuration DATABASE_URL=postgresql://myuser:mypassword@postgres:5432/mydb POSTGRES_USER=myuser POSTGRES_PASSWORD=mypassword POSTGRES_DB=mydb # Redis Configuration REDIS_URL=redis://redis:6379 # Application Configuration API_HOST=0.0.0.0 API_PORT=3000 DEBUG=false # Security SECRET_KEY=your-secret-key-here # Telegram Bot (if needed) BOT_TOKEN=your-bot-token WEBHOOK_URL=https://your-domain.com EOF fi echo "✅ .env файл создан" fi # Проверка requirements.txt REQUIREMENTS_FILE="requirements.txt" if [ ! -f "$REQUIREMENTS_FILE" ]; then if [ -f "requirements_new.txt" ]; then REQUIREMENTS_FILE="requirements_new.txt" elif [ -f "requirements.compatible.txt" ]; then REQUIREMENTS_FILE="requirements.compatible.txt" fi fi echo "✅ Используется файл зависимостей: $REQUIREMENTS_FILE" # =========================== # NGINX КОНФИГУРАЦИЯ # =========================== echo "" echo "=== 6. НАСТРОЙКА NGINX ===" cat > /tmp/nginx_universal.conf << 'EOF' server { listen 80; server_name _; # Максимальный размер загружаемых файлов client_max_body_size 100M; # API проксирование location /api/ { proxy_pass http://localhost:3000/api/; 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_connect_timeout 60s; proxy_send_timeout 60s; proxy_read_timeout 60s; proxy_buffering off; } # Health check location /health { proxy_pass http://localhost:3000/api/health; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; } # Альтернативные порты location /api5000/ { proxy_pass http://localhost:5000/; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; } # WebSocket поддержка (если нужна) location /ws/ { proxy_pass http://localhost:3000/ws/; 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; } # Статические файлы (если есть web2-client) location / { try_files $uri $uri/ @app; } # Fallback на приложение location @app { proxy_pass http://localhost:3000/; 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; } # Gzip сжатие gzip on; gzip_vary on; gzip_min_length 1024; gzip_types text/plain text/css text/xml text/javascript application/javascript application/xml+rss application/json; } EOF sudo mv /tmp/nginx_universal.conf /etc/nginx/sites-available/default sudo ln -sf /etc/nginx/sites-available/default /etc/nginx/sites-enabled/default # Удаление дефолтной страницы nginx sudo rm -f /var/www/html/index.nginx-debian.html echo "✅ Nginx конфигурация создана" # =========================== # ЗАПУСК ПРИЛОЖЕНИЯ # =========================== echo "" echo "=== 7. ЗАПУСК ПРИЛОЖЕНИЯ ===" echo "🚀 Запуск Docker Compose..." # Стратегия запуска: сначала базовые сервисы, потом приложение echo "📊 Запуск базы данных и Redis..." if docker-compose -f "$COMPOSE_FILE" up -d postgres redis 2>/dev/null; then echo "✅ База данных запущена" else echo "⚠️ Ошибка запуска БД, пробую альтернативные имена сервисов..." docker-compose -f "$COMPOSE_FILE" up -d db database mysql mariadb redis 2>/dev/null || true fi echo "⏳ Ждем запуска БД (15 секунд)..." sleep 15 echo "🚀 Запуск основного приложения..." if docker-compose -f "$COMPOSE_FILE" --profile main-node up -d 2>/dev/null; then echo "✅ Main-node профиль запущен" elif docker-compose -f "$COMPOSE_FILE" up -d app 2>/dev/null; then echo "✅ Приложение запущено" else echo "⚠️ Пробую запустить все сервисы..." docker-compose -f "$COMPOSE_FILE" up -d fi echo "⏳ Ждем запуска приложения (30 секунд)..." sleep 30 # =========================== # СОЗДАНИЕ SYSTEMD SERVICE # =========================== echo "" echo "=== 8. СОЗДАНИЕ SYSTEMD SERVICE ===" cat > /tmp/mynetwork.service << EOF [Unit] Description=MY Network Service After=docker.service Requires=docker.service [Service] Type=oneshot RemainAfterExit=yes WorkingDirectory=$PROJECT_DIR ExecStart=/usr/bin/docker-compose -f $COMPOSE_FILE up -d ExecStop=/usr/bin/docker-compose -f $COMPOSE_FILE down TimeoutStartSec=300 User=root [Install] WantedBy=multi-user.target EOF sudo mv /tmp/mynetwork.service /etc/systemd/system/ sudo systemctl daemon-reload sudo systemctl enable mynetwork echo "✅ SystemD service создан и активирован" # =========================== # ФИНАЛЬНАЯ ПРОВЕРКА # =========================== echo "" echo "=== 9. ФИНАЛЬНАЯ ПРОВЕРКА ===" # Перезапуск nginx sudo nginx -t && sudo systemctl restart nginx echo "✅ Nginx перезапущен" # Проверка статуса echo "📊 Статус контейнеров:" docker ps --format "table {{.Names}}\t{{.Image}}\t{{.Status}}\t{{.Ports}}" echo "" echo "🔍 Тестирование соединений:" sleep 10 # Тест локальных портов for port in 3000 5000 8080; do if timeout 5 curl -s http://localhost:$port/api/health > /dev/null 2>&1; then echo "✅ localhost:$port/api/health - РАБОТАЕТ" else echo "❌ localhost:$port/api/health - НЕ РАБОТАЕТ" fi done # Тест nginx proxy if timeout 5 curl -s http://localhost/api/health > /dev/null 2>&1; then echo "✅ nginx proxy (/api/health) - РАБОТАЕТ" else echo "❌ nginx proxy (/api/health) - НЕ РАБОТАЕТ" fi if timeout 5 curl -s http://localhost/health > /dev/null 2>&1; then echo "✅ nginx proxy (/health) - РАБОТАЕТ" else echo "❌ nginx proxy (/health) - НЕ РАБОТАЕТ" fi # =========================== # РЕЗУЛЬТАТ # =========================== echo "" echo "==================================================" echo "🎉 УСТАНОВКА ЗАВЕРШЕНА!" echo "==================================================" echo "" echo "📊 ИНФОРМАЦИЯ О СИСТЕМЕ:" echo "Проект: $PROJECT_DIR" echo "Compose: $COMPOSE_FILE" echo "Внешний IP: $(curl -s ifconfig.me 2>/dev/null || echo "неизвестно")" echo "" echo "🌐 ТЕСТИРОВАНИЕ:" EXTERNAL_IP=$(curl -s ifconfig.me 2>/dev/null || echo "YOUR_SERVER_IP") echo "curl -I http://$EXTERNAL_IP/api/health" echo "curl -I http://$EXTERNAL_IP/health" echo "" echo "🔍 ДИАГНОСТИКА (если нужна):" echo "docker ps" echo "docker logs \$(docker ps --format \"{{.Names}}\" | grep app | head -1)" echo "sudo systemctl status mynetwork" echo "sudo journalctl -u nginx -f" echo "" echo "🛠️ УПРАВЛЕНИЕ:" echo "Запуск: sudo systemctl start mynetwork" echo "Остановка: sudo systemctl stop mynetwork" echo "Перезапуск: sudo systemctl restart mynetwork" echo "Статус: sudo systemctl status mynetwork" echo "" echo "✅ MY Network готов к работе!"