ServerAID
Найти гайд, команду, тег… ⌘ K
Серверный стек

Установка Nextcloud на Ubuntu Server: nginx, PostgreSQL и HTTPS

Поднимаем своё облако на Ubuntu Server 24.04: nginx с PHP-FPM, база в PostgreSQL, сертификат Let's Encrypt и права на каталог данных. Разбираем полный конфиг nginx под Nextcloud, обязательный cron для фоновых задач и настройки, без которых установка ругается на предупреждения безопасности.

Nextcloud — собственное файловое облако с календарём, контактами и совместной работой над документами. Ставится на обычный LAMP/LEMP-стек, но между «скачал архив» и «работает без предупреждений» есть с десяток шагов, которые обычно и вызывают вопросы. Проходим их по порядку на Ubuntu Server 24.04 LTS.

Что понадобится

  • Ubuntu Server 24.04 LTS с root-доступом или sudo;
  • домен, указывающий на сервер (для HTTPS);
  • минимум 2 ГБ ОЗУ, разумно 4 ГБ;
  • место под файлы пользователей — с запасом.

Стек: nginx как веб-сервер, PHP-FPM как обработчик, PostgreSQL как база. Можно взять MariaDB — Nextcloud работает с обеими, но PostgreSQL стабильнее держит нагрузку при большом числе файлов.

Базовые статьи по компонентам пригодятся, если что-то пойдёт не так: установка nginx и установка PostgreSQL.

Ставим стек

sudo apt update
sudo apt install -y nginx postgresql \
  php-fpm php-pgsql php-gd php-curl php-mbstring php-intl php-xml php-zip \
  php-bcmath php-gmp php-imagick php-apcu \
  unzip

Набор PHP-расширений здесь не случайный: без gd не будет превью, без intl — локализации, без bcmath и gmp не заработает двухфакторная аутентификация, без imagick — генерация миниатюр. Nextcloud проверяет их наличие и жалуется на каждое отсутствующее.

Уточняем версию PHP — от неё зависят пути к конфигам и сокету:

php -v
ls /run/php/

В Ubuntu 24.04 это PHP 8.3, дальше в примерах используется он.

Создаём базу

sudo -u postgres psql
CREATE ROLE nextcloud WITH LOGIN PASSWORD 'СильныйПароль';
CREATE DATABASE nextcloud OWNER nextcloud TEMPLATE template0 ENCODING 'UTF8';
\q

TEMPLATE template0 с явной кодировкой избавляет от проблем с сортировкой на серверах, где локаль по умолчанию отличается от UTF-8.

Проверяем, что роль подключается:

psql -h 127.0.0.1 -U nextcloud -d nextcloud -c "SELECT 1;"

Если ответ Peer authentication failed, добавьте в pg_hba.conf правило для подключения по TCP с методом scram-sha-256 — разбор в статье про PostgreSQL.

Разворачиваем Nextcloud

cd /tmp
curl -fsSL https://download.nextcloud.com/server/releases/latest.zip -o nextcloud.zip
curl -fsSL https://download.nextcloud.com/server/releases/latest.zip.sha256 -o nextcloud.zip.sha256
sha256sum -c nextcloud.zip.sha256

Проверка контрольной суммы обязательна — вы разворачиваете код, который получит доступ ко всем вашим файлам.

sudo unzip -q nextcloud.zip -d /var/www/
sudo chown -R www-data:www-data /var/www/nextcloud

Каталог данных лучше вынести за пределы веб-корня: тогда файлы пользователей физически недоступны через веб-сервер, даже при ошибке в конфиге nginx.

sudo mkdir -p /var/nextcloud-data
sudo chown -R www-data:www-data /var/nextcloud-data
sudo chmod 750 /var/nextcloud-data

Про владельцев и права — в статьях про chown и chmod.

Настраиваем PHP-FPM

Значения по умолчанию для Nextcloud малы. Правим /etc/php/8.3/fpm/php.ini:

memory_limit = 512M
upload_max_filesize = 10G
post_max_size = 10G
max_execution_time = 3600
max_input_time = 3600
output_buffering = Off

upload_max_filesize и post_max_size определяют максимальный размер загружаемого файла — ставьте по своим потребностям. output_buffering = Off требуется самим Nextcloud, иначе он выдаст предупреждение.

Включаем кэш опкодов и APCu там же или в отдельном файле /etc/php/8.3/fpm/conf.d/99-nextcloud.ini:

opcache.enable=1
opcache.interned_strings_buffer=16
opcache.max_accelerated_files=10000
opcache.memory_consumption=128
opcache.save_comments=1
opcache.revalidate_freq=60
apc.enable_cli=1

interned_strings_buffer меньше 16 — самая частая причина предупреждения в панели администратора. Применяем:

sudo systemctl restart php8.3-fpm

Конфиг nginx

Создаём /etc/nginx/sites-available/nextcloud:

upstream php-handler {
    server unix:/run/php/php8.3-fpm.sock;
}

server {
    listen 80;
    listen [::]:80;
    server_name cloud.example.com;
    return 301 https://$server_name$request_uri;
}

server {
    listen 443 ssl http2;
    listen [::]:443 ssl http2;
    server_name cloud.example.com;

    root /var/www/nextcloud;
    index index.php index.html;

    client_max_body_size 10G;
    client_body_timeout 300s;
    fastcgi_buffers 64 4K;

    add_header Referrer-Policy "no-referrer" always;
    add_header X-Content-Type-Options "nosniff" always;
    add_header X-Frame-Options "SAMEORIGIN" always;
    add_header X-Robots-Tag "noindex, nofollow" always;

    # Служебные адреса, которые Nextcloud требует отдавать редиректом
    location = /.well-known/carddav { return 301 /remote.php/dav; }
    location = /.well-known/caldav  { return 301 /remote.php/dav; }

    location / {
        rewrite ^ /index.php$request_uri;
    }

    location ~ ^/(?:build|tests|config|lib|3rdparty|templates|data)/ {
        deny all;
    }

    location ~ ^/(?:\.|autotest|occ|issue|indie|db_|console) {
        deny all;
    }

    location ~ ^/(?:index|remote|public|cron|core\/ajax\/update|status|ocs\/v[12]|updater\/.+|ocs-provider\/.+)\.php(?:$|\/) {
        fastcgi_split_path_info ^(.+?\.php)(\/.*|)$;
        include fastcgi_params;
        fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
        fastcgi_param PATH_INFO $fastcgi_path_info;
        fastcgi_param HTTPS on;
        fastcgi_param modHeadersAvailable true;
        fastcgi_param front_controller_active true;
        fastcgi_pass php-handler;
        fastcgi_intercept_errors on;
        fastcgi_request_buffering off;
    }

    location ~ \.(?:css|js|woff2?|svg|gif|png|jpg|ico)$ {
        try_files $uri /index.php$request_uri;
        expires 6M;
        access_log off;
    }
}

Блоки deny all закрывают каталоги с конфигами и данными — их отдавать наружу нельзя ни при каких обстоятельствах.

Включаем сайт и проверяем конфиг:

sudo ln -s /etc/nginx/sites-available/nextcloud /etc/nginx/sites-enabled/
sudo rm -f /etc/nginx/sites-enabled/default
sudo nginx -t

Секция с listen 443 ssl пока не заработает — сертификата ещё нет. Выпускаем его следующим шагом, certbot сам пропишет пути.

Выпускаем сертификат

sudo apt install -y certbot python3-certbot-nginx
sudo certbot --nginx -d cloud.example.com
sudo nginx -t && sudo systemctl reload nginx

Подробности про выпуск и автопродление — в статье про Let's Encrypt и certbot. Открываем порты:

sudo ufw allow 'Nginx Full'

Завершаем установку

Можно пройти мастер в браузере, но через консоль надёжнее — не будет таймаутов на медленной базе:

sudo -u www-data php /var/www/nextcloud/occ maintenance:install \
  --database "pgsql" \
  --database-name "nextcloud" \
  --database-host "127.0.0.1" \
  --database-user "nextcloud" \
  --database-pass "СильныйПароль" \
  --admin-user "admin" \
  --admin-pass "ДругойСильныйПароль" \
  --data-dir "/var/nextcloud-data"

Утилита occ — основной инструмент администрирования Nextcloud, запускается всегда от пользователя www-data.

Разрешаем домен, с которого будет открываться облако:

sudo -u www-data php /var/www/nextcloud/occ config:system:set trusted_domains 1 --value=cloud.example.com

Без этого Nextcloud покажет ошибку «Access through untrusted domain».

Подключаем кэш и правильный адрес для ссылок в письмах:

sudo -u www-data php /var/www/nextcloud/occ config:system:set memcache.local --value='\OC\Memcache\APCu'
sudo -u www-data php /var/www/nextcloud/occ config:system:set overwrite.cli.url --value='https://cloud.example.com'
sudo -u www-data php /var/www/nextcloud/occ config:system:set default_phone_region --value='RU'

Последняя настройка убирает предупреждение о регионе телефонных номеров.

Фоновые задачи через cron

Nextcloud по умолчанию выполняет фоновые задачи запросами из браузера (AJAX) — это медленно и ненадёжно. Правильный режим — системный cron.

sudo -u www-data php /var/www/nextcloud/occ background:cron
sudo crontab -u www-data -e

Добавляем строку:

*/5 * * * * php -f /var/www/nextcloud/cron.php

Проверяем, что задание встало:

sudo crontab -u www-data -l

Через пять минут в панели администратора время последнего запуска должно обновиться. Про синтаксис расписания — в статье про cron.

Проверяем результат

Заходим в веб-интерфейс, открываем «Параметры администратора → Обзор». В идеале там не должно быть ни одного предупреждения.

Типовые замечания и их причины:

Предупреждение Что делать
Отсутствует индекс в базе sudo -u www-data php occ db:add-missing-indices
Не настроен кэш памяти Проверить memcache.local и что php-apcu установлен
Заголовок HSTS не задан Добавить add_header Strict-Transport-Security в nginx
interned_strings_buffer мал Поднять до 16 и перезапустить PHP-FPM
Фоновые задачи через AJAX Перевести на cron, см. выше
Модуль PHP не найден Доустановить пакет и перезапустить PHP-FPM

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

sudo -u www-data php /var/www/nextcloud/occ status
sudo -u www-data php /var/www/nextcloud/occ check

Логи при проблемах смотрят в трёх местах:

sudo tail -f /var/nextcloud-data/nextcloud.log
sudo tail -f /var/log/nginx/error.log
sudo journalctl -u php8.3-fpm -f

Обновление и бэкап

Nextcloud обновляется через встроенный апдейтер или из консоли:

sudo -u www-data php /var/www/nextcloud/updater/updater.phar

Перед обновлением — обязательно копия. Бэкапить нужно три вещи: каталог приложения, каталог данных и базу.

sudo -u www-data php /var/www/nextcloud/occ maintenance:mode --on

sudo tar czf /backup/nextcloud-app-$(date +%F).tar.gz /var/www/nextcloud
sudo -u postgres pg_dump -Fc nextcloud > /backup/nextcloud-db-$(date +%F).dump
sudo rsync -a /var/nextcloud-data/ /backup/nextcloud-data/

sudo -u www-data php /var/www/nextcloud/occ maintenance:mode --off

Режим обслуживания на время копирования гарантирует, что база и файлы согласованы между собой. Про ключи rsync — в отдельной статье.

Частые вопросы

Какую базу выбрать для Nextcloud — PostgreSQL или MariaDB?

Обе поддерживаются официально. PostgreSQL лучше держит большое количество файлов и параллельных пользователей, MariaDB чуть проще в администрировании и чаще встречается в готовых инструкциях.

SQLite подходит только для теста: при нескольких пользователях он начинает блокировать запись и тормозить. Nextcloud об этом прямо предупреждает.

Почему Nextcloud пишет «Access through untrusted domain»?

Домен не внесён в список доверенных. Добавьте его: sudo -u www-data php occ config:system:set trusted_domains 1 --value=cloud.example.com.

Список хранится в config/config.php в массиве trusted_domains. Индекс 0 обычно занят localhost, поэтому свой домен добавляют под индексом 1 и далее.

Как увеличить максимальный размер загружаемого файла?

Три параметра должны быть согласованы: upload_max_filesize и post_max_size в php.ini, а также client_max_body_size в конфиге nginx. Наименьшее из трёх значений и станет фактическим лимитом.

После правки перезапустите PHP-FPM и перечитайте конфиг nginx: sudo systemctl restart php8.3-fpm && sudo systemctl reload nginx.

Обязательно ли настраивать cron?

Для рабочей установки — да. В режиме AJAX фоновые задачи (индексация, чистка корзины, отправка уведомлений) выполняются только когда кто-то открыл страницу, поэтому на малопосещаемом облаке они попросту не отрабатывают.

Системный cron раз в пять минут решает проблему полностью: */5 * * * * php -f /var/www/nextcloud/cron.php в crontab пользователя www-data.

Где Nextcloud хранит файлы пользователей?

В каталоге данных, который задаётся при установке параметром --data-dir. В этой инструкции — /var/nextcloud-data.

Держать его внутри веб-корня (/var/www/nextcloud/data) не стоит: при ошибке в конфигурации nginx файлы могут стать доступны по прямой ссылке. Вынесенный каталог такой возможности не оставляет.

Что запомнить

  • Каталог данных выносите за пределы веб-корня — это защита от раздачи файлов при ошибке в конфиге nginx.
  • Набор PHP-расширений критичен: без gd, intl, bcmath, gmp и apcu Nextcloud будет ругаться и терять функциональность.
  • Установку удобнее проводить командой occ maintenance:install, а не мастером в браузере — не будет таймаутов.
  • Фоновые задачи переводите на системный cron: в режиме AJAX они не выполняются на малопосещаемом облаке.
  • Бэкап состоит из трёх частей — приложение, данные, база; снимать их нужно в режиме обслуживания.

Похожие материалы

Серверный стек

Установка PostgreSQL на Ubuntu 24.04: кластер, роли, pg_hba.conf и доступ по сети

Ставим PostgreSQL из архива Ubuntu или из репозитория PGDG, создаём базу и пользователя, разбираемся с методами аутентификации в pg_hba.conf и аккуратно открываем доступ по сети. Плюс бэкап через pg_dump и типовые ошибки подключения.

Редакция
Серверный стек

Установка nginx на Ubuntu 24.04: пакет, виртуальные хосты, HTTPS и PHP

Ставим nginx на Ubuntu, разбираемся в структуре каталогов sites-available/sites-enabled, поднимаем первый виртуальный хост и включаем HTTPS. Отдельно — когда стоит взять свежую версию из репозитория nginx.org вместо архива Ubuntu и как подключить PHP-FPM.

Редакция
Серверный стек

Установка Docker на Ubuntu 24.04: официальный репозиторий, проверка, настройка

Ставим Docker Engine из официального репозитория Docker, а не из архива Ubuntu — там пакет отстаёт на месяцы и не содержит compose-плагина. Разбираем полную последовательность: ключ, репозиторий, установка, запуск без sudo, ограничение размера логов и главную ловушку Ubuntu — Docker публикует порты в обход UFW.

Редакция
Серверный стек на Ubuntu: nginx, БД, Docker
Серверный стек

Серверный стек на Ubuntu: nginx, БД, Docker

Этот раздел про инфраструктуру, на которой живёт типичное веб-приложение: фронт-прокси, база данных, контейнеры, кэш. Здесь карта стека и порядок, в котором его обычно поднимают на Ubuntu Server.

Михаил Орлов