Образ «всё в одном»: один контейнер, многоузловые кластеры и кластеры с разделением вычислений и хранения
Официальный образ Apache Doris «всё в одном», apache/doris:all-in-one-<version>, содержит выпущенные версии FE, BE и Meta Service; переменная окружения DORIS_ROLE определяет, что контейнер запускает при старте. Один и тот же образ используется в трёх сценариях:
| Режим | Как запустить | Для чего предназначен |
|---|---|---|
| Один контейнер 1 FE + 1 BE в одном контейнере, готовность примерно через 20 с | docker run apache/doris:all-in-one-4.1.3 | Тестовое окружение e2e / CI для проектов экосистемы, таких как коннекторы, SDK и инструменты интеграции данных: настоящий экземпляр Doris вместо имитации |
| Многоузловой кластер 3 FE + 3 BE, отдельный контейнер для каждого узла, готовность примерно через 35 с | docker compose -f multi-node.yml up --wait | Локальная проверка сценариев, которые нельзя воспроизвести в одном контейнере: выбор ведущего FE и переключение при отказе, три реплики, балансировка, вывод узлов из эксплуатации |
| Кластер с разделением вычислений и хранения FoundationDB + Meta Service + Recycler + MinIO + от 1 до 3 FE + 3 BE в 2 вычислительных группах, готовность примерно через 50 с | docker compose -f cloud.yml up --wait | Локальная разработка функций и демонстрация режима с разделением вычислений и хранения: вычислительные группы, storage vault, переключение FE при отказе в облачном режиме без внешних облачных ресурсов |
Режим с одним контейнером предназначен для CI и не требует ничего, кроме docker run. Два файла Compose находятся в каталоге docker/runtime/all-in-one/4.1/compose/ основного репозитория Doris и предназначены для локальной разработки функций и демонстраций. Во всех трёх режимах есть проверка состояния: healthy означает, что кластер сформирован, поэтому зависимым процессам не нужно опрашивать состояние или вызывать sleep.
Все три режима предназначены для тестирования и разработки, а не для эксплуатации в рабочей среде: объём памяти уменьшен с учётом ресурсов исполнителей CI и рабочих станций, режим с одним контейнером использует одну реплику, а по умолчанию данные нигде не сохраняются. Многоузловой кластер и кластер с разделением вычислений и хранения также не заменяют конвейеры регрессионного тестирования; наборам тестов docker() из regression-test/suites/cloud_p0 по-прежнему нужен doris-compose.
Обзор образа
Теги образов имеют вид apache/doris:all-in-one-<version>, например apache/doris:all-in-one-4.1.3. Во всех примерах ниже используется версия 4.1.3; замените её нужной вам версией. Доступные теги перечислены в репозитории apache/doris на Docker Hub.
Образ собирается из официальных образов apache/doris:fe-<version>, be-<version> и ms-<version>, поэтому внутри запускаются именно выпущенные артефакты. Для уменьшения размера выполняются только две операции: отладочная информация удаляется из doris_be, а также из компонентов Meta Service doris_cloud и libfdb_c.so (таблица .symtab сохраняется, поэтому в трассировках стека при сбоях по-прежнему определяются имена функций), и удаляются каталоги JNI-сканеров, которые не нужны данному тегу.
Два тега: базовый и -full
| Тег | Возможности | Размер образа (4.1.3, без сжатия) |
|---|---|---|
apache/doris:all-in-one-<version> | Внутренние таблицы, Hive, Iceberg (включая системные таблицы), Paimon, JDBC Catalog, обратная запись во внешние таблицы, Java UDF | Около 2.7 ГБ |
apache/doris:all-in-one-<version>-full | Всё перечисленное выше, а также Hudi, коннектор Trino, MaxCompute | Около 3.2 ГБ |
Указанные размеры представляют собой сумму размеров несжатых слоёв, измеренную для версии 4.1.3; около 0.2 ГБ в каждом образе занимает Meta Service, который используется только кластером с разделением вычислений и хранения. Для сравнения: те же компоненты без удаления отладочной информации и лишних каталогов занимают около 5.6 ГБ.
Выбирайте -full, только если тесты действительно читают таблицы Hudi, используют коннектор Trino или MaxCompute. В остальных случаях используйте тег без суффикса. Ни один из трёх режимов не требует определённого тега; кластеры Compose можно переключить на -full или на самостоятельно собранный тег с помощью переменной окружения DORIS_IMAGE.
Разница между двумя тегами обусловлена тем, как BE загружает сканеры: при запуске BE перебирает каталоги в be/lib/java_extensions/ для загрузки JNI-сканеров. Отдельного списка и параметра конфигурации нет, поэтому тег поддерживает ровно те форматы, каталоги которых входят в образ. Обратите внимание: чтение данных Hive и Iceberg выполняется встроенным в BE модулем чтения parquet / orc, а не этими JNI-сканерами, поэтому поддерживается обоими тегами.
Поддержка нескольких архитектур
apache/doris:all-in-one-4.1.3 представляет собой индекс образов OCI, содержащий по одному манифесту для linux/amd64 и linux/arm64. Команда docker pull автоматически выбирает вариант, соответствующий архитектуре хоста, как и для apache/doris:fe-4.1.3, поэтому CI не нужны разные теги для исполнителей с разной архитектурой.
docker buildx imagetools inspect apache/doris:all-in-one-4.1.3
Как правило, BE Doris не может работать при эмуляции другой архитектуры. Например, запуск образа amd64 с параметром --platform linux/amd64 на Apple Silicon завершается ошибкой сегментации; официальные образы apache/doris:be-* ведут себя так же. Запускайте образ на реальном оборудовании соответствующей архитектуры.
Один контейнер: окружение для интеграционных тестов
Проектам экосистемы Apache Doris, таким как коннекторы, SDK и инструменты интеграции данных, для запусков e2e / CI обычно нужен настоящий экземпляр Doris вместо имитации. Режим с одним контейнером предназначен именно для этого: один FE и один BE в одном контейнере, готовые к использованию после запуска, позволяют подключить его как тестовое окружение.
Возможности, важные для интеграционного тестирования:
| Возможность | Описание |
|---|---|
| Готовность к работе | Запуск FE, регистрация BE командой ALTER SYSTEM ADD BACKEND и ожидание перехода BE в рабочее состояние выполняются внутри контейнера. Внешний скрипт не требуется |
| Проверка состояния | Образ содержит HEALTHCHECK, который переходит в состояние healthy, только когда FE готов и BE работает, обычно в течение 20 секунд. CI может ждать этого состояния вместо вызова sleep |
| Одна реплика | Задано force_olap_table_replication_num = 1, поэтому для CREATE TABLE не требуется replication_num |
| Ограниченные ресурсы | Потребление памяти уменьшено с учётом ресурсов исполнителей CI: куча FE -Xmx2048m, куча JNI на стороне BE -Xmx1024m и параметр BE mem_limit = 40% |
| Немедленное завершение при сбое | Если FE или BE завершает работу, контейнер сразу завершается с ненулевым кодом, а не перезапускает процесс незаметно, поэтому сбой немедленно становится виден в CI |
| Корректная остановка | docker stop сначала останавливает BE, затем FE и завершается с кодом 0 |
| Несколько архитектур | Один тег охватывает linux/amd64 и linux/arm64 |
Информация для подключения
| Параметр | Описание |
|---|---|
| Протокол MySQL | Порт 9030, пользователь root, без пароля |
| FE HTTP | Порт 8030, /api/health не требует аутентификации |
| BE HTTP | Порт 8040, конечная точка Stream Load |
| Проверка доступности BE | Порт 9050, используется внутри контейнера, обычно не пробрасывается на хост |
Обычный docker run
docker run -d --name doris \
-p 9030:9030 -p 8030:8030 -p 8040:8040 \
apache/doris:all-in-one-4.1.3
# Wait until the container is healthy
until [ "$(docker inspect -f '{{.State.Health.Status}}' doris)" = healthy ]; do sleep 1; done
mysql -uroot -h127.0.0.1 -P9030 -e "SHOW BACKENDS"
Образ содержит клиент MySQL, поэтому, если на хосте его нет, запустите его внутри контейнера:
docker exec doris mysql -uroot -h127.0.0.1 -P9030 -e "SHOW BACKENDS"
Docker Compose
При использовании depends_on и service_healthy тестовый контейнер запускается только после того, как Doris действительно готов к работе:
services:
doris:
image: apache/doris:all-in-one-4.1.3
ports: ["9030:9030", "8030:8030", "8040:8040"]
integration-test:
image: my-project-tests:latest
depends_on:
doris:
condition: service_healthy
GitHub Actions
Если Doris используется как сервисный контейнер, GitHub Actions ждёт, пока контейнер перейдёт в состояние healthy, прежде чем выполнять steps, поэтому тестовому коду не нужна собственная логика повторных попыток и ожидания:
jobs:
e2e:
runs-on: ubuntu-latest
services:
doris:
image: apache/doris:all-in-one-4.1.3
ports: ['9030:9030', '8030:8030', '8040:8040']
steps:
- uses: actions/checkout@v4
- run: mvn -B verify -Pe2e
Настройка конфигурации
Образ уже содержит набор настроек по умолчанию для интеграционных тестов. Чтобы изменить их, используйте перечисленные ниже переменные окружения; они записываются в fe.conf / be.conf при запуске контейнера, причём последнее присваивание имеет приоритет:
docker run -d --name doris \
-p 9030:9030 -p 8030:8030 -p 8040:8040 \
-e BE_CONFIG_EXTRA="mem_limit = 80%" \
-e FE_CONFIG_EXTRA="qe_max_connection = 2048" \
-e FE_HEAP=4096m \
apache/doris:all-in-one-4.1.3
| Переменная окружения | Действие |
|---|---|
FE_CONFIG_EXTRA | Добавляется в конец fe.conf. Разделяйте несколько параметров переводами строк |
BE_CONFIG_EXTRA | Добавляется в конец be.conf. Разделяйте несколько параметров переводами строк |
FE_HEAP / BE_HEAP | Переопределяют -Xmx JVM на стороне FE / BE, например 4096m; значения по умолчанию составляют 2048m и 1024m |
Сохранение данных: по умолчанию данные не сохраняются и удаляются вместе с контейнером, что обычно и требуется для CI. Чтобы сохранить данные, подключите каталоги /opt/apache-doris/fe/doris-meta и /opt/apache-doris/be/storage. Процедура запуска идемпотентна, поэтому один и тот же каталог данных можно использовать при повторных запусках.
Устранение неполадок
docker logs <container>содержит журнал запуска entrypoint и вывод консоли FE, по которым можно определить, на каком этапе остановился запуск кластера.- Полные журналы находятся внутри контейнера в
fe/log/fe.logиbe/log/be.INFO. - Завершение контейнера с ненулевым кодом означает, что FE или BE аварийно завершил работу. Запись в журнале непосредственно перед завершением указывает, какой именно процесс завершился и какой файл журнала следует прочитать.
- Для тестов с большими объёмами данных может потребоваться увеличить
vm.max_map_countна хосте (sysctl -w vm.max_map_count=2000000). Этот параметр sysctl не изолирован пространствами имён, поэтому контейнер не может его установить; по этой причине образ пропускает его проверку вstart_be.sh.
Многоузловые кластеры и кластеры с разделением вычислений и хранения
Два файла Compose находятся в каталоге docker/runtime/all-in-one/4.1/compose/ основного репозитория Doris и требуют Docker Compose v2 (подкоманду docker compose). По умолчанию используется образ apache/doris:all-in-one-4.1.3; его можно изменить через DORIS_IMAGE, задав переменную окружения или указав её в файле .env рядом с файлом Compose. Все остальные параметры передаются таким же образом, а полный их список приведён в комментарии в начале каждого файла.
cd <doris repository>/docker/runtime/all-in-one/4.1/compose
Оба файла содержат сервис client: он переходит в состояние healthy, только когда все узлы работают; именно этого ждёт docker compose up --wait. Затем он остаётся в ожидании внутри сети кластера и предоставляет mysql и curl, поэтому к кластеру можно обращаться через docker compose exec client ....
Многоузловой кластер: multi-node.yml
docker compose -f multi-node.yml up --wait # healthy in about 35 s
docker compose -f multi-node.yml exec client mysql -uroot -hfe-1 -P9030
docker compose -f multi-node.yml kill fe-1 # a new master in a few seconds
docker compose -f multi-node.yml start fe-1 # rejoins as a follower
docker compose -f multi-node.yml down # tears the cluster down; nothing persists
fe-1 ─┬─ fe-2, fe-3
├─ be-1, be-2, be-3
└─ client
fe-1создаёт кластер, аfe-2,fe-3присоединяются в роли follower;FE3_ROLE=observerпереводитfe-3в роль observer.- По умолчанию таблицы имеют три реплики, по одной на каждый BE, как в настоящем кластере.
- Порты хоста:
9030/8030дляfe-1,9031/8031дляfe-2,9032/8032дляfe-3и8040для HTTP-портаbe-1. - Параметры:
DORIS_IMAGE,SUBNET(по умолчанию172.31.81), порты хоста,FE_HEAP(по умолчанию1024m),BE_MEM_LIMIT(по умолчанию25%),FE3_ROLE.
Кластер с разделением вычислений и хранения: cloud.yml
docker compose -f cloud.yml up --wait # 1 FE + 3 BE, healthy in about 50 s
docker compose -f cloud.yml --profile ha up --wait # ... plus two follower FEs, 3 FEs in total
docker compose -f cloud.yml exec client mysql -uroot -hfe-1 -P9030
docker compose -f cloud.yml down # tears the cluster down; nothing persists
fdb ─ fdb-init ─┬─ ms ─ cloud-init ─ fe-1 ─┬─ be-1, be-2 (cg_a)
└─ recycler ├─ be-3 (cg_b)
minio ─ minio-init ─┘ └─ client
- Все процессы Doris (FE, BE, Meta Service, Recycler) запускаются из образа «всё в одном»; FoundationDB и MinIO используют образы своих исходных проектов.
cloud-initпредставляет собой контейнер для однократного выполнения, который создаёт экземпляр в Meta Service в режиме storage vault с MinIO в качестве хранилища (адресация path-style, обычный HTTP); затемfe-1назначаетbuilt_in_storage_vaultхранилищем по умолчанию, поэтомуCREATE TABLEработает без явного указания хранилища. Оба шага идемпотентны.- Три узла BE образуют две вычислительные группы:
be-1иbe-2входят вcg_a, аbe-3входит вcg_b. Такое окружение позволяет выполнятьuse @cg_b,SHOW COMPUTE GROUPS,ALTER SYSTEM ADD BACKEND ... ("tag.compute_group_name" = ...), проверять storage vault, прогрев данных и переключение FE при отказе в облачном режиме, а также наблюдать, как объекты появляются в MinIO. - Порты хоста:
9030/8030дляfe-1(9031/8031и9032/8032дляfe-2иfe-3при использовании профиляha),8040для HTTP-портаbe-1,15000для HTTP API Meta Service (5000занят AirPlay в macOS),9000для MinIO и9001для консоли MinIO (minioadmin/minioadmin). - Параметры:
DORIS_IMAGE,SUBNET(по умолчанию172.31.80), порты хоста,FE_HEAP,BE_MEM_LIMIT,CG_A/CG_B(имена вычислительных групп),INSTANCE_ID(по умолчанию100001, также используется какcluster_idузлов FE),S3_BUCKET/S3_AK/S3_SK,FDB_IMAGE/FDB_PLATFORM. - Кластер, запущенный с
--profile ha, следует останавливать и удалять с тем же флагом, чтобыfe-2иfe-3из этого профиля обрабатывались вместе с остальными компонентами.
Что нужно знать
- Сохранение данных. Команды
docker compose stop/start(или повторныйup) сохраняют данные; создание экземпляра, назначение хранилища по умолчанию и регистрация узлов идемпотентны. Командаdownудаляет контейнеры и сеть, а вместе с ними и данные. - Адреса узлов. Узлы получают фиксированные IP-адреса в частной подсети (
SUBNET, по умолчанию172.31.81для многоузлового кластера и172.31.80для облачного), поэтому после перезапуска контейнер сохраняет идентификатор, под которым он известен Doris. В файлах используются разные подсети, поэтому оба кластера могут работать одновременно, если одному из них назначить другие порты хоста. - Доступ с хоста. Используйте опубликованные порты. В Docker Desktop (macOS / Windows) адреса контейнеров недоступны для маршрутизации с хоста, поэтому Stream Load, запущенный с хоста, не сможет последовать перенаправлению FE на BE; запускайте его из сервиса
client(docker compose -f <file> exec client curl ...). На хостах Linux узлы доступны напрямую. - Память. Значения по умолчанию составляют
FE_HEAP=1024mиmem_limit = 25%для каждого BE. Полный кластер с разделением вычислений и хранения занимает около 9 ГБ; выделите Docker Desktop не менее 12 ГБ и не рассчитывайте разместить обе топологии одновременно на виртуальной машине с 16 ГБ памяти. - FoundationDB на Apple Silicon. Исходные образы
foundationdb/foundationdb:7.1.xдоступны только для amd64, поэтому на Apple Siliconfdbработает под эмуляцией, что допустимо для этих задач; заменить образ и платформу можно черезFDB_IMAGE/FDB_PLATFORM. Meta Service скомпонован с клиентской библиотекой 7.1, поэтому используйте сервер 7.1. - Проверка работоспособности.
compose/smoke-test.sh <multi-node|cloud> [image:tag]запускает топологию с отдельным именем проекта, подсетью и портами хоста, проверяет реплики или вычислительные группы и хранилище, выполняет Stream Load через клиент, принудительно завершает ведущий FE, перезапускает BE, пока прежний ведущий узел недоступен, возвращает ведущий узел в работу и удаляет всё окружение. Около двух минут на каждую топологию.
Роли контейнеров: DORIS_ROLE
Оба файла Compose используют роли одного и того же образа; entrypoint определяет по DORIS_ROLE, что должен запускать контейнер. Таким же образом можно собрать собственную топологию, например 1 FE + 5 BE:
DORIS_ROLE | Что запускается | Обязательные переменные |
|---|---|---|
all (по умолчанию) | FE + BE в одном контейнере, то есть режим с одним контейнером | нет |
fe | Один FE. Создаёт новый кластер, если FE_MASTER пуст; в противном случае регистрируется в роли FE_ROLE (follower | observer) и присоединяется к кластеру | FE_MASTER |
be | Один BE, регистрируемый через FE_MASTER; в режиме с разделением вычислений и хранения входит в вычислительную группу, имя которой задано в COMPUTE_GROUP | FE_MASTER |
ms / recycler | Meta Service / Recycler для режима с разделением вычислений и хранения | FDB_CLUSTER |
cloud-init | Однократное выполнение: создаёт экземпляр с разделением вычислений и хранения на основе S3-совместимого объектного хранилища, затем завершает работу | MS_ENDPOINT, INSTANCE_ID, S3_* |
client | Ожидает появления работающих узлов в количестве EXPECT_FE / EXPECT_BE, затем остаётся в ожидании с доступными mysql и curl | FE_MASTER |
DEPLOY_MODE=cloudпереводитfeиbeв режим разделения вычислений и хранения (параметрыdeploy_mode,meta_service_endpoint, файловый кеш и прочие настройки записываются автоматически); FE используетINSTANCE_IDв качестве своегоcluster_idи управляет узлами через SQL, поэтому назначатьcloud_unique_idне требуется.FE_MASTERможет содержать список нескольких FE (fe-1,fe-2,fe-3): используется первый ответивший узел, поэтому перезапуск узла не задерживается из-за ожидания FE, который в данный момент недоступен. FE, у которого уже есть метаданные, присоединяется повторно самостоятельно.- Все роли учитывают
FE_CONFIG_EXTRA/BE_CONFIG_EXTRA/MS_CONFIG_EXTRAиFE_HEAP/BE_HEAP, а после запуска создают флаг готовности, на который ориентируетсяHEALTHCHECKобраза. Поэтомуdocker compose up --waitждёт формирования всего кластера, а аварийное завершение процесса по-прежнему приводит к завершению контейнера с ненулевым кодом. - Настройки, зависящие от топологии (
priority_networks, число реплик, балансировка, параметры разделения вычислений и хранения), записываются entrypoint для каждой роли при запуске контейнера; встроенные в образ файлы конфигурации содержат только значения по умолчанию, связанные с объёмом ресурсов.
Самостоятельная сборка образа
Dockerfile и скрипт сборки находятся в каталоге docker/runtime/all-in-one/<release-line>/ основного репозитория Doris; сейчас доступна линейка 4.1. Структура артефактов в разных линейках релизов различается достаточно сильно, поэтому каждой выделен собственный каталог вместо переключения версий внутри единого Dockerfile.
build.sh является единственной точкой входа, а сам скрипт можно запускать из любого каталога:
# Build both the base and the -full tag from the official 4.1.3 component images
# (fe / be / ms), host architecture only
./build.sh -v 4.1.3
# Build base only, then run a smoke test against it
./build.sh -v 4.1.3 -f base -t
# Build from a local ./output, which is handy for verifying your own changes.
# Build Doris with build.sh --fe --be --cloud first; without --cloud there is no
# ./output/ms and the resulting image cannot serve the compute-storage separated cluster
./build.sh -v dev -s local
# Build from an extracted release tarball, e.g. while the component images of a
# new release are not on Docker Hub yet
./build.sh -v 4.1.4 -s tarball --tarball-dir ~/apache-doris-4.1.4-bin-x64
Контекстом сборки всегда служит корень репозитория (его содержимое сокращается до нескольких КБ с помощью Dockerfile.dockerignore); локальный ./output или каталог распакованного архива передаётся как именованный контекст BuildKit, поэтому может находиться где угодно, но для этого требуется docker buildx. Самостоятельно собранный образ можно напрямую использовать с обоими файлами Compose:
DORIS_IMAGE=apache/doris:all-in-one-dev docker compose -f multi-node.yml up --wait
Без --platform сборка выполняется только для архитектуры хоста. Для сборки под несколько архитектур их нужно указать явно, например ./build.sh -v 4.1.3 --platform linux/amd64,linux/arm64 --push. Поскольку сборка для другой архитектуры использует эмуляцию и занимает много времени, для релиза лучше собирать каждую архитектуру на отдельной машине соответствующей архитектуры, а затем объединять результаты с помощью docker buildx imagetools create.
./build.sh --help выводит остальные параметры.
Подробности реализации, в том числе что удаляется из образа, почему нельзя удалять некоторые каталоги, похожие на необязательные компоненты для внешних таблиц, на что расходуется место и как запускать проверку работоспособности, см. в README в этом каталоге.