Быстрое развертывание Rocket.Chat в Docker на Ubuntu: от установки до запуска

Практическое руководство для начинающих администраторов по развертыванию корпоративного мессенджера. Курс охватывает путь от подготовки чистого сервера до первичной настройки системы для работы команды.

1. Подготовка сервера Ubuntu и установка среды Docker

Подготовка сервера Ubuntu и установка среды Docker

До появления стандартизированных морских контейнеров в 1950-х годах погрузка судна была хаотичным процессом: бочки, мешки и ящики загружались вручную, часто повреждая друг друга. Изобретение универсального стального контейнера изменило мировую логистику — теперь портовым кранам неважно, что внутри: автомобили или бананы. Они работают со стандартным блоком. В мире разработки программного обеспечения похожую революцию совершил Docker.

Развертывание сложных веб-приложений, таких как Rocket.Chat, исторически требовало ручной установки множества компонентов. Вам нужно было бы установить правильную версию среды выполнения Node.js, настроить базу данных MongoDB, убедиться, что их версии совместимы с вашей операционной системой Ubuntu, и разрешить конфликты зависимостей, если на сервере уже крутятся другие проекты. Docker устраняет эту проблему, упаковывая приложение и все его зависимости в изолированные, стандартизированные программные блоки — контейнеры.

Архитектура: почему именно Docker

Традиционный подход к изоляции приложений — использование виртуальных машин (ВМ). Виртуальная машина эмулирует аппаратное обеспечение и запускает полноценную гостевую операционную систему поверх вашей основной (хостовой) ОС. Если вам нужно запустить три изолированных приложения, вы запускаете три виртуальные машины, каждая из которых потребляет гигабайты оперативной памяти и процессорное время просто на поддержание работы собственных ядер ОС.

Docker использует другой подход — контейнеризацию на уровне операционной системы.

!Сравнение архитектуры виртуальных машин и контейнеров Docker

Контейнеры не содержат собственной операционной системы. Они используют ядро вашей хостовой Ubuntu, но при этом изолированы друг от друга на уровне процессов, файловой системы и сети. Это делает их невероятно легковесными: контейнер запускается за доли секунды и потребляет ровно столько ресурсов, сколько нужно самому приложению, без накладных расходов на эмуляцию ОС. Для Rocket.Chat это означает, что база данных и сам мессенджер будут работать в изолированных средах, не засоряя системные директории вашего сервера, но при этом работать так же быстро, как если бы они были установлены напрямую в Ubuntu.

Подготовка операционной системы

Любая работа с новым сервером на базе Ubuntu начинается с обновления системных пакетов. Пакетный менеджер apt (Advanced Package Tool) использует локальную базу данных, в которой хранится информация о доступных программах и их версиях в официальных репозиториях.

Если сервер был установлен некоторое время назад, эта база данных устарела. Попытка установить новое программное обеспечение со старой базой может привести к ошибкам 404 (сервер не найдет старую версию программы по ссылке) или к нарушению зависимостей.

Процесс обновления состоит из двух строго последовательных шагов. Сначала необходимо обновить саму базу данных пакетов:

Команда update ничего не устанавливает. Она лишь скачивает актуальные списки программ с серверов Ubuntu и сравнивает их с тем, что установлено у вас. После выполнения этой команды терминал часто сообщает, что определенное количество пакетов может быть обновлено.

Второй шаг — фактическая установка новых версий:

Флаг -y (yes) автоматически отвечает утвердительно на вопрос системы «Хотите ли вы продолжить?», что экономит время. Процесс upgrade скачает и установит последние патчи безопасности и минорные обновления для системных утилит. Это критически важный фундамент: установка сложных сред вроде Docker на необновленную систему — прямой путь к конфликтам библиотек.

Установка среды Docker

Существует несколько способов установить Docker на Ubuntu: из стандартных репозиториев Ubuntu, через добавление официального репозитория Docker или с помощью автоматического скрипта.

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

Выполните в терминале следующую команду:

Разберем, что здесь происходит. Утилита curl обращается к веб-серверу по указанному адресу и скачивает содержимое.

  • Флаг -f (fail) заставляет curl тихо завершиться с ошибкой, если сервер недоступен, не выдавая мусорный HTML-код в терминал.
  • Флаг -s (silent) скрывает прогресс-бар скачивания.
  • Флаг -S (show-error) в комбинации с -s гарантирует, что если ошибка всё же произойдет, мы её увидим.
  • Флаг -L (location) позволяет переходить по редиректам, если файл переехал.
  • Конструкция -o get-docker.sh сохраняет скачанный текст в локальный файл с названием get-docker.sh.
  • Теперь этот скрипт нужно запустить с правами суперпользователя:

    Процесс займет от одной до нескольких минут в зависимости от скорости интернет-соединения сервера. Скрипт установит docker-ce (Community Edition — сам движок), docker-ce-cli (инструмент командной строки для управления движком) и containerd.io (низкоуровневую среду выполнения контейнеров).

    Настройка прав доступа

    По умолчанию архитектура Docker состоит из двух частей: фоновой службы (демона), которая выполняет всю тяжелую работу по созданию и запуску контейнеров, и клиентской утилиты командной строки (CLI), через которую мы отдаем команды.

    Демон Docker взаимодействует напрямую с ядром Linux и требует прав суперпользователя (root). Поэтому, если вы попытаетесь выполнить команду docker ps (показать запущенные контейнеры) от имени обычного пользователя, вы получите ошибку вида permission denied while trying to connect to the Docker daemon socket.

    Чтобы не писать sudo перед каждой командой Docker, необходимо добавить вашего текущего пользователя в специальную системную группу docker, которая создается автоматически при установке.

    bash docker compose version bash docker run hello-world ``

    Эта простая команда запускает сложную последовательность действий, которая является основой работы с любым приложением в Docker.

    !Жизненный цикл контейнера при выполнении команды run

    Когда вы нажимаете Enter, происходит следующее:

  • Клиент Docker обращается к фоновому демону и передает ему команду запустить образ hello-world`.
  • Демон проверяет локальное хранилище сервера. Поскольку мы только что установили Docker, образа там нет.
  • Демон автоматически подключается к Docker Hub (официальному публичному реестру образов) и скачивает (pull) нужный образ оттуда.
  • Из скачанного образа демон создает новый изолированный контейнер и запускает внутри него программу.
  • Программа выводит в ваш терминал приветственное сообщение, объясняющее, что установка прошла успешно, после чего завершает свою работу. Контейнер переходит в остановленное состояние.
  • Если вы видите сообщение, начинающееся со слов «Hello from Docker!», значит базовый фундамент полностью готов. Сервер обновлен, среда контейнеризации установлена, права настроены корректно, а плагин Compose ожидает инструкций. Инфраструктура готова к тому, чтобы принять конфигурационный файл и развернуть полноценный сервер Rocket.Chat.

    2. Создание и конфигурация шаблона docker-compose для Rocket.Chat

    Создание и конфигурация шаблона docker-compose для Rocket.Chat

    Представьте, что вам нужно собрать сложный механизм из сотен деталей, но вместо того чтобы вручную закручивать каждый болт, у вас есть магический чертеж. Стоит приложить его к верстаку — и механизм собирается сам. В мире контейнеризации таким чертежом является файл docker-compose.yml. Для новичка запуск Rocket.Chat может показаться сложным из-за необходимости настраивать не только сам мессенджер, но и базу данных, а также обеспечивать их бесперебойную связь. Однако использование Docker Compose превращает эту многослойную задачу в редактирование одного текстового документа.

    Архитектурная связка: почему Rocket.Chat не работает в одиночку

    Прежде чем переходить к написанию конфигурации, важно понять, из каких «кирпичей» строится наше здание. Rocket.Chat — это приложение, написанное на JavaScript (Node.js), которое по своей природе является «безгосударственным» (stateless). Это значит, что сам код мессенджера не умеет хранить историю ваших переписок, аватарки пользователей или настройки комнат внутри себя. Если вы просто запустите контейнер с Rocket.Chat и завтра его удалите, все данные исчезнут.

    Для постоянного хранения информации Rocket.Chat использует внешнюю базу данных — MongoDB. Это NoSQL-решение, которое идеально подходит для мессенджеров, так как оно быстро обрабатывает неструктурированные данные (сообщения разной длины, метаданные файлов). Таким образом, наша минимальная рабочая среда всегда состоит из двух ключевых сервисов:

  • Rocket.Chat — «мозг» системы, отвечающий за логику, интерфейс и обработку запросов пользователей.
  • MongoDB — «память» системы, где лежат все данные.
  • В Docker Compose эти сервисы описываются в одном файле, что позволяет им видеть друг друга по внутренним именам внутри виртуальной сети, которую Docker создаст автоматически.

    Структура YAML: правила написания «чертежа»

    Файлы конфигурации Docker Compose используют формат YAML (Yet Another Markup Language). Его главная особенность — строгая зависимость от отступов. В отличие от языков программирования, где скобки {} определяют границы блоков, в YAML всё решают пробелы.

    > Ошибка в один лишний пробел в начале строки приведет к тому, что Docker не сможет прочитать файл. Всегда используйте именно пробелы, а не клавишу Tab, чтобы избежать проблем с интерпретацией текста разными редакторами.

    Типичная структура файла выглядит так:

  • version: указывает версию формата (сейчас чаще всего используется '3.8' или '3.9').
  • services: раздел, где мы перечисляем наши компоненты (rocketchat, mongodb).
  • volumes: описание мест на диске вашего сервера, где данные будут сохраняться даже после остановки контейнеров.
  • networks: описание виртуальных сетей для связи компонентов.
  • Подготовка рабочего пространства

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

    Выполните в терминале Ubuntu следующую последовательность команд:

    Здесь мы создали папку rocket-project в домашнем каталоге пользователя и перешли в неё. Теперь создадим сам файл конфигурации с помощью текстового редактора nano:

    Перед вами откроется пустое окно редактора. Именно сюда мы будем вписывать конфигурацию, которую разберем ниже.

    Разбор конфигурации сервиса базы данных (MongoDB)

    Первым делом в нашем файле мы опишем базу данных. Без неё Rocket.Chat даже не начнет процесс инициализации. Для современных версий Rocket.Chat (начиная с 4.x и 5.x) критически важно использовать правильную версию MongoDB и специфический режим работы — Replica Set.

    Даже если у вас всего один сервер базы данных, Rocket.Chat требует, чтобы MongoDB работала в режиме репликации. Это техническая особенность движка сообщений, которая позволяет приложению мгновенно узнавать об изменениях в базе данных (например, о приходе нового сообщения) без постоянного опроса сервера.

    Вставьте следующий блок в редактор:

    Разберем, что здесь происходит:

  • image: bitnami/mongodb:5.0: Мы берем готовый образ от Bitnami. Это проверенный поставщик, который заранее настроил MongoDB для удобной работы в контейнерах.
  • volumes: Здесь мы говорим Docker: «Возьми папку внутри контейнера /bitnami/mongodb и привяжи её к виртуальному хранилищу mongodb_data на диске сервера». Это гарантирует сохранность ваших чатов.
  • MONGODB_REPLICA_SET_MODE=primary: Мы принудительно включаем режим репликации, о котором говорили выше.
  • ALLOW_EMPTY_PASSWORD=yes: Для тестовой среды внутри закрытой сети Docker это допустимо, так как база данных не будет доступна из внешнего интернета напрямую.
  • Конфигурация сервиса Rocket.Chat

    Теперь, когда база данных описана, добавим описание самого мессенджера. Этот блок должен идти сразу после MongoDB, с тем же уровнем отступа.

    Здесь скрыто несколько важных нюансов:

  • Повторные попытки запуска (command): Контейнеры запускаются почти одновременно. Rocket.Chat стартует быстрее, чем MongoDB успевает полностью инициализироваться. Без этого скрипта-цикла Rocket.Chat попытается подключиться к базе, упадет с ошибкой и прекратит работу. Скрипт заставляет его пробовать подключение 30 раз с паузой в 5 секунд.
  • Переменные окружения:
  • - ROOT_URL: Здесь указывается адрес, по которому вы будете заходить в мессенджер. Для теста на локальной машине оставляем http://localhost:3000. Если у вас есть домен или внешний IP — его нужно будет вписать сюда позже. - MONGO_URL и MONGO_OPLOG_URL: Это «адресная книга» для Rocket.Chat. Обратите внимание на слово mongodb в адресе — это имя сервиса, которое мы дали базе данных выше. Docker сам сопоставит это имя с нужным контейнером.
  • Порты (ports): Запись 3000:3000 означает: «Возьми порт 3000 внутри контейнера и пробрось его на порт 3000 нашего сервера Ubuntu». Теперь, введя в браузере IP сервера с этим портом, мы увидим интерфейс чата.
  • Зависимость (depends_on): Эта директива говорит Docker, что сервис rocketchat логически зависит от mongodb, и базу нужно пытаться запустить первой.
  • Финальные штрихи: тома данных

    В самом конце файла, без каких-либо отступов слева, нам нужно объявить тома (volumes), которые мы использовали в описании сервисов. Это служебная секция, которая велит Docker создать именованные области памяти.

    Полный файл docker-compose.yml должен выглядеть как монолитная структура, где каждый пробел на своем месте. После того как вы вставили текст в nano, нажмите Ctrl + O (сохранить), Enter и Ctrl + X (выйти).

    Нюансы работы с томами и данными

    Важно понимать разницу между типами хранилищ в Docker. Мы использовали именованные тома (named volumes).

  • Они управляются самим Docker.
  • Вы не видите их как обычные папки в ~/rocket-project.
  • Они хранятся в глубоких системных директориях Docker (обычно /var/lib/docker/volumes/).
  • Это удобно для новичков, так как Docker сам следит за правами доступа к этим папкам. Если бы мы использовали «bind mounts» (привязку к конкретной папке на диске), нам пришлось бы вручную настраивать права пользователя id 1001 (под которым работает образ Bitnami), чтобы база данных могла записывать файлы. Использование именованных томов избавляет нас от этой головной боли на этапе первого запуска.

    Проверка конфигурации перед стартом

    Прежде чем вводить команду на запуск (которую мы подробно разберем в следующей части), полезно проверить файл на наличие синтаксических ошибок. Docker Compose имеет встроенную команду для валидации:

    Если вы всё сделали правильно, команда выведет в терминал «собранную» версию вашего файла. Если же где-то закрался лишний пробел или вы забыли двоеточие, терминал выдаст ошибку с указанием строки. Чаще всего новички ошибаются в блоке environment, забывая дефис перед переменной или ставя пробел там, где его быть не должно.

    Например, запись - PORT=3000 верна, а -PORT=3000 (без пробела после дефиса) — нет. Также помните, что значения, содержащие специальные символы или пробелы, лучше заключать в кавычки, хотя для портов и простых URL это не всегда обязательно.

    Безопасность и масштабирование

    Хотя мы создаем тестовую среду, стоит помнить о будущем. В этой конфигурации мы используем latest тег для Rocket.Chat. Это означает, что при каждом перезапуске Docker может скачать самую новую версию. В промышленной эксплуатации профессионалы фиксируют версию, например registry.rocket.chat/rocketchat/rocket.chat:6.2.0, чтобы внезапное обновление не сломало базу данных из-за несовместимости.

    Также мы не ограничивали ресурсы. По умолчанию контейнеры могут потреблять столько оперативной памяти, сколько им даст система. Для Rocket.Chat желательно иметь минимум 2 ГБ ОЗУ на сервере, так как Node.js и MongoDB довольно требовательны к ресурсам даже в режиме простоя.

    Подготовка файла docker-compose.yml — это 80% успеха. Мы создали описание системы, которая сама развернет базу данных, настроит репликацию, свяжет приложение с хранилищем и подготовит сетевые мосты. Теперь наша инфраструктура описана как код (Infrastructure as Code), и её можно легко перенести на другой сервер, просто скопировав этот файл.