test server
This commit is contained in:
127
README.md
Normal file
127
README.md
Normal file
@@ -0,0 +1,127 @@
|
|||||||
|
# 🚀 AI Server для Ubuntu с RTX 2060
|
||||||
|
|
||||||
|
Автоматическое развертывание Ollama + Open WebUI на Ubuntu Server, оптимизированное для NVIDIA RTX 2060.
|
||||||
|
|
||||||
|
## ⚡ Быстрый старт
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Клонирование репозитория
|
||||||
|
git clone https://github.com/your-repo/api-ai-server.git
|
||||||
|
cd api-ai-server
|
||||||
|
|
||||||
|
# Автоматическая установка (одна команда!)
|
||||||
|
chmod +x install-ubuntu.sh
|
||||||
|
sudo ./install-ubuntu.sh
|
||||||
|
|
||||||
|
# Управление сервером
|
||||||
|
ai-start # Запуск
|
||||||
|
ai-stop # Остановка
|
||||||
|
ai-status # Подробный статус
|
||||||
|
```
|
||||||
|
|
||||||
|
**Веб-интерфейс:** `http://YOUR_SERVER_IP:3000`
|
||||||
|
|
||||||
|
## 🎯 Оптимизировано для RTX 2060
|
||||||
|
|
||||||
|
### Рекомендуемые модели:
|
||||||
|
- **`llama3.2:3b`** (2GB VRAM) - лучший баланс ⭐
|
||||||
|
- **`llama3.2:1b`** (1.3GB VRAM) - максимальная скорость
|
||||||
|
- **`codellama:7b`** (3.8GB VRAM) - для программирования
|
||||||
|
- **`mistral:7b`** (4.1GB VRAM) - высокое качество
|
||||||
|
|
||||||
|
### Управление моделями:
|
||||||
|
```bash
|
||||||
|
ai-models # Интерактивное меню управления
|
||||||
|
ollama pull llama3.2:3b # Установка модели
|
||||||
|
ollama list # Список моделей
|
||||||
|
```
|
||||||
|
|
||||||
|
## 📋 Системные требования
|
||||||
|
|
||||||
|
- **ОС:** Ubuntu 20.04/22.04/24.04 LTS
|
||||||
|
- **GPU:** RTX 2060 (6GB VRAM) или аналогичная NVIDIA
|
||||||
|
- **RAM:** 16GB+ (рекомендуется 32GB)
|
||||||
|
- **Диск:** 50GB свободного места
|
||||||
|
- **Права:** sudo доступ
|
||||||
|
|
||||||
|
## 🔧 Что устанавливается
|
||||||
|
|
||||||
|
- ✅ NVIDIA драйверы + CUDA
|
||||||
|
- ✅ Docker + NVIDIA Container Toolkit
|
||||||
|
- ✅ Ollama (локальный AI движок)
|
||||||
|
- ✅ Open WebUI (ChatGPT-подобный интерфейс)
|
||||||
|
- ✅ Systemd сервисы (автозапуск)
|
||||||
|
- ✅ Мониторинг GPU и системы
|
||||||
|
|
||||||
|
## 🛠️ Управление
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Основные команды
|
||||||
|
ai-start # Запуск AI сервера
|
||||||
|
ai-stop # Остановка AI сервера
|
||||||
|
ai-status # Статус с информацией о GPU/VRAM
|
||||||
|
ai-models # Управление моделями ИИ
|
||||||
|
|
||||||
|
# Системные сервисы
|
||||||
|
sudo systemctl status ollama # Статус Ollama
|
||||||
|
sudo systemctl status ai-server-webui # Статус Web UI
|
||||||
|
|
||||||
|
# Логи
|
||||||
|
journalctl -u ollama -f # Логи Ollama
|
||||||
|
docker compose logs -f # Логи контейнеров
|
||||||
|
```
|
||||||
|
|
||||||
|
## 🔥 Особенности
|
||||||
|
|
||||||
|
- **GPU мониторинг** - отслеживание температуры и VRAM
|
||||||
|
- **Автооптимизация** - настройки под RTX 2060
|
||||||
|
- **Безопасность** - все работает локально
|
||||||
|
- **Простота** - установка одной командой
|
||||||
|
- **Надежность** - systemd сервисы с автозапуском
|
||||||
|
|
||||||
|
## 🐛 Устранение неполадок
|
||||||
|
|
||||||
|
### GPU не найден:
|
||||||
|
```bash
|
||||||
|
nvidia-smi # Проверка драйверов
|
||||||
|
sudo ubuntu-drivers autoinstall # Установка драйверов
|
||||||
|
sudo reboot
|
||||||
|
```
|
||||||
|
|
||||||
|
### Нехватка VRAM:
|
||||||
|
```bash
|
||||||
|
ai-status # Проверка использования VRAM
|
||||||
|
ollama pull llama3.2:1b # Переход на меньшую модель
|
||||||
|
```
|
||||||
|
|
||||||
|
### Перегрев GPU:
|
||||||
|
- Проверьте `ai-status` - если температура > 80°C
|
||||||
|
- Очистите систему охлаждения от пыли
|
||||||
|
- Используйте меньшие модели
|
||||||
|
|
||||||
|
## 📁 Структура проекта
|
||||||
|
|
||||||
|
```
|
||||||
|
api-ai-server/
|
||||||
|
├── install-ubuntu.sh # Основной установщик
|
||||||
|
├── docker-compose.yml # Конфигурация контейнеров
|
||||||
|
├── ollama.service # Systemd сервис Ollama
|
||||||
|
├── ai-server-webui.service # Systemd сервис Web UI
|
||||||
|
├── config/
|
||||||
|
│ └── config.json # Настройки RTX 2060
|
||||||
|
└── scripts/
|
||||||
|
├── start.sh # Запуск
|
||||||
|
├── stop.sh # Остановка
|
||||||
|
├── status.sh # Статус
|
||||||
|
└── models.sh # Управление моделями
|
||||||
|
```
|
||||||
|
|
||||||
|
## 🔗 Полезные ссылки
|
||||||
|
|
||||||
|
- [Ollama](https://ollama.ai/) - Локальный AI движок
|
||||||
|
- [Open WebUI](https://github.com/open-webui/open-webui) - Веб-интерфейс
|
||||||
|
- [NVIDIA Drivers](https://www.nvidia.com/drivers) - Драйверы GPU
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
**Готово к работе за 5 минут! 🎉**
|
||||||
42
SUMMARY.md
Normal file
42
SUMMARY.md
Normal file
@@ -0,0 +1,42 @@
|
|||||||
|
# AI Server - Итоговая структура проекта
|
||||||
|
|
||||||
|
## 📁 Файлы проекта (10 файлов):
|
||||||
|
|
||||||
|
### 🔧 Основные компоненты:
|
||||||
|
- **`install-ubuntu.sh`** - Главный установщик (запускать с sudo)
|
||||||
|
- **`docker-compose.yml`** - Конфигурация Docker контейнеров
|
||||||
|
- **`README.md`** - Документация проекта
|
||||||
|
|
||||||
|
### ⚙️ Системные сервисы:
|
||||||
|
- **`ollama.service`** - Systemd сервис для Ollama
|
||||||
|
- **`ai-server-webui.service`** - Systemd сервис для Web UI
|
||||||
|
|
||||||
|
### 📂 Конфигурация:
|
||||||
|
- **`config/config.json`** - Настройки оптимизированные для RTX 2060
|
||||||
|
|
||||||
|
### 🛠️ Скрипты управления:
|
||||||
|
- **`scripts/start.sh`** - Запуск AI сервера
|
||||||
|
- **`scripts/stop.sh`** - Остановка AI сервера
|
||||||
|
- **`scripts/status.sh`** - Подробный статус системы
|
||||||
|
- **`scripts/models.sh`** - Интерактивное управление моделями
|
||||||
|
|
||||||
|
## 🚀 Использование:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# 1. Установка
|
||||||
|
sudo ./install-ubuntu.sh
|
||||||
|
|
||||||
|
# 2. Управление
|
||||||
|
ai-start # Запуск
|
||||||
|
ai-stop # Остановка
|
||||||
|
ai-status # Статус
|
||||||
|
ai-models # Модели
|
||||||
|
```
|
||||||
|
|
||||||
|
## 🎯 Результат:
|
||||||
|
- Веб-интерфейс: http://YOUR_IP:3000
|
||||||
|
- Локальный ChatGPT с поддержкой RTX 2060
|
||||||
|
- Автоматический запуск при загрузке системы
|
||||||
|
- Полный мониторинг GPU и производительности
|
||||||
|
|
||||||
|
**Проект готов к использованию! 🎉**
|
||||||
20
ai-server-webui.service
Normal file
20
ai-server-webui.service
Normal file
@@ -0,0 +1,20 @@
|
|||||||
|
[Unit]
|
||||||
|
Description=AI Server Web UI
|
||||||
|
Requires=docker.service ollama.service
|
||||||
|
After=docker.service ollama.service
|
||||||
|
StartLimitIntervalSec=0
|
||||||
|
|
||||||
|
[Service]
|
||||||
|
Type=oneshot
|
||||||
|
RemainAfterExit=yes
|
||||||
|
WorkingDirectory=/opt/ai-server
|
||||||
|
ExecStart=/usr/bin/docker compose up -d
|
||||||
|
ExecStop=/usr/bin/docker compose down
|
||||||
|
ExecReload=/usr/bin/docker compose restart
|
||||||
|
TimeoutStartSec=300
|
||||||
|
TimeoutStopSec=120
|
||||||
|
User=root
|
||||||
|
Group=root
|
||||||
|
|
||||||
|
[Install]
|
||||||
|
WantedBy=multi-user.target
|
||||||
181
config/config.json
Normal file
181
config/config.json
Normal file
@@ -0,0 +1,181 @@
|
|||||||
|
{
|
||||||
|
"server": {
|
||||||
|
"name": "AI Server RTX 2060",
|
||||||
|
"version": "1.0",
|
||||||
|
"description": "Локальный AI сервер оптимизированный для RTX 2060",
|
||||||
|
"installation_date": "2024-12-22"
|
||||||
|
},
|
||||||
|
|
||||||
|
"hardware": {
|
||||||
|
"gpu": {
|
||||||
|
"model": "RTX 2060",
|
||||||
|
"vram_gb": 6,
|
||||||
|
"cuda_cores": 1920,
|
||||||
|
"recommended_batch_size": 8,
|
||||||
|
"max_context_length": 4096,
|
||||||
|
"memory_fraction": 0.8
|
||||||
|
},
|
||||||
|
"system": {
|
||||||
|
"min_ram_gb": 16,
|
||||||
|
"recommended_ram_gb": 32,
|
||||||
|
"min_storage_gb": 50
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
|
"ollama": {
|
||||||
|
"host": "0.0.0.0",
|
||||||
|
"port": 11434,
|
||||||
|
"keep_alive": "24h",
|
||||||
|
"num_parallel": 2,
|
||||||
|
"max_loaded_models": 2,
|
||||||
|
"flash_attention": true,
|
||||||
|
"gpu_memory_fraction": 0.8,
|
||||||
|
"environment": {
|
||||||
|
"CUDA_VISIBLE_DEVICES": "0",
|
||||||
|
"OLLAMA_GPU_OVERHEAD": "0.2",
|
||||||
|
"OLLAMA_NUM_PARALLEL": "2",
|
||||||
|
"OLLAMA_MAX_LOADED_MODELS": "2",
|
||||||
|
"OLLAMA_FLASH_ATTENTION": "1"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
|
"webui": {
|
||||||
|
"port": 3000,
|
||||||
|
"default_locale": "ru-RU",
|
||||||
|
"enable_signup": true,
|
||||||
|
"enable_login_form": true,
|
||||||
|
"show_admin_details": false,
|
||||||
|
"enable_community_sharing": false,
|
||||||
|
"default_models": ["llama3.2:3b", "codellama:7b"],
|
||||||
|
"model_filter_enabled": true
|
||||||
|
},
|
||||||
|
|
||||||
|
"models": {
|
||||||
|
"recommended_for_rtx2060": [
|
||||||
|
{
|
||||||
|
"name": "llama3.2:1b",
|
||||||
|
"size_gb": 1.3,
|
||||||
|
"vram_usage_gb": 1.5,
|
||||||
|
"description": "Быстрая модель для повседневных задач",
|
||||||
|
"use_case": "Общие вопросы, быстрые ответы",
|
||||||
|
"performance": "высокая",
|
||||||
|
"quality": "хорошая"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "llama3.2:3b",
|
||||||
|
"size_gb": 2.0,
|
||||||
|
"vram_usage_gb": 2.5,
|
||||||
|
"description": "Оптимальная модель для RTX 2060",
|
||||||
|
"use_case": "Сбалансированное качество и скорость",
|
||||||
|
"performance": "средняя",
|
||||||
|
"quality": "отличная"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "codellama:7b",
|
||||||
|
"size_gb": 3.8,
|
||||||
|
"vram_usage_gb": 4.2,
|
||||||
|
"description": "Специализированная модель для программирования",
|
||||||
|
"use_case": "Написание и анализ кода",
|
||||||
|
"performance": "средняя",
|
||||||
|
"quality": "отличная"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "mistral:7b",
|
||||||
|
"size_gb": 4.1,
|
||||||
|
"vram_usage_gb": 4.5,
|
||||||
|
"description": "Универсальная модель высокого качества",
|
||||||
|
"use_case": "Сложные задачи, анализ текста",
|
||||||
|
"performance": "низкая",
|
||||||
|
"quality": "превосходная"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
|
||||||
|
"not_recommended": [
|
||||||
|
{
|
||||||
|
"name": "llama3:70b",
|
||||||
|
"reason": "Требует более 40GB VRAM, не поместится в RTX 2060"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "codellama:34b",
|
||||||
|
"reason": "Требует более 20GB VRAM"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
|
||||||
|
"performance_tuning": {
|
||||||
|
"rtx_2060_optimizations": {
|
||||||
|
"batch_size": 8,
|
||||||
|
"sequence_length": 2048,
|
||||||
|
"attention_type": "flash_attention",
|
||||||
|
"precision": "fp16",
|
||||||
|
"gradient_checkpointing": true,
|
||||||
|
"memory_efficient_attention": true
|
||||||
|
},
|
||||||
|
|
||||||
|
"system_optimizations": {
|
||||||
|
"docker_memory_limit": "6G",
|
||||||
|
"docker_cpu_limit": "4.0",
|
||||||
|
"swap_usage": "minimal",
|
||||||
|
"gpu_memory_growth": true
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
|
"monitoring": {
|
||||||
|
"gpu_thresholds": {
|
||||||
|
"temperature_warning": 80,
|
||||||
|
"temperature_critical": 90,
|
||||||
|
"memory_warning": 90,
|
||||||
|
"utilization_high": 95
|
||||||
|
},
|
||||||
|
|
||||||
|
"system_thresholds": {
|
||||||
|
"cpu_warning": 80,
|
||||||
|
"memory_warning": 85,
|
||||||
|
"disk_warning": 90
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
|
"networking": {
|
||||||
|
"ports": {
|
||||||
|
"webui": 3000,
|
||||||
|
"ollama_api": 11434,
|
||||||
|
"portainer": 9000,
|
||||||
|
"grafana": 3001,
|
||||||
|
"prometheus": 9090
|
||||||
|
},
|
||||||
|
|
||||||
|
"firewall_rules": [
|
||||||
|
"ufw allow 3000/tcp comment 'AI Server Web UI'",
|
||||||
|
"ufw allow 11434/tcp comment 'Ollama API'",
|
||||||
|
"ufw allow 9000/tcp comment 'Portainer'"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
|
||||||
|
"backup": {
|
||||||
|
"important_paths": [
|
||||||
|
"/opt/ai-server/config",
|
||||||
|
"/opt/ai-server/data",
|
||||||
|
"/var/lib/docker/volumes/api-ai-server_open-webui-data"
|
||||||
|
],
|
||||||
|
|
||||||
|
"backup_schedule": "daily",
|
||||||
|
"retention_days": 7
|
||||||
|
},
|
||||||
|
|
||||||
|
"troubleshooting": {
|
||||||
|
"common_issues": [
|
||||||
|
{
|
||||||
|
"issue": "GPU не обнаружен",
|
||||||
|
"solution": "Проверить nvidia-smi, переустановить драйверы"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"issue": "Нехватка VRAM",
|
||||||
|
"solution": "Использовать меньшую модель или уменьшить batch_size"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"issue": "Медленная работа",
|
||||||
|
"solution": "Проверить температуру GPU, очистить систему"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
||||||
197
docker-compose.yml
Normal file
197
docker-compose.yml
Normal file
@@ -0,0 +1,197 @@
|
|||||||
|
version: '3.8'
|
||||||
|
|
||||||
|
services:
|
||||||
|
# Основной веб-интерфейс с поддержкой GPU
|
||||||
|
open-webui:
|
||||||
|
image: ghcr.io/open-webui/open-webui:main
|
||||||
|
container_name: ai-server-webui
|
||||||
|
ports:
|
||||||
|
- "3000:8080"
|
||||||
|
environment:
|
||||||
|
# Подключение к Ollama
|
||||||
|
- OLLAMA_BASE_URL=http://host.docker.internal:11434
|
||||||
|
|
||||||
|
# Настройки безопасности
|
||||||
|
- WEBUI_SECRET_KEY=ai-server-ubuntu-rtx2060-2024
|
||||||
|
- WEBUI_NAME=AI Server RTX 2060
|
||||||
|
|
||||||
|
# Локализация
|
||||||
|
- DEFAULT_LOCALE=ru-RU
|
||||||
|
- DEFAULT_MODELS=llama3.2:3b,codellama:7b
|
||||||
|
|
||||||
|
# Настройки интерфейса
|
||||||
|
- SHOW_ADMIN_DETAILS=false
|
||||||
|
- ENABLE_SIGNUP=true
|
||||||
|
- ENABLE_LOGIN_FORM=true
|
||||||
|
- ENABLE_COMMUNITY_SHARING=false
|
||||||
|
|
||||||
|
# Настройки чатов
|
||||||
|
- DEFAULT_USER_ROLE=user
|
||||||
|
- ENABLE_MODEL_FILTER=true
|
||||||
|
- MODEL_FILTER_LIST=llama3.2:1b;llama3.2:3b;codellama:7b;mistral:7b
|
||||||
|
|
||||||
|
# Настройки производительности
|
||||||
|
- WEBUI_SESSION_COOKIE_SAME_SITE=lax
|
||||||
|
- WEBUI_SESSION_COOKIE_SECURE=false
|
||||||
|
|
||||||
|
volumes:
|
||||||
|
# Постоянное хранение данных
|
||||||
|
- open-webui-data:/app/backend/data
|
||||||
|
|
||||||
|
# Кастомные настройки
|
||||||
|
- ./config:/app/backend/config:ro
|
||||||
|
- ./logs:/app/backend/logs
|
||||||
|
|
||||||
|
extra_hosts:
|
||||||
|
# Доступ к хосту для подключения к Ollama
|
||||||
|
- "host.docker.internal:host-gateway"
|
||||||
|
|
||||||
|
restart: unless-stopped
|
||||||
|
networks:
|
||||||
|
- ai-network
|
||||||
|
|
||||||
|
# Ограничения ресурсов (оптимизировано для RTX 2060)
|
||||||
|
deploy:
|
||||||
|
resources:
|
||||||
|
limits:
|
||||||
|
cpus: '4.0'
|
||||||
|
memory: 6G
|
||||||
|
reservations:
|
||||||
|
cpus: '1.0'
|
||||||
|
memory: 2G
|
||||||
|
|
||||||
|
# Healthcheck
|
||||||
|
healthcheck:
|
||||||
|
test: ["CMD", "curl", "-f", "http://localhost:8080/health"]
|
||||||
|
interval: 30s
|
||||||
|
timeout: 10s
|
||||||
|
retries: 3
|
||||||
|
start_period: 40s
|
||||||
|
|
||||||
|
# Мониторинг GPU и системы
|
||||||
|
nvidia-exporter:
|
||||||
|
image: mindprince/nvidia_gpu_prometheus_exporter:0.1
|
||||||
|
container_name: ai-server-gpu-exporter
|
||||||
|
ports:
|
||||||
|
- "9445:9445"
|
||||||
|
volumes:
|
||||||
|
- /usr/lib/x86_64-linux-gnu/libnvidia-ml.so.1:/usr/lib/x86_64-linux-gnu/libnvidia-ml.so.1:ro
|
||||||
|
- /usr/bin/nvidia-smi:/usr/bin/nvidia-smi:ro
|
||||||
|
environment:
|
||||||
|
- NVIDIA_VISIBLE_DEVICES=all
|
||||||
|
restart: unless-stopped
|
||||||
|
networks:
|
||||||
|
- ai-network
|
||||||
|
profiles:
|
||||||
|
- monitoring
|
||||||
|
|
||||||
|
# Веб-интерфейс для управления Docker
|
||||||
|
portainer:
|
||||||
|
image: portainer/portainer-ce:latest
|
||||||
|
container_name: ai-server-portainer
|
||||||
|
ports:
|
||||||
|
- "9000:9000"
|
||||||
|
volumes:
|
||||||
|
- /var/run/docker.sock:/var/run/docker.sock
|
||||||
|
- portainer-data:/data
|
||||||
|
restart: unless-stopped
|
||||||
|
networks:
|
||||||
|
- ai-network
|
||||||
|
deploy:
|
||||||
|
resources:
|
||||||
|
limits:
|
||||||
|
cpus: '0.5'
|
||||||
|
memory: 512M
|
||||||
|
profiles:
|
||||||
|
- monitoring
|
||||||
|
|
||||||
|
# Grafana для мониторинга (опционально)
|
||||||
|
grafana:
|
||||||
|
image: grafana/grafana:latest
|
||||||
|
container_name: ai-server-grafana
|
||||||
|
ports:
|
||||||
|
- "3001:3000"
|
||||||
|
environment:
|
||||||
|
- GF_SECURITY_ADMIN_PASSWORD=admin
|
||||||
|
- GF_USERS_ALLOW_SIGN_UP=false
|
||||||
|
volumes:
|
||||||
|
- grafana-data:/var/lib/grafana
|
||||||
|
restart: unless-stopped
|
||||||
|
networks:
|
||||||
|
- ai-network
|
||||||
|
profiles:
|
||||||
|
- monitoring
|
||||||
|
|
||||||
|
# Prometheus для сбора метрик (опционально)
|
||||||
|
prometheus:
|
||||||
|
image: prom/prometheus:latest
|
||||||
|
container_name: ai-server-prometheus
|
||||||
|
ports:
|
||||||
|
- "9090:9090"
|
||||||
|
volumes:
|
||||||
|
- ./config/prometheus.yml:/etc/prometheus/prometheus.yml:ro
|
||||||
|
- prometheus-data:/prometheus
|
||||||
|
command:
|
||||||
|
- '--config.file=/etc/prometheus/prometheus.yml'
|
||||||
|
- '--storage.tsdb.path=/prometheus'
|
||||||
|
- '--web.console.libraries=/etc/prometheus/console_libraries'
|
||||||
|
- '--web.console.templates=/etc/prometheus/consoles'
|
||||||
|
- '--storage.tsdb.retention.time=200h'
|
||||||
|
- '--web.enable-lifecycle'
|
||||||
|
restart: unless-stopped
|
||||||
|
networks:
|
||||||
|
- ai-network
|
||||||
|
profiles:
|
||||||
|
- monitoring
|
||||||
|
|
||||||
|
# Reverse proxy для безопасности (опционально)
|
||||||
|
nginx:
|
||||||
|
image: nginx:alpine
|
||||||
|
container_name: ai-server-nginx
|
||||||
|
ports:
|
||||||
|
- "80:80"
|
||||||
|
- "443:443"
|
||||||
|
volumes:
|
||||||
|
- ./config/nginx.conf:/etc/nginx/nginx.conf:ro
|
||||||
|
- ./ssl:/etc/nginx/ssl:ro
|
||||||
|
depends_on:
|
||||||
|
- open-webui
|
||||||
|
restart: unless-stopped
|
||||||
|
networks:
|
||||||
|
- ai-network
|
||||||
|
profiles:
|
||||||
|
- production
|
||||||
|
|
||||||
|
networks:
|
||||||
|
ai-network:
|
||||||
|
driver: bridge
|
||||||
|
ipam:
|
||||||
|
config:
|
||||||
|
- subnet: 172.20.0.0/16
|
||||||
|
gateway: 172.20.0.1
|
||||||
|
|
||||||
|
volumes:
|
||||||
|
open-webui-data:
|
||||||
|
driver: local
|
||||||
|
driver_opts:
|
||||||
|
type: none
|
||||||
|
o: bind
|
||||||
|
device: /opt/ai-server/data
|
||||||
|
|
||||||
|
portainer-data:
|
||||||
|
driver: local
|
||||||
|
|
||||||
|
grafana-data:
|
||||||
|
driver: local
|
||||||
|
|
||||||
|
prometheus-data:
|
||||||
|
driver: local
|
||||||
|
|
||||||
|
# Конфигурация для production
|
||||||
|
x-production-settings: &production-settings
|
||||||
|
restart: unless-stopped
|
||||||
|
logging:
|
||||||
|
driver: "json-file"
|
||||||
|
options:
|
||||||
|
max-size: "10m"
|
||||||
|
max-file: "3"
|
||||||
592
install-ubuntu.sh
Normal file
592
install-ubuntu.sh
Normal file
@@ -0,0 +1,592 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# ======================================
|
||||||
|
# AI Server Ubuntu Installation Script
|
||||||
|
# ======================================
|
||||||
|
# Автоматическое развертывание Ollama + Open WebUI на Ubuntu
|
||||||
|
# Оптимизировано для RTX 2060 и других NVIDIA GPU
|
||||||
|
# Версия: 1.0
|
||||||
|
|
||||||
|
set -e # Остановка при ошибках
|
||||||
|
|
||||||
|
# Цвета для вывода
|
||||||
|
RED='\033[0;31m'
|
||||||
|
GREEN='\033[0;32m'
|
||||||
|
YELLOW='\033[1;33m'
|
||||||
|
BLUE='\033[0;34m'
|
||||||
|
PURPLE='\033[0;35m'
|
||||||
|
CYAN='\033[0;36m'
|
||||||
|
NC='\033[0m' # No Color
|
||||||
|
|
||||||
|
# Конфигурация
|
||||||
|
DEFAULT_MODEL="llama3.2:3b"
|
||||||
|
WEB_PORT=3000
|
||||||
|
OLLAMA_PORT=11434
|
||||||
|
INSTALL_DIR="/opt/ai-server"
|
||||||
|
SERVICE_USER="aiserver"
|
||||||
|
|
||||||
|
# Функции вывода
|
||||||
|
print_banner() {
|
||||||
|
echo -e "${GREEN}"
|
||||||
|
echo "╔══════════════════════════════════════════════════════════════╗"
|
||||||
|
echo "║ AI SERVER UBUNTU ║"
|
||||||
|
echo "║ Ollama + Open WebUI + RTX 2060 ║"
|
||||||
|
echo "╚══════════════════════════════════════════════════════════════╝"
|
||||||
|
echo -e "${NC}"
|
||||||
|
}
|
||||||
|
|
||||||
|
log_info() {
|
||||||
|
echo -e "${CYAN}[INFO]${NC} $1"
|
||||||
|
}
|
||||||
|
|
||||||
|
log_success() {
|
||||||
|
echo -e "${GREEN}[SUCCESS]${NC} $1"
|
||||||
|
}
|
||||||
|
|
||||||
|
log_warning() {
|
||||||
|
echo -e "${YELLOW}[WARNING]${NC} $1"
|
||||||
|
}
|
||||||
|
|
||||||
|
log_error() {
|
||||||
|
echo -e "${RED}[ERROR]${NC} $1"
|
||||||
|
}
|
||||||
|
|
||||||
|
log_step() {
|
||||||
|
echo -e "${PURPLE}[STEP]${NC} $1"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Проверка прав root
|
||||||
|
check_root() {
|
||||||
|
if [[ $EUID -ne 0 ]]; then
|
||||||
|
log_error "Этот скрипт должен запускаться с правами root"
|
||||||
|
log_info "Используйте: sudo $0"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# Определение дистрибутива
|
||||||
|
detect_distro() {
|
||||||
|
if [[ -f /etc/os-release ]]; then
|
||||||
|
. /etc/os-release
|
||||||
|
DISTRO=$ID
|
||||||
|
VERSION=$VERSION_ID
|
||||||
|
log_info "Обнаружен дистрибутив: $PRETTY_NAME"
|
||||||
|
else
|
||||||
|
log_error "Не удается определить дистрибутив Linux"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# Обновление системы
|
||||||
|
update_system() {
|
||||||
|
log_step "Обновление системы..."
|
||||||
|
apt update && apt upgrade -y
|
||||||
|
apt install -y curl wget git htop neofetch lsb-release gnupg software-properties-common
|
||||||
|
log_success "Система обновлена"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Проверка и установка NVIDIA драйверов
|
||||||
|
install_nvidia_drivers() {
|
||||||
|
log_step "Проверка NVIDIA GPU..."
|
||||||
|
|
||||||
|
if ! command -v nvidia-smi &> /dev/null; then
|
||||||
|
log_warning "NVIDIA драйверы не найдены, устанавливаю..."
|
||||||
|
|
||||||
|
# Определение рекомендуемого драйвера
|
||||||
|
ubuntu-drivers devices
|
||||||
|
|
||||||
|
# Автоматическая установка рекомендуемого драйвера
|
||||||
|
ubuntu-drivers autoinstall
|
||||||
|
|
||||||
|
log_info "NVIDIA драйверы установлены. Требуется перезагрузка!"
|
||||||
|
log_warning "Выполните 'sudo reboot' и запустите скрипт снова"
|
||||||
|
exit 0
|
||||||
|
else
|
||||||
|
log_success "NVIDIA драйверы уже установлены"
|
||||||
|
nvidia-smi
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# Установка Docker
|
||||||
|
install_docker() {
|
||||||
|
log_step "Установка Docker..."
|
||||||
|
|
||||||
|
if ! command -v docker &> /dev/null; then
|
||||||
|
# Удаление старых версий
|
||||||
|
apt remove -y docker.io docker-doc docker-compose podman-docker containerd runc 2>/dev/null || true
|
||||||
|
|
||||||
|
# Установка репозитория Docker
|
||||||
|
curl -fsSL https://download.docker.com/linux/ubuntu/gpg | gpg --dearmor -o /usr/share/keyrings/docker-archive-keyring.gpg
|
||||||
|
echo "deb [arch=$(dpkg --print-architecture) signed-by=/usr/share/keyrings/docker-archive-keyring.gpg] https://download.docker.com/linux/ubuntu $(lsb_release -cs) stable" | tee /etc/apt/sources.list.d/docker.list > /dev/null
|
||||||
|
|
||||||
|
# Установка Docker
|
||||||
|
apt update
|
||||||
|
apt install -y docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin
|
||||||
|
|
||||||
|
# Настройка пользователя
|
||||||
|
usermod -aG docker $SUDO_USER 2>/dev/null || true
|
||||||
|
systemctl enable docker
|
||||||
|
systemctl start docker
|
||||||
|
|
||||||
|
log_success "Docker установлен"
|
||||||
|
else
|
||||||
|
log_success "Docker уже установлен"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Проверка Docker
|
||||||
|
docker --version
|
||||||
|
}
|
||||||
|
|
||||||
|
# Установка NVIDIA Container Toolkit
|
||||||
|
install_nvidia_docker() {
|
||||||
|
log_step "Установка NVIDIA Container Toolkit..."
|
||||||
|
|
||||||
|
if ! docker run --rm --gpus all nvidia/cuda:11.0.3-base-ubuntu20.04 nvidia-smi &>/dev/null; then
|
||||||
|
# Добавление репозитория NVIDIA
|
||||||
|
curl -fsSL https://nvidia.github.io/libnvidia-container/gpgkey | gpg --dearmor -o /usr/share/keyrings/nvidia-container-toolkit-keyring.gpg
|
||||||
|
curl -s -L https://nvidia.github.io/libnvidia-container/stable/deb/nvidia-container-toolkit.list | \
|
||||||
|
sed 's#deb https://#deb [signed-by=/usr/share/keyrings/nvidia-container-toolkit-keyring.gpg] https://#g' | \
|
||||||
|
tee /etc/apt/sources.list.d/nvidia-container-toolkit.list
|
||||||
|
|
||||||
|
apt update
|
||||||
|
apt install -y nvidia-container-toolkit
|
||||||
|
|
||||||
|
# Настройка Docker для NVIDIA
|
||||||
|
nvidia-ctk runtime configure --runtime=docker
|
||||||
|
systemctl restart docker
|
||||||
|
|
||||||
|
log_success "NVIDIA Container Toolkit установлен"
|
||||||
|
else
|
||||||
|
log_success "NVIDIA Container Toolkit уже настроен"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Тест GPU в Docker
|
||||||
|
log_info "Тестирование GPU в Docker..."
|
||||||
|
docker run --rm --gpus all nvidia/cuda:11.0.3-base-ubuntu20.04 nvidia-smi
|
||||||
|
}
|
||||||
|
|
||||||
|
# Установка Ollama
|
||||||
|
install_ollama() {
|
||||||
|
log_step "Установка Ollama..."
|
||||||
|
|
||||||
|
if ! command -v ollama &> /dev/null; then
|
||||||
|
curl -fsSL https://ollama.ai/install.sh | sh
|
||||||
|
log_success "Ollama установлен"
|
||||||
|
else
|
||||||
|
log_success "Ollama уже установлен"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Создание пользователя для сервиса
|
||||||
|
if ! id "$SERVICE_USER" &>/dev/null; then
|
||||||
|
useradd -r -s /bin/false -d /nonexistent $SERVICE_USER
|
||||||
|
usermod -aG docker $SERVICE_USER
|
||||||
|
log_success "Пользователь $SERVICE_USER создан"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# Настройка systemd сервиса для Ollama
|
||||||
|
setup_ollama_service() {
|
||||||
|
log_step "Настройка Ollama сервиса..."
|
||||||
|
|
||||||
|
cat > /etc/systemd/system/ollama.service << EOF
|
||||||
|
[Unit]
|
||||||
|
Description=Ollama Server
|
||||||
|
After=network-online.target
|
||||||
|
|
||||||
|
[Service]
|
||||||
|
ExecStart=/usr/local/bin/ollama serve
|
||||||
|
User=$SERVICE_USER
|
||||||
|
Group=$SERVICE_USER
|
||||||
|
Restart=always
|
||||||
|
RestartSec=3
|
||||||
|
Environment="OLLAMA_HOST=0.0.0.0:$OLLAMA_PORT"
|
||||||
|
Environment="OLLAMA_KEEP_ALIVE=24h"
|
||||||
|
Environment="OLLAMA_NUM_PARALLEL=2"
|
||||||
|
Environment="OLLAMA_MAX_LOADED_MODELS=2"
|
||||||
|
Environment="OLLAMA_FLASH_ATTENTION=1"
|
||||||
|
|
||||||
|
[Install]
|
||||||
|
WantedBy=multi-user.target
|
||||||
|
EOF
|
||||||
|
|
||||||
|
systemctl daemon-reload
|
||||||
|
systemctl enable ollama
|
||||||
|
systemctl start ollama
|
||||||
|
|
||||||
|
log_success "Ollama сервис настроен"
|
||||||
|
|
||||||
|
# Ожидание запуска
|
||||||
|
sleep 10
|
||||||
|
|
||||||
|
# Проверка статуса
|
||||||
|
if systemctl is-active --quiet ollama; then
|
||||||
|
log_success "Ollama сервис запущен"
|
||||||
|
else
|
||||||
|
log_error "Ошибка запуска Ollama сервиса"
|
||||||
|
journalctl -u ollama --no-pager -l
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# Установка моделей
|
||||||
|
install_models() {
|
||||||
|
log_step "Установка модели $DEFAULT_MODEL..."
|
||||||
|
log_info "Это может занять несколько минут в зависимости от скорости интернета..."
|
||||||
|
|
||||||
|
# Установка модели от имени пользователя сервиса
|
||||||
|
sudo -u $SERVICE_USER ollama pull $DEFAULT_MODEL
|
||||||
|
|
||||||
|
log_success "Модель $DEFAULT_MODEL установлена"
|
||||||
|
|
||||||
|
# Список доступных моделей
|
||||||
|
log_info "Доступные модели:"
|
||||||
|
sudo -u $SERVICE_USER ollama list
|
||||||
|
}
|
||||||
|
|
||||||
|
# Создание рабочей директории
|
||||||
|
setup_directories() {
|
||||||
|
log_step "Создание рабочих директорий..."
|
||||||
|
|
||||||
|
mkdir -p $INSTALL_DIR
|
||||||
|
mkdir -p $INSTALL_DIR/config
|
||||||
|
mkdir -p $INSTALL_DIR/logs
|
||||||
|
mkdir -p $INSTALL_DIR/scripts
|
||||||
|
|
||||||
|
# Копирование файлов конфигурации
|
||||||
|
if [[ -f docker-compose.yml ]]; then
|
||||||
|
cp docker-compose.yml $INSTALL_DIR/
|
||||||
|
fi
|
||||||
|
|
||||||
|
chown -R $SERVICE_USER:$SERVICE_USER $INSTALL_DIR
|
||||||
|
|
||||||
|
log_success "Директории созданы: $INSTALL_DIR"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Создание Docker Compose файла
|
||||||
|
create_docker_compose() {
|
||||||
|
log_step "Создание Docker Compose конфигурации..."
|
||||||
|
|
||||||
|
cat > $INSTALL_DIR/docker-compose.yml << EOF
|
||||||
|
version: '3.8'
|
||||||
|
|
||||||
|
services:
|
||||||
|
open-webui:
|
||||||
|
image: ghcr.io/open-webui/open-webui:main
|
||||||
|
container_name: ai-server-webui
|
||||||
|
ports:
|
||||||
|
- "$WEB_PORT:8080"
|
||||||
|
environment:
|
||||||
|
- OLLAMA_BASE_URL=http://host.docker.internal:$OLLAMA_PORT
|
||||||
|
- WEBUI_SECRET_KEY=ai-server-secret-key-ubuntu-2024
|
||||||
|
- WEBUI_NAME=AI Server Ubuntu
|
||||||
|
- DEFAULT_LOCALE=ru-RU
|
||||||
|
- DEFAULT_MODELS=$DEFAULT_MODEL
|
||||||
|
- ENABLE_SIGNUP=true
|
||||||
|
- ENABLE_LOGIN_FORM=true
|
||||||
|
- SHOW_ADMIN_DETAILS=false
|
||||||
|
- ENABLE_COMMUNITY_SHARING=false
|
||||||
|
volumes:
|
||||||
|
- open-webui-data:/app/backend/data
|
||||||
|
- $INSTALL_DIR/config:/app/backend/config:ro
|
||||||
|
extra_hosts:
|
||||||
|
- "host.docker.internal:host-gateway"
|
||||||
|
restart: unless-stopped
|
||||||
|
networks:
|
||||||
|
- ai-network
|
||||||
|
deploy:
|
||||||
|
resources:
|
||||||
|
limits:
|
||||||
|
cpus: '2.0'
|
||||||
|
memory: 4G
|
||||||
|
reservations:
|
||||||
|
cpus: '0.5'
|
||||||
|
memory: 1G
|
||||||
|
|
||||||
|
# Мониторинг (опционально)
|
||||||
|
portainer:
|
||||||
|
image: portainer/portainer-ce:latest
|
||||||
|
container_name: ai-server-portainer
|
||||||
|
ports:
|
||||||
|
- "9000:9000"
|
||||||
|
volumes:
|
||||||
|
- /var/run/docker.sock:/var/run/docker.sock
|
||||||
|
- portainer-data:/data
|
||||||
|
restart: unless-stopped
|
||||||
|
networks:
|
||||||
|
- ai-network
|
||||||
|
profiles:
|
||||||
|
- monitoring
|
||||||
|
|
||||||
|
networks:
|
||||||
|
ai-network:
|
||||||
|
driver: bridge
|
||||||
|
|
||||||
|
volumes:
|
||||||
|
open-webui-data:
|
||||||
|
driver: local
|
||||||
|
portainer-data:
|
||||||
|
driver: local
|
||||||
|
EOF
|
||||||
|
|
||||||
|
log_success "Docker Compose файл создан"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Запуск веб-интерфейса
|
||||||
|
start_webui() {
|
||||||
|
log_step "Запуск веб-интерфейса..."
|
||||||
|
|
||||||
|
cd $INSTALL_DIR
|
||||||
|
docker compose up -d
|
||||||
|
|
||||||
|
# Проверка запуска
|
||||||
|
sleep 15
|
||||||
|
|
||||||
|
if docker compose ps | grep -q "running"; then
|
||||||
|
log_success "Веб-интерфейс запущен"
|
||||||
|
log_info "Доступен по адресу: http://$(hostname -I | awk '{print $1}'):$WEB_PORT"
|
||||||
|
else
|
||||||
|
log_error "Ошибка запуска веб-интерфейса"
|
||||||
|
docker compose logs
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# Создание скриптов управления
|
||||||
|
create_management_scripts() {
|
||||||
|
log_step "Создание скриптов управления..."
|
||||||
|
|
||||||
|
# Скрипт запуска
|
||||||
|
cat > $INSTALL_DIR/scripts/start.sh << 'EOF'
|
||||||
|
#!/bin/bash
|
||||||
|
echo "🚀 Запуск AI Server..."
|
||||||
|
|
||||||
|
cd /opt/ai-server
|
||||||
|
|
||||||
|
# Проверка Ollama
|
||||||
|
if ! systemctl is-active --quiet ollama; then
|
||||||
|
echo "Запуск Ollama..."
|
||||||
|
sudo systemctl start ollama
|
||||||
|
sleep 5
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Запуск веб-интерфейса
|
||||||
|
echo "Запуск веб-интерфейса..."
|
||||||
|
docker compose up -d
|
||||||
|
|
||||||
|
echo "✅ AI Server запущен!"
|
||||||
|
echo "🌐 Веб-интерфейс: http://$(hostname -I | awk '{print $1}'):3000"
|
||||||
|
EOF
|
||||||
|
|
||||||
|
# Скрипт остановки
|
||||||
|
cat > $INSTALL_DIR/scripts/stop.sh << 'EOF'
|
||||||
|
#!/bin/bash
|
||||||
|
echo "⏹️ Остановка AI Server..."
|
||||||
|
|
||||||
|
cd /opt/ai-server
|
||||||
|
|
||||||
|
# Остановка веб-интерфейса
|
||||||
|
docker compose down
|
||||||
|
|
||||||
|
# Остановка Ollama (опционально)
|
||||||
|
# sudo systemctl stop ollama
|
||||||
|
|
||||||
|
echo "✅ AI Server остановлен!"
|
||||||
|
EOF
|
||||||
|
|
||||||
|
# Скрипт статуса
|
||||||
|
cat > $INSTALL_DIR/scripts/status.sh << 'EOF'
|
||||||
|
#!/bin/bash
|
||||||
|
echo "📊 Статус AI Server"
|
||||||
|
echo "==================="
|
||||||
|
|
||||||
|
# Статус Ollama
|
||||||
|
echo "🤖 Ollama:"
|
||||||
|
if systemctl is-active --quiet ollama; then
|
||||||
|
echo " ✅ Запущен"
|
||||||
|
echo " 📍 http://localhost:11434"
|
||||||
|
else
|
||||||
|
echo " ❌ Остановлен"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Статус веб-интерфейса
|
||||||
|
echo ""
|
||||||
|
echo "🌐 Веб-интерфейс:"
|
||||||
|
cd /opt/ai-server
|
||||||
|
if docker compose ps | grep -q "running"; then
|
||||||
|
echo " ✅ Запущен"
|
||||||
|
echo " 📍 http://$(hostname -I | awk '{print $1}'):3000"
|
||||||
|
else
|
||||||
|
echo " ❌ Остановлен"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Модели
|
||||||
|
echo ""
|
||||||
|
echo "📦 Установленные модели:"
|
||||||
|
sudo -u aiserver ollama list 2>/dev/null || echo " ❌ Ollama недоступен"
|
||||||
|
|
||||||
|
# Ресурсы
|
||||||
|
echo ""
|
||||||
|
echo "💻 Использование ресурсов:"
|
||||||
|
echo "GPU:"
|
||||||
|
nvidia-smi --query-gpu=utilization.gpu,memory.used,memory.total --format=csv,noheader,nounits 2>/dev/null || echo " ❌ NVIDIA GPU недоступен"
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo "CPU/RAM:"
|
||||||
|
docker stats --no-stream --format "table {{.Container}}\t{{.CPUPerc}}\t{{.MemUsage}}" 2>/dev/null | grep ai-server || echo " ❌ Контейнеры не запущены"
|
||||||
|
EOF
|
||||||
|
|
||||||
|
# Установка прав
|
||||||
|
chmod +x $INSTALL_DIR/scripts/*.sh
|
||||||
|
|
||||||
|
# Создание символических ссылок
|
||||||
|
ln -sf $INSTALL_DIR/scripts/start.sh /usr/local/bin/ai-start
|
||||||
|
ln -sf $INSTALL_DIR/scripts/stop.sh /usr/local/bin/ai-stop
|
||||||
|
ln -sf $INSTALL_DIR/scripts/status.sh /usr/local/bin/ai-status
|
||||||
|
|
||||||
|
log_success "Скрипты управления созданы"
|
||||||
|
log_info "Доступные команды: ai-start, ai-stop, ai-status"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Настройка файрвола
|
||||||
|
setup_firewall() {
|
||||||
|
log_step "Настройка файрвола..."
|
||||||
|
|
||||||
|
if command -v ufw &> /dev/null; then
|
||||||
|
ufw allow $WEB_PORT/tcp comment "AI Server Web UI"
|
||||||
|
ufw allow $OLLAMA_PORT/tcp comment "Ollama API"
|
||||||
|
ufw --force enable
|
||||||
|
log_success "Файрвол настроен"
|
||||||
|
else
|
||||||
|
log_warning "UFW не найден, настройте файрвол вручную"
|
||||||
|
log_info "Откройте порты: $WEB_PORT (веб-интерфейс), $OLLAMA_PORT (Ollama API)"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# Создание конфигурационного файла
|
||||||
|
create_config() {
|
||||||
|
log_step "Создание конфигурационного файла..."
|
||||||
|
|
||||||
|
cat > $INSTALL_DIR/config/server.conf << EOF
|
||||||
|
# AI Server Configuration
|
||||||
|
# RTX 2060 Optimized Settings
|
||||||
|
|
||||||
|
[ollama]
|
||||||
|
host = 0.0.0.0
|
||||||
|
port = $OLLAMA_PORT
|
||||||
|
keep_alive = 24h
|
||||||
|
num_parallel = 2
|
||||||
|
max_loaded_models = 2
|
||||||
|
flash_attention = true
|
||||||
|
|
||||||
|
[webui]
|
||||||
|
port = $WEB_PORT
|
||||||
|
default_model = $DEFAULT_MODEL
|
||||||
|
locale = ru-RU
|
||||||
|
enable_signup = true
|
||||||
|
|
||||||
|
[gpu]
|
||||||
|
# RTX 2060 имеет 6GB VRAM
|
||||||
|
# Рекомендуемые модели для RTX 2060:
|
||||||
|
# - llama3.2:1b (быстрая, ~1.3GB VRAM)
|
||||||
|
# - llama3.2:3b (оптимальная, ~2.0GB VRAM)
|
||||||
|
# - codellama:7b (для кода, ~3.8GB VRAM)
|
||||||
|
# - mistral:7b (универсальная, ~4.1GB VRAM)
|
||||||
|
|
||||||
|
recommended_models = llama3.2:1b,llama3.2:3b,codellama:7b,mistral:7b
|
||||||
|
max_context_length = 4096
|
||||||
|
gpu_memory_fraction = 0.8
|
||||||
|
|
||||||
|
[performance]
|
||||||
|
# Оптимизация для RTX 2060
|
||||||
|
batch_size = 8
|
||||||
|
num_threads = 4
|
||||||
|
use_mlock = true
|
||||||
|
use_mmap = true
|
||||||
|
EOF
|
||||||
|
|
||||||
|
log_success "Конфигурационный файл создан"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Финальные настройки
|
||||||
|
finalize_installation() {
|
||||||
|
log_step "Финальные настройки..."
|
||||||
|
|
||||||
|
# Создание алиасов
|
||||||
|
cat >> /home/$SUDO_USER/.bashrc << EOF
|
||||||
|
|
||||||
|
# AI Server aliases
|
||||||
|
alias ai-start='sudo /usr/local/bin/ai-start'
|
||||||
|
alias ai-stop='sudo /usr/local/bin/ai-stop'
|
||||||
|
alias ai-status='/usr/local/bin/ai-status'
|
||||||
|
alias ai-logs='cd /opt/ai-server && docker compose logs -f'
|
||||||
|
alias ai-models='sudo -u aiserver ollama list'
|
||||||
|
EOF
|
||||||
|
|
||||||
|
# Информация о системе
|
||||||
|
log_success "Установка завершена!"
|
||||||
|
|
||||||
|
echo -e "${GREEN}"
|
||||||
|
echo "╔══════════════════════════════════════════════════════════════╗"
|
||||||
|
echo "║ УСТАНОВКА ЗАВЕРШЕНА! ║"
|
||||||
|
echo "╚══════════════════════════════════════════════════════════════╝"
|
||||||
|
echo -e "${NC}"
|
||||||
|
|
||||||
|
echo -e "${YELLOW}🌐 Веб-интерфейс:${NC} http://$(hostname -I | awk '{print $1}'):$WEB_PORT"
|
||||||
|
echo -e "${YELLOW}🤖 Ollama API:${NC} http://$(hostname -I | awk '{print $1}'):$OLLAMA_PORT"
|
||||||
|
echo -e "${YELLOW}📁 Рабочая директория:${NC} $INSTALL_DIR"
|
||||||
|
echo ""
|
||||||
|
echo -e "${CYAN}📋 Команды управления:${NC}"
|
||||||
|
echo " • ai-start - запуск AI сервера"
|
||||||
|
echo " • ai-stop - остановка AI сервера"
|
||||||
|
echo " • ai-status - проверка статуса"
|
||||||
|
echo " • ai-logs - просмотр логов"
|
||||||
|
echo " • ai-models - список моделей"
|
||||||
|
echo ""
|
||||||
|
echo -e "${CYAN}📦 Установленные модели:${NC}"
|
||||||
|
sudo -u $SERVICE_USER ollama list 2>/dev/null || echo " Модели будут загружены при первом запуске"
|
||||||
|
echo ""
|
||||||
|
echo -e "${CYAN}🎯 Рекомендуемые модели для RTX 2060:${NC}"
|
||||||
|
echo " • ollama pull llama3.2:1b (быстрая, 1.3GB)"
|
||||||
|
echo " • ollama pull llama3.2:3b (сбалансированная, 2GB)"
|
||||||
|
echo " • ollama pull codellama:7b (для кода, 3.8GB)"
|
||||||
|
echo " • ollama pull mistral:7b (универсальная, 4.1GB)"
|
||||||
|
echo ""
|
||||||
|
echo -e "${GREEN}Перезайдите в терминал для применения алиасов!${NC}"
|
||||||
|
}
|
||||||
|
|
||||||
|
# ======================================
|
||||||
|
# ОСНОВНАЯ ЛОГИКА СКРИПТА
|
||||||
|
# ======================================
|
||||||
|
|
||||||
|
main() {
|
||||||
|
print_banner
|
||||||
|
|
||||||
|
# Проверки
|
||||||
|
check_root
|
||||||
|
detect_distro
|
||||||
|
|
||||||
|
# Установка компонентов
|
||||||
|
update_system
|
||||||
|
install_nvidia_drivers
|
||||||
|
install_docker
|
||||||
|
install_nvidia_docker
|
||||||
|
install_ollama
|
||||||
|
|
||||||
|
# Настройка сервисов
|
||||||
|
setup_directories
|
||||||
|
create_docker_compose
|
||||||
|
create_config
|
||||||
|
setup_ollama_service
|
||||||
|
install_models
|
||||||
|
|
||||||
|
# Запуск сервисов
|
||||||
|
start_webui
|
||||||
|
create_management_scripts
|
||||||
|
setup_firewall
|
||||||
|
|
||||||
|
# Завершение
|
||||||
|
finalize_installation
|
||||||
|
}
|
||||||
|
|
||||||
|
# Запуск основной функции
|
||||||
|
main "$@"
|
||||||
37
ollama.service
Normal file
37
ollama.service
Normal file
@@ -0,0 +1,37 @@
|
|||||||
|
[Unit]
|
||||||
|
Description=Ollama Server
|
||||||
|
After=network-online.target
|
||||||
|
Wants=network-online.target
|
||||||
|
StartLimitIntervalSec=0
|
||||||
|
|
||||||
|
[Service]
|
||||||
|
Type=exec
|
||||||
|
ExecStart=/usr/local/bin/ollama serve
|
||||||
|
User=aiserver
|
||||||
|
Group=aiserver
|
||||||
|
Restart=always
|
||||||
|
RestartSec=3
|
||||||
|
Environment="OLLAMA_HOST=0.0.0.0:11434"
|
||||||
|
Environment="OLLAMA_KEEP_ALIVE=24h"
|
||||||
|
Environment="OLLAMA_NUM_PARALLEL=2"
|
||||||
|
Environment="OLLAMA_MAX_LOADED_MODELS=2"
|
||||||
|
Environment="OLLAMA_FLASH_ATTENTION=1"
|
||||||
|
Environment="CUDA_VISIBLE_DEVICES=0"
|
||||||
|
Environment="OLLAMA_GPU_OVERHEAD=0.2"
|
||||||
|
WorkingDirectory=/opt/ai-server
|
||||||
|
StandardOutput=journal
|
||||||
|
StandardError=journal
|
||||||
|
|
||||||
|
# Security settings
|
||||||
|
NoNewPrivileges=true
|
||||||
|
PrivateTmp=true
|
||||||
|
ProtectSystem=strict
|
||||||
|
ProtectHome=true
|
||||||
|
ReadWritePaths=/opt/ai-server
|
||||||
|
|
||||||
|
# Resource limits for RTX 2060
|
||||||
|
MemoryMax=8G
|
||||||
|
CPUQuota=400%
|
||||||
|
|
||||||
|
[Install]
|
||||||
|
WantedBy=multi-user.target
|
||||||
228
scripts/models.sh
Normal file
228
scripts/models.sh
Normal file
@@ -0,0 +1,228 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# AI Server Model Management Script
|
||||||
|
# Optimized for RTX 2060
|
||||||
|
|
||||||
|
# Colors
|
||||||
|
GREEN='\033[0;32m'
|
||||||
|
RED='\033[0;31m'
|
||||||
|
YELLOW='\033[1;33m'
|
||||||
|
BLUE='\033[0;34m'
|
||||||
|
PURPLE='\033[0;35m'
|
||||||
|
NC='\033[0m'
|
||||||
|
|
||||||
|
show_menu() {
|
||||||
|
echo -e "${BLUE}🤖 AI Server - Управление моделями${NC}"
|
||||||
|
echo "=================================="
|
||||||
|
echo "1. Показать установленные модели"
|
||||||
|
echo "2. Установить рекомендуемые модели для RTX 2060"
|
||||||
|
echo "3. Установить конкретную модель"
|
||||||
|
echo "4. Удалить модель"
|
||||||
|
echo "5. Тестировать модель"
|
||||||
|
echo "6. Показать использование VRAM"
|
||||||
|
echo "7. Рекомендации по моделям"
|
||||||
|
echo "8. Выход"
|
||||||
|
echo ""
|
||||||
|
}
|
||||||
|
|
||||||
|
list_models() {
|
||||||
|
echo -e "${PURPLE}📦 Установленные модели:${NC}"
|
||||||
|
sudo -u aiserver ollama list
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
if command -v nvidia-smi &> /dev/null; then
|
||||||
|
echo -e "${PURPLE}💾 Использование VRAM:${NC}"
|
||||||
|
nvidia-smi --query-gpu=memory.used,memory.total --format=csv,noheader,nounits | \
|
||||||
|
awk -F', ' '{printf "Используется: %d MB / %d MB (%.1f%%)\n", $1, $2, ($1/$2)*100}'
|
||||||
|
fi
|
||||||
|
echo ""
|
||||||
|
}
|
||||||
|
|
||||||
|
install_recommended() {
|
||||||
|
echo -e "${YELLOW}🎯 Установка рекомендуемых моделей для RTX 2060...${NC}"
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
models=("llama3.2:1b" "llama3.2:3b" "codellama:7b")
|
||||||
|
descriptions=("Быстрая модель (1.3GB)" "Оптимальная модель (2GB)" "Модель для кода (3.8GB)")
|
||||||
|
|
||||||
|
for i in "${!models[@]}"; do
|
||||||
|
model="${models[$i]}"
|
||||||
|
desc="${descriptions[$i]}"
|
||||||
|
|
||||||
|
echo -e "${BLUE}Устанавливаю: $model - $desc${NC}"
|
||||||
|
sudo -u aiserver ollama pull "$model"
|
||||||
|
|
||||||
|
if [ $? -eq 0 ]; then
|
||||||
|
echo -e "${GREEN}✅ $model установлена${NC}"
|
||||||
|
else
|
||||||
|
echo -e "${RED}❌ Ошибка установки $model${NC}"
|
||||||
|
fi
|
||||||
|
echo ""
|
||||||
|
done
|
||||||
|
}
|
||||||
|
|
||||||
|
install_custom() {
|
||||||
|
echo -e "${YELLOW}Введите название модели (например: llama3.2:3b):${NC}"
|
||||||
|
read -r model_name
|
||||||
|
|
||||||
|
if [[ -z "$model_name" ]]; then
|
||||||
|
echo -e "${RED}❌ Название модели не может быть пустым${NC}"
|
||||||
|
return
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo -e "${BLUE}Установка модели: $model_name${NC}"
|
||||||
|
echo -e "${YELLOW}Это может занять несколько минут...${NC}"
|
||||||
|
|
||||||
|
sudo -u aiserver ollama pull "$model_name"
|
||||||
|
|
||||||
|
if [ $? -eq 0 ]; then
|
||||||
|
echo -e "${GREEN}✅ Модель $model_name успешно установлена${NC}"
|
||||||
|
else
|
||||||
|
echo -e "${RED}❌ Ошибка установки модели $model_name${NC}"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
remove_model() {
|
||||||
|
echo -e "${PURPLE}📦 Доступные модели для удаления:${NC}"
|
||||||
|
sudo -u aiserver ollama list
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
echo -e "${YELLOW}Введите название модели для удаления:${NC}"
|
||||||
|
read -r model_name
|
||||||
|
|
||||||
|
if [[ -z "$model_name" ]]; then
|
||||||
|
echo -e "${RED}❌ Название модели не может быть пустым${NC}"
|
||||||
|
return
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo -e "${YELLOW}⚠️ Удалить модель $model_name? (y/N):${NC}"
|
||||||
|
read -r confirm
|
||||||
|
|
||||||
|
if [[ $confirm =~ ^[Yy]$ ]]; then
|
||||||
|
sudo -u aiserver ollama rm "$model_name"
|
||||||
|
|
||||||
|
if [ $? -eq 0 ]; then
|
||||||
|
echo -e "${GREEN}✅ Модель $model_name удалена${NC}"
|
||||||
|
else
|
||||||
|
echo -e "${RED}❌ Ошибка удаления модели $model_name${NC}"
|
||||||
|
fi
|
||||||
|
else
|
||||||
|
echo -e "${BLUE}Отменено${NC}"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
test_model() {
|
||||||
|
echo -e "${PURPLE}📦 Доступные модели:${NC}"
|
||||||
|
sudo -u aiserver ollama list
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
echo -e "${YELLOW}Введите название модели для тестирования:${NC}"
|
||||||
|
read -r model_name
|
||||||
|
|
||||||
|
if [[ -z "$model_name" ]]; then
|
||||||
|
echo -e "${RED}❌ Название модели не может быть пустым${NC}"
|
||||||
|
return
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo -e "${BLUE}Тестирование модели: $model_name${NC}"
|
||||||
|
echo -e "${YELLOW}Задаю тестовый вопрос...${NC}"
|
||||||
|
|
||||||
|
sudo -u aiserver ollama run "$model_name" "Привет! Как дела? Ответь кратко."
|
||||||
|
}
|
||||||
|
|
||||||
|
show_vram_usage() {
|
||||||
|
if command -v nvidia-smi &> /dev/null; then
|
||||||
|
echo -e "${PURPLE}🎮 Информация о GPU:${NC}"
|
||||||
|
nvidia-smi --query-gpu=name,memory.used,memory.total,utilization.gpu,temperature.gpu --format=csv,noheader
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
echo -e "${PURPLE}📊 Детальное использование VRAM:${NC}"
|
||||||
|
nvidia-smi
|
||||||
|
else
|
||||||
|
echo -e "${RED}❌ NVIDIA GPU не найден или драйверы не установлены${NC}"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
show_recommendations() {
|
||||||
|
echo -e "${BLUE}🎯 Рекомендации по моделям для RTX 2060 (6GB VRAM):${NC}"
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
echo -e "${GREEN}🥇 ЛУЧШИЙ ВЫБОР:${NC}"
|
||||||
|
echo " • llama3.2:3b (2GB VRAM) - оптимальный баланс скорости и качества"
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
echo -e "${YELLOW}🥈 БЫСТРЫЕ МОДЕЛИ:${NC}"
|
||||||
|
echo " • llama3.2:1b (1.3GB VRAM) - максимальная скорость"
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
echo -e "${PURPLE}🥉 СПЕЦИАЛИЗИРОВАННЫЕ:${NC}"
|
||||||
|
echo " • codellama:7b (3.8GB VRAM) - для программирования"
|
||||||
|
echo " • mistral:7b (4.1GB VRAM) - высокое качество (почти предел)"
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
echo -e "${RED}❌ НЕ РЕКОМЕНДУЕТСЯ:${NC}"
|
||||||
|
echo " • llama3:8b - требует 8GB+ VRAM"
|
||||||
|
echo " • llama3:70b - требует 40GB+ VRAM"
|
||||||
|
echo " • codellama:34b - требует 20GB+ VRAM"
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
echo -e "${CYAN}💡 СОВЕТЫ:${NC}"
|
||||||
|
echo " • Не устанавливайте много больших моделей одновременно"
|
||||||
|
echo " • Мониторьте температуру GPU (ai-status)"
|
||||||
|
echo " • При перегреве используйте меньшие модели"
|
||||||
|
echo " • Для продакшена рекомендуется llama3.2:3b"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Основной цикл
|
||||||
|
main() {
|
||||||
|
while true; do
|
||||||
|
show_menu
|
||||||
|
echo -e "${YELLOW}Выберите опцию (1-8):${NC}"
|
||||||
|
read -r choice
|
||||||
|
|
||||||
|
case $choice in
|
||||||
|
1)
|
||||||
|
list_models
|
||||||
|
;;
|
||||||
|
2)
|
||||||
|
install_recommended
|
||||||
|
;;
|
||||||
|
3)
|
||||||
|
install_custom
|
||||||
|
;;
|
||||||
|
4)
|
||||||
|
remove_model
|
||||||
|
;;
|
||||||
|
5)
|
||||||
|
test_model
|
||||||
|
;;
|
||||||
|
6)
|
||||||
|
show_vram_usage
|
||||||
|
;;
|
||||||
|
7)
|
||||||
|
show_recommendations
|
||||||
|
;;
|
||||||
|
8)
|
||||||
|
echo -e "${GREEN}👋 До свидания!${NC}"
|
||||||
|
exit 0
|
||||||
|
;;
|
||||||
|
*)
|
||||||
|
echo -e "${RED}❌ Неверный выбор. Попробуйте снова.${NC}"
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo -e "${CYAN}Нажмите Enter для продолжения...${NC}"
|
||||||
|
read -r
|
||||||
|
clear
|
||||||
|
done
|
||||||
|
}
|
||||||
|
|
||||||
|
# Проверка прав
|
||||||
|
if [[ ! -d "/opt/ai-server" ]]; then
|
||||||
|
echo -e "${RED}❌ AI Server не установлен. Запустите сначала install-ubuntu.sh${NC}"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
clear
|
||||||
|
main
|
||||||
119
scripts/start.sh
Normal file
119
scripts/start.sh
Normal file
@@ -0,0 +1,119 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# AI Server Start Script for Ubuntu
|
||||||
|
# Optimized for RTX 2060
|
||||||
|
|
||||||
|
set -e
|
||||||
|
|
||||||
|
# Colors
|
||||||
|
GREEN='\033[0;32m'
|
||||||
|
RED='\033[0;31m'
|
||||||
|
YELLOW='\033[1;33m'
|
||||||
|
BLUE='\033[0;34m'
|
||||||
|
NC='\033[0m'
|
||||||
|
|
||||||
|
echo -e "${BLUE}🚀 Запуск AI Server...${NC}"
|
||||||
|
|
||||||
|
# Check if running as root for system services
|
||||||
|
if [[ $EUID -eq 0 ]]; then
|
||||||
|
echo -e "${YELLOW}Запуск системных сервисов...${NC}"
|
||||||
|
|
||||||
|
# Start Ollama service
|
||||||
|
echo "🤖 Запуск Ollama..."
|
||||||
|
systemctl start ollama
|
||||||
|
|
||||||
|
# Wait for Ollama to start
|
||||||
|
sleep 5
|
||||||
|
|
||||||
|
# Check Ollama status
|
||||||
|
if systemctl is-active --quiet ollama; then
|
||||||
|
echo -e "${GREEN}✅ Ollama запущен${NC}"
|
||||||
|
else
|
||||||
|
echo -e "${RED}❌ Ошибка запуска Ollama${NC}"
|
||||||
|
journalctl -u ollama --no-pager -l | tail -10
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Start Web UI service
|
||||||
|
echo "🌐 Запуск веб-интерфейса..."
|
||||||
|
systemctl start ai-server-webui
|
||||||
|
|
||||||
|
# Wait for containers to start
|
||||||
|
sleep 10
|
||||||
|
|
||||||
|
# Check Web UI status
|
||||||
|
if systemctl is-active --quiet ai-server-webui; then
|
||||||
|
echo -e "${GREEN}✅ Веб-интерфейс запущен${NC}"
|
||||||
|
else
|
||||||
|
echo -e "${RED}❌ Ошибка запуска веб-интерфейса${NC}"
|
||||||
|
journalctl -u ai-server-webui --no-pager -l | tail -10
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
else
|
||||||
|
echo -e "${YELLOW}Запуск пользовательских сервисов...${NC}"
|
||||||
|
|
||||||
|
# Change to working directory
|
||||||
|
cd /opt/ai-server
|
||||||
|
|
||||||
|
# Check if Ollama is running
|
||||||
|
echo "🤖 Проверка Ollama..."
|
||||||
|
if ! curl -s http://localhost:11434 >/dev/null 2>&1; then
|
||||||
|
echo -e "${YELLOW}Ollama не отвечает, попытка запуска...${NC}"
|
||||||
|
sudo systemctl start ollama
|
||||||
|
sleep 5
|
||||||
|
|
||||||
|
# Check again
|
||||||
|
if ! curl -s http://localhost:11434 >/dev/null 2>&1; then
|
||||||
|
echo -e "${RED}❌ Не удается запустить Ollama${NC}"
|
||||||
|
echo "Попробуйте: sudo systemctl status ollama"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
echo -e "${GREEN}✅ Ollama доступен${NC}"
|
||||||
|
|
||||||
|
# Start web interface containers
|
||||||
|
echo "🌐 Запуск веб-интерфейса..."
|
||||||
|
docker compose up -d
|
||||||
|
|
||||||
|
# Wait for containers
|
||||||
|
sleep 10
|
||||||
|
|
||||||
|
# Check container status
|
||||||
|
if docker compose ps | grep -q "running"; then
|
||||||
|
echo -e "${GREEN}✅ Веб-интерфейс запущен${NC}"
|
||||||
|
else
|
||||||
|
echo -e "${RED}❌ Ошибка запуска контейнеров${NC}"
|
||||||
|
docker compose logs --tail=20
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Get server IP
|
||||||
|
SERVER_IP=$(hostname -I | awk '{print $1}')
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo -e "${GREEN}🎉 AI Server успешно запущен!${NC}"
|
||||||
|
echo ""
|
||||||
|
echo -e "${BLUE}📍 Доступные сервисы:${NC}"
|
||||||
|
echo " 🌐 Веб-интерфейс: http://${SERVER_IP}:3000"
|
||||||
|
echo " 🤖 Ollama API: http://${SERVER_IP}:11434"
|
||||||
|
echo " 📊 Portainer: http://${SERVER_IP}:9000 (если включен)"
|
||||||
|
echo ""
|
||||||
|
echo -e "${BLUE}💡 GPU информация:${NC}"
|
||||||
|
if command -v nvidia-smi &> /dev/null; then
|
||||||
|
nvidia-smi --query-gpu=name,memory.used,memory.total,utilization.gpu --format=csv,noheader,nounits 2>/dev/null | \
|
||||||
|
awk -F', ' '{printf " GPU: %s\n VRAM: %d/%d MB (%.1f%%)\n Загрузка: %d%%\n", $1, $2, $3, ($2/$3)*100, $4}'
|
||||||
|
else
|
||||||
|
echo " ❌ NVIDIA GPU недоступен"
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo -e "${YELLOW}📋 Полезные команды:${NC}"
|
||||||
|
echo " ai-status - проверка статуса"
|
||||||
|
echo " ai-stop - остановка сервера"
|
||||||
|
echo " ai-logs - просмотр логов"
|
||||||
|
echo " ai-models - список моделей"
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo -e "${GREEN}Готово к работе! 🎯${NC}"
|
||||||
202
scripts/status.sh
Normal file
202
scripts/status.sh
Normal file
@@ -0,0 +1,202 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# AI Server Status Script for Ubuntu
|
||||||
|
# RTX 2060 Optimized
|
||||||
|
|
||||||
|
# Colors
|
||||||
|
GREEN='\033[0;32m'
|
||||||
|
RED='\033[0;31m'
|
||||||
|
YELLOW='\033[1;33m'
|
||||||
|
BLUE='\033[0;34m'
|
||||||
|
PURPLE='\033[0;35m'
|
||||||
|
CYAN='\033[0;36m'
|
||||||
|
NC='\033[0m'
|
||||||
|
|
||||||
|
echo -e "${BLUE}📊 AI Server Status Report${NC}"
|
||||||
|
echo "========================================"
|
||||||
|
|
||||||
|
# System Information
|
||||||
|
echo -e "${PURPLE}🖥️ Система:${NC}"
|
||||||
|
echo " Хост: $(hostname)"
|
||||||
|
echo " IP: $(hostname -I | awk '{print $1}')"
|
||||||
|
echo " Время работы: $(uptime -p)"
|
||||||
|
echo " Дата: $(date '+%Y-%m-%d %H:%M:%S')"
|
||||||
|
|
||||||
|
# GPU Status
|
||||||
|
echo ""
|
||||||
|
echo -e "${PURPLE}🎮 GPU (RTX 2060):${NC}"
|
||||||
|
if command -v nvidia-smi &> /dev/null; then
|
||||||
|
# GPU basic info
|
||||||
|
GPU_INFO=$(nvidia-smi --query-gpu=name,driver_version,memory.used,memory.total,utilization.gpu,temperature.gpu --format=csv,noheader,nounits)
|
||||||
|
if [[ -n "$GPU_INFO" ]]; then
|
||||||
|
echo "$GPU_INFO" | while IFS=', ' read -r name driver mem_used mem_total util temp; do
|
||||||
|
echo " ✅ Модель: $name"
|
||||||
|
echo " 📦 Драйвер: $driver"
|
||||||
|
echo " 🧠 VRAM: ${mem_used}MB / ${mem_total}MB ($(( (mem_used * 100) / mem_total ))%)"
|
||||||
|
echo " ⚡ Загрузка: ${util}%"
|
||||||
|
echo " 🌡️ Температура: ${temp}°C"
|
||||||
|
|
||||||
|
# Warning thresholds
|
||||||
|
if (( temp > 80 )); then
|
||||||
|
echo -e " ${RED}⚠️ ВНИМАНИЕ: Высокая температура GPU!${NC}"
|
||||||
|
fi
|
||||||
|
if (( util > 90 )); then
|
||||||
|
echo -e " ${YELLOW}⚠️ GPU сильно загружен${NC}"
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
else
|
||||||
|
echo -e " ${RED}❌ Не удается получить информацию о GPU${NC}"
|
||||||
|
fi
|
||||||
|
else
|
||||||
|
echo -e " ${RED}❌ NVIDIA драйверы не установлены${NC}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Docker Status
|
||||||
|
echo ""
|
||||||
|
echo -e "${PURPLE}🐳 Docker:${NC}"
|
||||||
|
if command -v docker &> /dev/null; then
|
||||||
|
if docker info >/dev/null 2>&1; then
|
||||||
|
echo -e " ✅ Docker запущен"
|
||||||
|
echo " 📦 Версия: $(docker --version | cut -d' ' -f3 | tr -d ',')"
|
||||||
|
|
||||||
|
# Check NVIDIA Docker support
|
||||||
|
if docker run --rm --gpus all nvidia/cuda:11.0.3-base-ubuntu20.04 nvidia-smi >/dev/null 2>&1; then
|
||||||
|
echo -e " ✅ NVIDIA GPU поддержка включена"
|
||||||
|
else
|
||||||
|
echo -e " ${YELLOW}⚠️ NVIDIA GPU поддержка не настроена${NC}"
|
||||||
|
fi
|
||||||
|
else
|
||||||
|
echo -e " ${RED}❌ Docker не запущен${NC}"
|
||||||
|
fi
|
||||||
|
else
|
||||||
|
echo -e " ${RED}❌ Docker не установлен${NC}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Ollama Status
|
||||||
|
echo ""
|
||||||
|
echo -e "${PURPLE}🤖 Ollama:${NC}"
|
||||||
|
if systemctl is-active --quiet ollama; then
|
||||||
|
echo -e " ✅ Сервис запущен"
|
||||||
|
echo " 📍 Адрес: http://localhost:11434"
|
||||||
|
|
||||||
|
# Test connection
|
||||||
|
if curl -s http://localhost:11434 >/dev/null 2>&1; then
|
||||||
|
echo -e " ✅ API доступен"
|
||||||
|
|
||||||
|
# List models
|
||||||
|
echo " 📦 Установленные модели:"
|
||||||
|
sudo -u aiserver ollama list 2>/dev/null | tail -n +2 | while read -r line; do
|
||||||
|
if [[ -n "$line" ]]; then
|
||||||
|
model_name=$(echo "$line" | awk '{print $1}')
|
||||||
|
model_size=$(echo "$line" | awk '{print $2}')
|
||||||
|
echo " • $model_name ($model_size)"
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
|
||||||
|
else
|
||||||
|
echo -e " ${RED}❌ API недоступен${NC}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Service logs (last 3 lines)
|
||||||
|
echo " 📋 Последние логи:"
|
||||||
|
sudo journalctl -u ollama --no-pager -n 3 | tail -n +4 | sed 's/^/ /'
|
||||||
|
|
||||||
|
else
|
||||||
|
echo -e " ${RED}❌ Сервис остановлен${NC}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Web UI Status
|
||||||
|
echo ""
|
||||||
|
echo -e "${PURPLE}🌐 Веб-интерфейс:${NC}"
|
||||||
|
cd /opt/ai-server 2>/dev/null || {
|
||||||
|
echo -e " ${RED}❌ Рабочая директория не найдена${NC}"
|
||||||
|
exit 1
|
||||||
|
}
|
||||||
|
|
||||||
|
if docker compose ps 2>/dev/null | grep -q "running"; then
|
||||||
|
echo -e " ✅ Контейнеры запущены"
|
||||||
|
echo " 📍 Адрес: http://$(hostname -I | awk '{print $1}'):3000"
|
||||||
|
|
||||||
|
# Container details
|
||||||
|
echo " 📦 Статус контейнеров:"
|
||||||
|
docker compose ps --format "table {{.Service}}\t{{.Status}}\t{{.Ports}}" 2>/dev/null | tail -n +2 | while read -r line; do
|
||||||
|
if [[ -n "$line" ]]; then
|
||||||
|
echo " $line"
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
|
||||||
|
# Resource usage
|
||||||
|
echo " 💻 Использование ресурсов:"
|
||||||
|
docker stats --no-stream --format "table {{.Container}}\t{{.CPUPerc}}\t{{.MemUsage}}" 2>/dev/null | \
|
||||||
|
grep "ai-server" | while read -r line; do
|
||||||
|
echo " $line"
|
||||||
|
done
|
||||||
|
|
||||||
|
else
|
||||||
|
echo -e " ${RED}❌ Контейнеры не запущены${NC}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# System Resources
|
||||||
|
echo ""
|
||||||
|
echo -e "${PURPLE}💾 Системные ресурсы:${NC}"
|
||||||
|
|
||||||
|
# CPU
|
||||||
|
CPU_USAGE=$(top -bn1 | grep "Cpu(s)" | awk '{print $2}' | cut -d'%' -f1)
|
||||||
|
echo " 🧮 CPU: ${CPU_USAGE}%"
|
||||||
|
|
||||||
|
# Memory
|
||||||
|
MEM_INFO=$(free -h | grep "Mem:")
|
||||||
|
MEM_TOTAL=$(echo $MEM_INFO | awk '{print $2}')
|
||||||
|
MEM_USED=$(echo $MEM_INFO | awk '{print $3}')
|
||||||
|
MEM_PERCENT=$(free | grep Mem | awk '{printf("%.1f", ($3/$2) * 100.0)}')
|
||||||
|
echo " 🧠 RAM: ${MEM_USED}/${MEM_TOTAL} (${MEM_PERCENT}%)"
|
||||||
|
|
||||||
|
# Disk
|
||||||
|
DISK_INFO=$(df -h /opt/ai-server 2>/dev/null | tail -1)
|
||||||
|
if [[ -n "$DISK_INFO" ]]; then
|
||||||
|
DISK_USED=$(echo $DISK_INFO | awk '{print $3}')
|
||||||
|
DISK_TOTAL=$(echo $DISK_INFO | awk '{print $2}')
|
||||||
|
DISK_PERCENT=$(echo $DISK_INFO | awk '{print $5}')
|
||||||
|
echo " 💽 Диск: ${DISK_USED}/${DISK_TOTAL} (${DISK_PERCENT})"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Network
|
||||||
|
echo " 🌐 Сетевые порты:"
|
||||||
|
netstat -tln 2>/dev/null | grep -E ":3000|:11434|:9000" | while read -r line; do
|
||||||
|
port=$(echo $line | awk '{print $4}' | cut -d':' -f2)
|
||||||
|
case $port in
|
||||||
|
3000) echo " ✅ 3000 (Web UI) - активен" ;;
|
||||||
|
11434) echo " ✅ 11434 (Ollama) - активен" ;;
|
||||||
|
9000) echo " ✅ 9000 (Portainer) - активен" ;;
|
||||||
|
esac
|
||||||
|
done
|
||||||
|
|
||||||
|
# Recommendations
|
||||||
|
echo ""
|
||||||
|
echo -e "${CYAN}💡 Рекомендации для RTX 2060:${NC}"
|
||||||
|
|
||||||
|
# Check GPU memory usage
|
||||||
|
if command -v nvidia-smi &> /dev/null; then
|
||||||
|
GPU_MEM_USED=$(nvidia-smi --query-gpu=memory.used --format=csv,noheader,nounits)
|
||||||
|
if (( GPU_MEM_USED > 5000 )); then
|
||||||
|
echo -e " ${YELLOW}⚠️ VRAM почти заполнена. Рассмотрите использование меньших моделей${NC}"
|
||||||
|
echo " • llama3.2:1b (1.3GB) - быстрая модель"
|
||||||
|
echo " • llama3.2:3b (2GB) - оптимальная для RTX 2060"
|
||||||
|
elif (( GPU_MEM_USED < 1000 )); then
|
||||||
|
echo -e " ${GREEN}✅ VRAM свободна. Можно использовать более крупные модели${NC}"
|
||||||
|
echo " • codellama:7b (3.8GB) - для программирования"
|
||||||
|
echo " • mistral:7b (4.1GB) - универсальная модель"
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo "========================================"
|
||||||
|
echo -e "${GREEN}📋 Команды управления:${NC}"
|
||||||
|
echo " ai-start - запуск сервера"
|
||||||
|
echo " ai-stop - остановка сервера"
|
||||||
|
echo " ai-logs - просмотр логов"
|
||||||
|
echo " ai-models - управление моделями"
|
||||||
|
|
||||||
|
# Show last update time
|
||||||
|
echo ""
|
||||||
|
echo -e "${CYAN}Обновлено: $(date '+%H:%M:%S')${NC}"
|
||||||
98
scripts/stop.sh
Normal file
98
scripts/stop.sh
Normal file
@@ -0,0 +1,98 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# AI Server Stop Script for Ubuntu
|
||||||
|
|
||||||
|
set -e
|
||||||
|
|
||||||
|
# Colors
|
||||||
|
GREEN='\033[0;32m'
|
||||||
|
RED='\033[0;31m'
|
||||||
|
YELLOW='\033[1;33m'
|
||||||
|
BLUE='\033[0;34m'
|
||||||
|
NC='\033[0m'
|
||||||
|
|
||||||
|
echo -e "${BLUE}⏹️ Остановка AI Server...${NC}"
|
||||||
|
|
||||||
|
# Check if running as root for system services
|
||||||
|
if [[ $EUID -eq 0 ]]; then
|
||||||
|
echo -e "${YELLOW}Остановка системных сервисов...${NC}"
|
||||||
|
|
||||||
|
# Stop Web UI service
|
||||||
|
echo "🌐 Остановка веб-интерфейса..."
|
||||||
|
if systemctl is-active --quiet ai-server-webui; then
|
||||||
|
systemctl stop ai-server-webui
|
||||||
|
echo -e "${GREEN}✅ Веб-интерфейс остановлен${NC}"
|
||||||
|
else
|
||||||
|
echo -e "${YELLOW}⚠️ Веб-интерфейс не был запущен${NC}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Stop Ollama service (optional)
|
||||||
|
read -p "Остановить Ollama сервер? (y/N): " -n 1 -r
|
||||||
|
echo
|
||||||
|
if [[ $REPLY =~ ^[Yy]$ ]]; then
|
||||||
|
echo "🤖 Остановка Ollama..."
|
||||||
|
systemctl stop ollama
|
||||||
|
echo -e "${GREEN}✅ Ollama остановлен${NC}"
|
||||||
|
else
|
||||||
|
echo -e "${YELLOW}⚠️ Ollama оставлен запущенным${NC}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
else
|
||||||
|
echo -e "${YELLOW}Остановка пользовательских сервисов...${NC}"
|
||||||
|
|
||||||
|
# Change to working directory
|
||||||
|
cd /opt/ai-server 2>/dev/null || {
|
||||||
|
echo -e "${RED}❌ Не найдена рабочая директория /opt/ai-server${NC}"
|
||||||
|
exit 1
|
||||||
|
}
|
||||||
|
|
||||||
|
# Stop web interface containers
|
||||||
|
echo "🌐 Остановка веб-интерфейса..."
|
||||||
|
if docker compose ps | grep -q "running"; then
|
||||||
|
docker compose down
|
||||||
|
echo -e "${GREEN}✅ Контейнеры остановлены${NC}"
|
||||||
|
else
|
||||||
|
echo -e "${YELLOW}⚠️ Контейнеры не были запущены${NC}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Optional: Stop Ollama if requested
|
||||||
|
if systemctl is-active --quiet ollama; then
|
||||||
|
read -p "Остановить Ollama сервер? (y/N): " -n 1 -r
|
||||||
|
echo
|
||||||
|
if [[ $REPLY =~ ^[Yy]$ ]]; then
|
||||||
|
echo "🤖 Остановка Ollama..."
|
||||||
|
sudo systemctl stop ollama
|
||||||
|
echo -e "${GREEN}✅ Ollama остановлен${NC}"
|
||||||
|
else
|
||||||
|
echo -e "${YELLOW}⚠️ Ollama оставлен запущенным${NC}"
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Clean up unused Docker resources
|
||||||
|
echo "🧹 Очистка неиспользуемых ресурсов..."
|
||||||
|
docker system prune -f >/dev/null 2>&1 || true
|
||||||
|
|
||||||
|
# Show final status
|
||||||
|
echo ""
|
||||||
|
echo -e "${GREEN}✅ AI Server остановлен!${NC}"
|
||||||
|
echo ""
|
||||||
|
echo -e "${BLUE}📊 Текущий статус:${NC}"
|
||||||
|
|
||||||
|
# Check Ollama
|
||||||
|
if systemctl is-active --quiet ollama; then
|
||||||
|
echo " 🤖 Ollama: запущен"
|
||||||
|
else
|
||||||
|
echo " 🤖 Ollama: остановлен"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Check containers
|
||||||
|
cd /opt/ai-server 2>/dev/null || exit 0
|
||||||
|
if docker compose ps 2>/dev/null | grep -q "running"; then
|
||||||
|
echo " 🌐 Веб-интерфейс: запущен"
|
||||||
|
else
|
||||||
|
echo " 🌐 Веб-интерфейс: остановлен"
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo -e "${YELLOW}💡 Для запуска используйте: ai-start${NC}"
|
||||||
Reference in New Issue
Block a user