Docs/docs/10-security.md
2026-04-01 15:30:40 +05:00

16 KiB
Raw Blame History

10. Безопасность

Обзор

В этом разделе собраны текущие проблемы безопасности инфраструктуры и план их устранения. Документ основан на результатах аудита, проведённого в марте 2026 года.

Последнее обновление: 1 апреля 2026
Применено на хостах: torrent (192.168.1.211), Olimp (Proxmox VE)
В процессе: применение на остальных хостах


Текущее состояние

Область Статус Комментарий
SSH (парольная аутентификация) Отключена на всех хостах
SSH (вход root) Запрещён (PermitRootLogin no) на torrent, применяется на остальных
Пользователь zailon Создан с правами sudo, SSH-ключи настроены
SSH-ключи Управляются централизованно через Ansible
Samba (протокол) Обновлён до SMB2 на media
Samba (шифрование) 🟡 smb encrypt = desired (пока не required из-за совместимости)
UFW / фаервол 🔴 Отключён на всех LXC и ВМ
Хранение паролей в Ansible Все секреты перенесены в vault.yml и зашифрованы
Заголовки безопасности в NPM 🔴 Отсутствуют для большинства прокси
Docker-образы 🟡 Используется тег latest на части сервисов
Обновления систем 🟡 Требуют периодического применения
Мониторинг Node Exporter, Promtail, VictoriaMetrics настроены
Резервное копирование Proxmox Backup Server настроен и протестирован

Решённые проблемы

1. Вход root по SSH — ИСПРАВЛЕНО

  • Описание: На всех хостах разрешён вход под пользователем root через SSH. При компрометации ключа злоумышленник получает полный контроль над системой.
  • Что сделано:
    • Создан пользователь zailon с правами sudo
    • Настроены SSH-ключи из ssh_public_keys
    • В /etc/ssh/sshd_config установлено PermitRootLogin no
    • Применено через Ansible на хосте torrent
  • Проверка:
ssh zailon@192.168.1.211
ssh root@192.168.1.211
grep PermitRootLogin /etc/ssh/sshd_config
  • Статус: Применено на всех хостах

2. Пароли в открытом виде в Ansible — ИСПРАВЛЕНО

  • Описание: В файле group_vars/all.yml присутствовали пароли в открытом виде.
  • Что сделано:
    • Все секреты перенесены в group_vars/vault.yml
    • Файл зашифрован через ansible-vault encrypt vault.yml
    • В all.yml остались только публичные переменные
  • Список зашифрованных переменных:
vault_zailon_password: "..."
vault_grafana_admin_password: "..."
vault_gitlab_root_password: "..."
vault_bitwarden_admin_token: "..."
vault_bitwarden_smtp_password: "..."
vault_mealie_db_password: "..."
vault_flibusta_db_password: "..."
vault_immich_db_password: "..."
vault_mumble_server_password: "..."
vault_mumble_superuser_password: "..."
vault_matrix_postgres_password: "..."
vault_matrix_synapse_secret: "..."
vault_matrix_macaroon_secret: "..."
vault_matrix_form_secret: "..."
vault_matrix_admin_password: "..."
vault_snikket_admin_password: "..."
vault_snikket_invite_token: "..."
vault_smb_olimp_password: "..."
vault_samba_password_qb: "..."
vault_pve_exporter_token: "..."
  • Запуск playbook с vault:
ansible-playbook -i inventories/hosts olimp-deploy.yml --ask-vault-pass
echo "your_vault_password" > ~/.vault_pass
chmod 600 ~/.vault_pass
ansible-playbook -i inventories/hosts olimp-deploy.yml --vault-password-file ~/.vault_pass
  • Статус: Завершено

3. Samba использует SMB1 — ИСПРАВЛЕНО

  • Описание: На хосте media в конфигурации Samba был установлен server min protocol = NT1 (SMB1), что уязвимо к атакам типа EternalBlue.
  • Что сделано:
    • В /etc/samba/smb.conf на хосте media изменено:
[global]
   server min protocol = smb2
   smb encrypt = desired
  • Проверена работа клиентов (Windows, Android, Docker)
  • Статус: Завершено на media games

4. Резервное копирование не было настроено — ИСПРАВЛЕНО

  • Описание: Отсутствовала автоматическая система резервного копирования конфигураций, баз данных и пользовательских данных.
  • Что сделано (апрель 2026):
    • Установлен Proxmox Backup Server (PBS) в LXC контейнере (CT 220)
    • Создано хранилище на ZFS dataset rpool/pbs-backups (187 GB, SSD mirror)
    • Настроено хранилище ssd-backups с дедупликацией и компрессией ZSTD
    • PBS подключён к Proxmox VE как pbs-ssd
    • Настроены бэкапы для критичных систем:
      • LXC контейнеры: 201-211 (gateway, data, media, photo, talk, games, manage, git, ansible, torrent)
      • VM: 205 (Nextcloud), 213 (VPN)
    • Расписание: ежедневно в 02:30 и 22:30
    • Retention политика: Keep Last 7, Keep Daily 7, Keep Weekly 2
    • Режим: Snapshot (без остановки сервисов)
    • Исключены большие диски (16TB RAID6 массив)
    • Восстановление протестировано: CT 201 → CT 216 (успешно)
  • Архитектура:
Proxmox VE Host (Olimp)
├─ ZFS Pool: rpool (2x240GB SSD mirror)
│  └─ Dataset: rpool/pbs-backups (187 GB)
│     └─ Mounted to: /rpool/pbs-backups
│
└─ LXC Container (CT 220) - Proxmox Backup Server
   └─ Mount: /mnt/backups → /rpool/pbs-backups
      └─ Datastore: ssd-backups
  • Команды управления:
zfs list rpool/pbs-backups
zpool list rpool
pct exec 220 -- proxmox-backup-client datastore stats ssd-backups
  • Восстановление:
pct restore <new-vmid> pbs-ssd:backup/ct/<ctid>/<backup-time>
qm restore <new-vmid> pbs-ssd:backup/vm/<vmid>/<backup-time>
  • Статус: Работает, требует мониторинга места
  • Примечание: PBS развёрнут на том же хосте что и Proxmox VE (временное решение до появления отдельного сервера). Рекомендуется настроить репликацию на внешний носитель или облако.

🔴 Критические проблемы (требуют внимания)

1. Отсутствие фаервола на всех LXC

  • Описание: UFW отключён на всех LXC-контейнерах. Сервисы доступны из всей локальной сети без ограничений.
  • Решение: Включить UFW на каждом хосте с минимально необходимыми правилами:
- name: Enable UFW with default deny
  ufw:
    state: enabled
    policy: deny
    direction: incoming
  become: yes

- name: Allow SSH from trusted subnets
  ufw:
    rule: allow
    port: 22
    proto: tcp
    from: "{{ item }}"
  loop:
    - "192.168.1.0/24"
    - "192.168.45.0/24"
  become: yes

- name: Allow Samba from trusted subnets
  ufw:
    rule: allow
    port: "{{ item }}"
    proto: tcp
    from: "192.168.1.0/24"
  loop:
    - 139
    - 445
  become: yes

- name: Allow HTTP/HTTPS for NPM
  ufw:
    rule: allow
    port: "{{ item }}"
    proto: tcp
  loop:
    - 80
    - 443
  become: yes
  • План: Создать роль ufw_setup и применить ко всем хостам
  • Срок: В течение недели

2. Отсутствие заголовков безопасности в NPM

  • Описание: Для публичных прокси не настроены заголовки безопасности: HSTS, X-Content-Type-Options, X-Frame-Options.
  • Решение: Через веб-интерфейс NPM → Proxy Hosts → Edit → Advanced → Custom locations добавить:
add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;
add_header X-Content-Type-Options "nosniff" always;
add_header X-Frame-Options "SAMEORIGIN" always;
add_header X-XSS-Protection "1; mode=block" always;
add_header Referrer-Policy "strict-origin-when-cross-origin" always;
add_header Content-Security-Policy "default-src 'self'" always;
  • Применить ко всем публичным доменам: *.zailon.ru
  • Срок: В течение недели

🟠 Проблемы высокого приоритета

1. Использование Docker-образов с тегом latest

  • Описание: Образы обновляются неконтролируемо, что может привести к несовместимости.
  • Решение: Зафиксировать версии в docker-compose.yml:
services:
  npm:
    image: jc21/nginx-proxy-manager:2.12.3
  • План: Пройтись по всем docker-compose.yml и зафиксировать версии
  • Срок: В течение месяца

2. Необновлённые системы

  • Описание: На хостах накапливаются обновления пакетов.
  • Решение:
    • Регулярно запускать apt update && apt upgrade через Ansible
    • Настроить unattended-upgrades для автоматических обновлений безопасности
- name: Install unattended-upgrades
  apt:
    name: unattended-upgrades
    state: present
  become: yes

- name: Configure unattended-upgrades
  copy:
    content: |
      Unattended-Upgrade::Allowed-Origins {
          "${distro_id}:${distro_codename}";
          "${distro_id}:${distro_codename}-security";
      };
      Unattended-Upgrade::Automatic-Reboot "false";      
    dest: /etc/apt/apt.conf.d/50unattended-upgrades
  become: yes
  • Статус: 🟡 В процессе

🟡 Проблемы среднего приоритета

1. Шифрование Samba: desired вместо required

  • Описание: smb encrypt = desired допускает незашифрованные соединения.
  • Решение: После тестирования всех клиентов в VPN изменить на required:
[global]
   smb encrypt = required
  • Статус: 🟡 Отложено до полной проверки совместимости

2. Отсутствие алертов на логи в Grafana

  • Описание: Нет правил для оповещения при ошибках в логах.
  • Решение: Настроить правила в Grafana → Alerting на основе Loki:
{job="promtail", filename="/var/log/auth.log"} |= "Failed password" | rate() > 5
{job="promtail", container="nginx-proxy-manager"} |= "error"
  • Статус: 🟡 В планах

3. cAdvisor не включён на всех хостах

  • Описание: Метрики Docker-контейнеров собираются не везде.
  • Решение: Раскомментировать роль cadvisor в olimp-deploy.yml при необходимости.
  • Статус: 🟡 По мере необходимости

🟢 Рекомендации по улучшению

Задача Описание Приоритет
Автоматические обновления Настроить unattended-upgrades на всех хостах 🟢
Сегментация сети Выделить VLAN для IoT и гостевой сети 🟢
Мониторинг роутера Сбор SNMP-метрик с TP-Link 🟢
Двухфакторная аутентификация Включить 2FA в Grafana, GitLab, Bitwarden 🟢
Регулярный аудит Запускать Lynis/OpenVAS раз в 3 месяца 🟢
Оффсайт-бэкапы Настроить репликацию PBS в облако (Backblaze B2/Wasabi) 🟢

📋 План действий

Задача Приоритет Срок Статус
Применить настройку SSH (root+zailon) на всех хостах 🔴 1 день 🔄 В процессе
Включить UFW на всех хостах 🔴 1 неделя Ожидает
Добавить заголовки безопасности в NPM 🔴 1 неделя Ожидает
Зафиксировать версии Docker-образов 🟠 1 месяц Ожидает
Настроить unattended-upgrades 🟢 1 месяц Ожидает
Настроить алерты на логи 🟡 По необходимости Ожидает
Настроить репликацию PBS (оффсайт) 🟢 2 месяца Ожидает

🔐 Чек-лист применения изменений

Перед запуском playbook на всех хостах:

chmod 600 /root/.ssh/id_rsa
ansible-vault view vault.yml --ask-vault-pass | grep zailon
ansible-playbook -i inventories/hosts olimp-deploy.yml -l torrent --check --diff --ask-vault-pass
ansible-playbook -i inventories/hosts olimp-deploy.yml -l torrent --ask-vault-pass
ssh zailon@192.168.1.211
ansible-playbook -i inventories/hosts olimp-deploy.yml --ask-vault-pass

⚠️ Важно: Не закрывайте текущую SSH-сессию root, пока не проверите вход под zailon в отдельном окне!


📊 Мониторинг безопасности

zfs list rpool/pbs-backups
zpool list rpool
pct exec 220 -- proxmox-backup-client datastore stats ssd-backups
pct exec 220 -- df -h /mnt/backups

Связанные разделы: