Перейти к основному содержимому
Версия: 2.0.x

Engine cluster, bootstrap и storage

Selena Engine устанавливается только через Selena Cluster Manager API. Не создавайте Engine StatefulSet/CR вручную и не масштабируйте их напрямую в штатном режиме.

Порядок:

  1. Сохранить Engine spec в CM.
  2. Запустить install operation.
  3. Дождаться READY.
  4. Запустить auth/RBAC bootstrap.
  5. Проверить bootstrap credentials и FE MySQL endpoint.
  6. Настроить storage volume, если deployment использует shared-data/S3.

1. Проверка перед Engine install​

Перед продолжением должны быть готовы:

  • CM health UP;
  • license загружена;
  • Selena operator установлен;
  • {engine_namespace} создан;
  • image pull Secret selena-registry создан в {engine_namespace};
  • selena-ide-secrets и selena-ai-secrets созданы в {selena_namespace}, если Engine bootstrap должен записать туда IDE/AI impersonator passwords;
  • CM admin access token получен из POST {cm_url}/auth/login.

Проверки:

curl -fsS {cm_url}/actuator/health | jq

curl -fsS {cm_url}/license \
-H 'Authorization: Bearer {cm_admin_access_token}' \
| jq

kubectl -n {operator_namespace} get pods -o wide
kubectl -n {engine_namespace} get secret selena-registry
kubectl -n {selena_namespace} get secret selena-ide-secrets selena-ai-secrets

2. Минимальный Engine spec​

Пример ниже описывает SHARED_DATA cluster: 3 FE + 3 CN. Это рекомендуемый вариант для deployment, где данные хранятся во внешнем shared storage/S3, а CN используются как compute nodes.

Перед выполнением команды замените placeholders:

PlaceholderОткуда взять
{engine_namespace}Namespace, где operator будет создавать Engine pods, services и PVC.
{selena_namespace}Namespace, где установлены Selena application services: CM, IDE, AI. Обычно это namespace CM/IDE/AI chart-ов.
{registry}Registry/mirror из согласованного deployment profile.
{engine_tag}Версия Selena Engine image из release/deployment profile.
{storage_class}Kubernetes StorageClass, выбранный для Engine PVC.

Если нужен SHARED_NOTHING cluster с BE, не добавляйте be в этот JSON поверх cn. Используйте отдельный BE-пример ниже: в одном spec должен быть либо fe + cn, либо fe + be.

Важно про config: значения из fe.config, cn.config и be.config CM передает в Engine component как есть, построчно в config files нод: fe.config -> fe.conf, cn.config -> cn.conf, be.config -> be.conf. Каждая JSON-пара превращается в строку вида key = value. Поэтому указывайте здесь только реальные Selena Engine config keys для соответствующего компонента. Если key написан с ошибкой или value несовместим с Engine, pod может не стартовать или operation завершится ошибкой.

cat > /tmp/selena-engine-spec.json <<'JSON'
{
"spec": {
"name": "selena-prod",
"namespace": "{engine_namespace}",
"deploymentType": "KUBERNETES",
"clusterMode": "SHARED_DATA",
"fe": {
"replicas": 3,
"image": "{registry}/engine-frontend:{engine_tag}",
"imagePullPolicy": "IfNotPresent",
"command": ["/opt/selena/fe_entrypoint.sh"],
"args": ["$(FE_SERVICE_NAME)"],
"imagePullSecrets": [
{"name": "selena-registry"}
],
"requests": {"cpu": "4", "memory": "16Gi"},
"limits": {"cpu": "8", "memory": "32Gi"},
"config": {
"run_mode": "shared_data",
"authentication_chain": "native",
"meta_dir": "/opt/selena/fe/meta",
"sys_log_dir": "/opt/selena/fe/log",
"sys_log_level": "INFO"
},
"volumes": [
{
"name": "fe-meta",
"mountPath": "/opt/selena/fe/meta",
"size": "100Gi",
"storageClassName": "{storage_class}"
},
{
"name": "fe-log",
"mountPath": "/opt/selena/fe/log",
"size": "100Gi",
"storageClassName": "{storage_class}"
}
],
"env": [
{
"name": "MYSQL_PWD",
"valueFrom": {
"secretKeyRef": {
"name": "selena-engine-admin-sql",
"key": "SELENA_ADMIN_SQL_PASSWORD",
"optional": true
}
}
}
],
"service": {
"type": "ClusterIP"
}
},
"cn": {
"replicas": 3,
"image": "{registry}/engine-compute:{engine_tag}",
"imagePullPolicy": "IfNotPresent",
"command": ["/opt/selena/cn_entrypoint.sh"],
"args": ["$(FE_SERVICE_NAME)"],
"imagePullSecrets": [
{"name": "selena-registry"}
],
"requests": {"cpu": "8", "memory": "32Gi"},
"limits": {"cpu": "16", "memory": "64Gi"},
"config": {
"storage_root_path": "/data/cn1;/data/cn2",
"datacache_enable": "true",
"datacache_mem_size": "10G",
"datacache_disk_size": "80%",
"sys_log_dir": "/opt/selena/cn/log",
"sys_log_level": "INFO"
},
"volumes": [
{
"name": "cn-cache-1",
"mountPath": "/data/cn1",
"size": "500Gi",
"storageClassName": "{storage_class}"
},
{
"name": "cn-cache-2",
"mountPath": "/data/cn2",
"size": "500Gi",
"storageClassName": "{storage_class}"
},
{
"name": "cn-log",
"mountPath": "/opt/selena/cn/log",
"size": "100Gi",
"storageClassName": "{storage_class}"
}
],
"env": [
{
"name": "MYSQL_PWD",
"valueFrom": {
"secretKeyRef": {
"name": "selena-engine-admin-sql",
"key": "SELENA_ADMIN_SQL_PASSWORD",
"optional": true
}
}
}
]
},
"bootstrap": {
"impersonators": [
{
"purpose": "CM_IMPERSONATOR",
"username": "cm_impersonator_all"
},
{
"purpose": "IDE_IMPERSONATOR",
"username": "ide_impersonator_all",
"k8sNamespace": "{selena_namespace}",
"k8sSecretName": "selena-ide-secrets",
"k8sSecretKey": "IDE_SELENA_IMPERSONATOR_PASSWORD"
},
{
"purpose": "AI_IMPERSONATOR",
"username": "ai_impersonator_all",
"k8sNamespace": "{selena_namespace}",
"k8sSecretName": "selena-ai-secrets",
"k8sSecretKey": "MCP_SELENA_IMPERSONATOR_PASSWORD"
}
]
}
}
}
JSON

Как читать и менять этот spec:

JSON pathЗначение в примереМожно менять?Что означает
spec.nameselena-prodДа, до install.Имя Engine cluster. Оно входит в имена Kubernetes resources и Service DNS names. После install меняйте только через delete/recreate.
spec.namespace{engine_namespace}Да, до install.Namespace, где operator создаст FE/CN или FE/BE pods, services и PVC.
spec.deploymentTypeKUBERNETESОбычно нет.Сейчас CM поддерживает Kubernetes/operator deployment backend.
spec.clusterModeSHARED_DATAВыбирается до install.SHARED_DATA означает fe + cn. Для SHARED_NOTHING используйте fe + be. После install mode не меняют на месте.
spec.feobjectОбязателен.FE component: metadata, SQL frontend, MySQL-compatible endpoint и cluster coordination.
spec.fe.replicas3Да, через CM API.Количество FE pods. Для HA используйте 3. Не масштабируйте FE до 0; CM API защищает от такого сценария.
spec.fe.image{registry}/engine-frontend:{engine_tag}Да, для upgrade.Полный image FE. Registry и tag должны соответствовать release profile.
spec.fe.imagePullPolicyIfNotPresentРедко.Kubernetes pull policy. Для immutable release tags обычно достаточно IfNotPresent.
spec.fe.command / spec.fe.args/opt/selena/fe_entrypoint.sh, $(FE_SERVICE_NAME)Не меняйте для Selena images.Selena images используют /opt/selena, а не upstream /opt/starrocks. Явный command защищает от operator defaults, рассчитанных на StarRocks paths. CM может обернуть FE/BE entrypoint в /bin/bash -c ... sleep 5 ... для graceful stop; это ожидаемо.
spec.fe.imagePullSecretsselena-registryДа.Secret для private registry. Secret должен быть создан в {engine_namespace} до install.
spec.fe.requests4 CPU, 16GiДа.Минимально запрашиваемые ресурсы pod-а. Kubernetes scheduler использует их для размещения.
spec.fe.limits8 CPU, 32GiДа.Верхняя граница ресурсов container-а. Подбирайте под sizing и policy заказчика.
spec.fe.config.run_modeshared_dataМенять только вместе с clusterMode.Engine runtime mode. Для SHARED_DATA должен быть shared_data, для SHARED_NOTHING - shared_nothing.
spec.fe.config.authentication_chainnativeНе меняйте.Selena Engine не подключается напрямую к LDAP/AD. Web login идет через Keycloak, direct SQL использует CM-generated CLI secret.
spec.fe.config.meta_dir/opt/selena/fe/metaТолько вместе с volume mount.Каталог FE metadata. Должен совпадать с fe-meta.mountPath.
spec.fe.config.sys_log_dir/opt/selena/fe/logТолько вместе с volume mount.Каталог FE logs. Должен совпадать с fe-log.mountPath.
spec.fe.config.sys_log_levelINFOДа.Уровень логирования FE. Для диагностики временно можно повысить, но не оставляйте verbose logging без необходимости.
spec.fe.volumes[].namefe-meta, fe-logПланируйте до install.Имя volume в Engine component. Должно быть уникальным внутри component.
spec.fe.volumes[].mountPath/opt/selena/fe/...Планируйте до install.Куда PVC монтируется в container. Config paths должны ссылаться на эти же каталоги.
spec.fe.volumes[].size100GiЗависит от StorageClass.Размер PVC. Увеличение после install возможно только если StorageClass разрешает expansion. Уменьшение PVC обычно невозможно.
spec.fe.volumes[].storageClassName{storage_class}Планируйте до install.StorageClass для FE PVC. Выбирайте класс с нужной надежностью, IOPS/throughput и backup policy.
spec.fe.env[].MYSQL_PWDsecret selena-engine-admin-sql/SELENA_ADMIN_SQL_PASSWORDДа, оставьте в spec.Нужен FE/CN entrypoint после /engine/cluster:bootstrap-auth-rbac, когда root/admin SQL password уже установлен. Без этого post-bootstrap scale-up/restart может не зарегистрировать новый pod в FE. Secret создает CM bootstrap.
spec.fe.service.typeClusterIPДа.Kubernetes Service type для FE. ClusterIP оставляет FE внутри cluster; LoadBalancer публикует endpoint наружу, если это разрешено network/security policy.
spec.cnobjectТолько для SHARED_DATA.CN component: compute nodes и локальный cache для shared-data mode. Не используйте одновременно с be.
spec.cn.replicas3Да, через CM API.Количество CN pods. Scale up/down делайте только через CM API, не через kubectl scale.
spec.cn.image{registry}/engine-compute:{engine_tag}Да, для upgrade.Полный image CN. Tag должен быть совместим с FE tag.
spec.cn.command / spec.cn.args/opt/selena/cn_entrypoint.sh, $(FE_SERVICE_NAME)Не меняйте для Selena images.Явно запускает Selena CN entrypoint из /opt/selena, чтобы не зависеть от operator defaults.
spec.cn.requests / spec.cn.limits8/16 CPU, 32/64GiДа.Ресурсы compute pods. Подбирайте под workload и node size.
spec.cn.config.storage_root_path/data/cn1;/data/cn2Только вместе с volumes.Каталоги локального CN cache/storage. Каждый путь должен иметь matching volume mount.
spec.cn.config.datacache_enabletrueДа.Включает local data cache на CN. Для shared-data deployments обычно нужен.
spec.cn.config.datacache_mem_size10GДа.Объем memory cache на CN. Должен соответствовать memory limit.
spec.cn.config.datacache_disk_size80%Да.Доля cache volumes, которую может использовать disk cache.
spec.cn.config.sys_log_dir/opt/selena/cn/logТолько вместе с volume mount.Каталог CN logs.
spec.cn.volumes[]cn-cache-1, cn-cache-2, cn-logПланируйте до install.PVC для CN cache и logs. Cache volumes должны соответствовать storage_root_path.
spec.cn.env[].MYSQL_PWDsecret selena-engine-admin-sql/SELENA_ADMIN_SQL_PASSWORDДа, оставьте в spec.Нужен CN entrypoint для регистрации compute node в FE после auth/RBAC bootstrap и для последующих scale-up/restart.
spec.bootstrap.impersonators[]cm/ide/ai_impersonator_allОбычно не меняйте.Service users, которые CM создаст в Selena после install. Они нужны CM, IDE и AI/MCP для выполнения запросов от имени пользователя.
impersonators[].purposeCM_IMPERSONATOR, IDE_IMPERSONATOR, AI_IMPERSONATORНет.Тип service credential. CM понимает фиксированные purpose names.
impersonators[].username*_impersonator_allОбычно нет.Имя service user в Selena Engine. Если меняете, синхронно обновляйте dependent service config.
impersonators[].k8sNamespace{selena_namespace}Да.Namespace Kubernetes Secret, куда CM запишет generated password для IDE/AI после bootstrap.
impersonators[].k8sSecretNameselena-ide-secrets, selena-ai-secretsДа, если меняете charts.Existing Secret, который читают IDE/AI/MCP pods. Имя должно совпадать с values этих chart-ов.
impersonators[].k8sSecretKeyIDE_SELENA_IMPERSONATOR_PASSWORD, MCP_SELENA_IMPERSONATOR_PASSWORDДа, если меняете charts.Key внутри Secret. Должен совпадать с env var, которую читает соответствующий service.

Пример для SHARED_NOTHING cluster: 3 FE + 3 BE. Используйте его вместо SHARED_DATA примера, если deployment profile выбран без shared storage/S3.

cat > /tmp/selena-engine-spec-shared-nothing.json <<'JSON'
{
"spec": {
"name": "selena-prod",
"namespace": "{engine_namespace}",
"deploymentType": "KUBERNETES",
"clusterMode": "SHARED_NOTHING",
"fe": {
"replicas": 3,
"image": "{registry}/engine-frontend:{engine_tag}",
"imagePullPolicy": "IfNotPresent",
"command": ["/opt/selena/fe_entrypoint.sh"],
"args": ["$(FE_SERVICE_NAME)"],
"imagePullSecrets": [
{"name": "selena-registry"}
],
"requests": {"cpu": "4", "memory": "16Gi"},
"limits": {"cpu": "8", "memory": "32Gi"},
"config": {
"run_mode": "shared_nothing",
"authentication_chain": "native",
"meta_dir": "/opt/selena/fe/meta",
"sys_log_dir": "/opt/selena/fe/log",
"sys_log_level": "INFO"
},
"volumes": [
{
"name": "fe-meta",
"mountPath": "/opt/selena/fe/meta",
"size": "100Gi",
"storageClassName": "{storage_class}"
},
{
"name": "fe-log",
"mountPath": "/opt/selena/fe/log",
"size": "100Gi",
"storageClassName": "{storage_class}"
}
],
"service": {
"type": "ClusterIP"
}
},
"be": {
"replicas": 3,
"image": "{registry}/engine-backend:{engine_tag}",
"imagePullPolicy": "IfNotPresent",
"command": ["/opt/selena/be_entrypoint.sh"],
"args": ["$(FE_SERVICE_NAME)"],
"imagePullSecrets": [
{"name": "selena-registry"}
],
"requests": {"cpu": "8", "memory": "32Gi"},
"limits": {"cpu": "16", "memory": "64Gi"},
"config": {
"storage_root_path": "/data/be1;/data/be2",
"sys_log_dir": "/opt/selena/be/log",
"sys_log_level": "INFO"
},
"volumes": [
{
"name": "be-storage-1",
"mountPath": "/data/be1",
"size": "500Gi",
"storageClassName": "{storage_class}"
},
{
"name": "be-storage-2",
"mountPath": "/data/be2",
"size": "500Gi",
"storageClassName": "{storage_class}"
},
{
"name": "be-log",
"mountPath": "/opt/selena/be/log",
"size": "100Gi",
"storageClassName": "{storage_class}"
}
]
},
"bootstrap": {
"impersonators": [
{
"purpose": "CM_IMPERSONATOR",
"username": "cm_impersonator_all"
},
{
"purpose": "IDE_IMPERSONATOR",
"username": "ide_impersonator_all",
"k8sNamespace": "{selena_namespace}",
"k8sSecretName": "selena-ide-secrets",
"k8sSecretKey": "IDE_SELENA_IMPERSONATOR_PASSWORD"
},
{
"purpose": "AI_IMPERSONATOR",
"username": "ai_impersonator_all",
"k8sNamespace": "{selena_namespace}",
"k8sSecretName": "selena-ai-secrets",
"k8sSecretKey": "MCP_SELENA_IMPERSONATOR_PASSWORD"
}
]
}
}
}
JSON

Поля BE:

JSON pathЗначение в примереЧто означает
spec.beobjectBE component используется только в SHARED_NOTHING. В таком spec не должно быть cn.
spec.be.image{registry}/engine-backend:{engine_tag}Полный image BE. Tag должен быть совместим с FE tag.
spec.be.command / spec.be.args/opt/selena/be_entrypoint.sh, $(FE_SERVICE_NAME)Явно запускает Selena BE entrypoint из /opt/selena, чтобы не зависеть от operator defaults.
spec.be.config.storage_root_path/data/be1;/data/be2Каталоги постоянного BE storage. Каждый путь должен иметь отдельный matching volume mount.
spec.be.volumes[].mountPath/data/be1, /data/be2, /opt/selena/be/logPersistent volumes для BE данных и logs.

Если нужен внешний direct SQL endpoint сразу через FE Service, задайте в fe.service тип LoadBalancer или используйте approved TCP Ingress/Gateway. Для production ограничьте source ranges firewall/network policy.

3. Сохранить spec в CM​

Если вы выбрали SHARED_DATA, дальше используйте /tmp/selena-engine-spec.json. Если выбрали SHARED_NOTHING, дальше используйте /tmp/selena-engine-spec-shared-nothing.json.

В командах ниже {engine_spec_file} - это выбранный файл spec. Перед отправкой проверьте, что это именно тот файл, который вы хотели установить:

jq empty {engine_spec_file}
rg -n '\{[a-zA-Z0-9_]+\}' {engine_spec_file}

jq empty должен завершиться без ошибки. rg не должен найти незамененные placeholders.

curl -fsS -X PUT {cm_url}/engine/cluster/config \
-H 'Authorization: Bearer {cm_admin_access_token}' \
-H 'Content-Type: application/json' \
--data-binary @{engine_spec_file} \
| jq

Проверить сохраненный spec:

curl -fsS {cm_url}/engine/cluster/config \
-H 'Authorization: Bearer {cm_admin_access_token}' \
| jq

До установки ожидаемый status: CONFIG_SAVED.

4. Запустить install operation​

curl -fsS -X POST {cm_url}/engine/cluster:install \
-H 'Authorization: Bearer {cm_admin_access_token}' \
| jq

Скопируйте .operationId из ответа. Дальше это {operation_id}.

Проверить operation:

curl -fsS {cm_url}/engine/cluster/operations/{operation_id} \
-H 'Authorization: Bearer {cm_admin_access_token}' \
| jq

curl -fsS {cm_url}/engine/cluster/operations/{operation_id}/events \
-H 'Authorization: Bearer {cm_admin_access_token}' \
| jq

Проверить Kubernetes:

kubectl -n {engine_namespace} get pods,svc,pvc -o wide
kubectl -n {engine_namespace} get events --sort-by=.lastTimestamp

5. Дождаться реальной готовности Engine​

Operation status APPLIED означает, что CM отправил desired state в Kubernetes/operator. Это не то же самое, что готовые FE/CN pods.

Проверяйте CM status до READY:

curl -fsS '{cm_url}/engine/cluster/status?refresh=true' \
-H 'Authorization: Bearer {cm_admin_access_token}' \
| jq

И Kubernetes:

kubectl -n {engine_namespace} get statefulsets,pods -o wide
kubectl get pods -A --field-selector=status.phase!=Running,status.phase!=Succeeded

Критерий готовности:

  • CM cluster status READY;
  • FE StatefulSet ready;
  • CN или BE StatefulSet ready;
  • нет неожиданных failed/pending pods.

6. Выполнить auth/RBAC bootstrap​

Install не создает runtime credentials для приложений. Bootstrap запускается отдельно, только после READY.

Если в Engine spec есть IDE_IMPERSONATOR или AI_IMPERSONATOR, Secrets для IDE/AI должны уже существовать, потому что CM записывает generated passwords в эти existing Secrets:

kubectl -n {selena_namespace} get secret selena-ide-secrets selena-ai-secrets
curl -fsS -X POST {cm_url}/engine/cluster:bootstrap-auth-rbac \
-H 'Authorization: Bearer {cm_admin_access_token}' \
| jq

Скопируйте .operationId из ответа. Дальше это {bootstrap_operation_id}.

Проверить bootstrap operation:

curl -fsS {cm_url}/engine/cluster/operations/{bootstrap_operation_id} \
-H 'Authorization: Bearer {cm_admin_access_token}' \
| jq

curl -fsS {cm_url}/engine/cluster/operations/{bootstrap_operation_id}/events \
-H 'Authorization: Bearer {cm_admin_access_token}' \
| jq

Проверить, что CM записал service passwords в Secrets:

curl -fsS {cm_url}/engine/cluster/impersonators \
-H 'Authorization: Bearer {cm_admin_access_token}' \
| jq

kubectl -n {selena_namespace} get secret selena-ide-secrets \
-o jsonpath='{.data.IDE_SELENA_IMPERSONATOR_PASSWORD}' | wc -c

kubectl -n {selena_namespace} get secret selena-ai-secrets \
-o jsonpath='{.data.MCP_SELENA_IMPERSONATOR_PASSWORD}' | wc -c

Ожидаемо: wc -c больше 0.

Теперь можно устанавливать IDE, AI backend/frontend и MCP. Это описано в IDE, AI/MCP, RBAC, пользователи и direct SQL.

7. FE MySQL endpoint для direct SQL​

Если пользователи будут подключаться через DBeaver, IntelliJ IDEA Database Tools или MySQL CLI, опубликуйте FE port 9030 approved способом: LoadBalancer, TCP Ingress/Gateway, VPN-only address или другой customer network pattern.

Проверить Service:

kubectl -n {engine_namespace} get svc -o wide

Admin smoke test:

mysql --protocol=TCP \
-h {selena_fe_mysql_host} \
-P 9030 \
-u root \
-e "SHOW USERS; SHOW ROLES;"

Пользовательские direct SQL подключения не выполняются под root; для них создается отдельный CLI secret через CM API. Это сделано намеренно: LDAP/Keycloak password остается web/identity credential, а MySQL/JDBC protocol получает отдельный пароль для database-доступа, который можно независимо сбросить, отозвать и не хранить в корпоративном password flow. С точки зрения безопасности не рекомендуется использовать LDAP/Keycloak password как пароль для MySQL/JDBC clients: такие clients часто сохраняют password локально, не понимают SSO/MFA policies и не должны получать основной identity password пользователя.

Пользователь получает access token через обычный CM login:

curl -fsS -X POST {cm_url}/auth/login \
-H 'Content-Type: application/json' \
-d '{"username":"{username}","password":"{web_password}"}' \
| jq

Скопируйте .accessToken из ответа. Дальше это {user_access_token}. Затем пользователь сбрасывает CLI secret:

curl -fsS -X POST {cm_url}/me/cli-secret:reset \
-H 'Authorization: Bearer {user_access_token}' \
| jq

Скопируйте .cliSecret из ответа. Значение показывается только один раз; если secret потерян, выполните reset снова. Подробный direct SQL checklist описан в IDE, AI/MCP, RBAC, пользователи и direct SQL.

8. Storage volume для shared-data​

Для shared-data clusters обычный CREATE TABLE требует default storage volume. Если используется external S3, создайте bucket и access key вне Selena. Если используется MinIO в Kubernetes, убедитесь, что application user создан в MinIO, а не только записан в Kubernetes Secret.

Пример создания MinIO user:

kubectl -n {minio_namespace} exec {minio_pod_name} -c minio -- \
mc alias set local http://localhost:9000 {minio_root_user} {minio_root_password}

kubectl -n {minio_namespace} exec {minio_pod_name} -c minio -- \
mc admin user add local {s3_access_key} {s3_secret_key}

kubectl -n {minio_namespace} exec {minio_pod_name} -c minio -- \
mc admin policy attach local readwrite --user {s3_access_key}

kubectl -n {minio_namespace} exec {minio_pod_name} -c minio -- \
mc mb -p local/{bucket_name}

Создать default storage volume:

mysql --protocol=TCP \
-h {selena_fe_mysql_host} \
-P 9030 \
-u root <<'SQL'
CREATE STORAGE VOLUME IF NOT EXISTS {storage_volume_name}
TYPE = S3
LOCATIONS = ("s3://{bucket_name}/{bucket_prefix}/")
PROPERTIES
(
"enabled" = "true",
"aws.s3.region" = "{s3_region}",
"aws.s3.endpoint" = "{s3_endpoint}",
"aws.s3.use_aws_sdk_default_behavior" = "false",
"aws.s3.use_instance_profile" = "false",
"aws.s3.access_key" = "{s3_access_key}",
"aws.s3.secret_key" = "{s3_secret_key}",
"aws.s3.enable_ssl" = "false",
"aws.s3.enable_path_style_access" = "true"
);

SET {storage_volume_name} AS DEFAULT STORAGE VOLUME;
SHOW STORAGE VOLUMES;
SQL

Как читать и менять SQL:

Строка / параметрЧто означаетЧто менять
mysql --protocol=TCPПодключение к FE по MySQL-compatible protocol.Оставьте TCP, чтобы client не пытался использовать local socket.
-h {selena_fe_mysql_host}Host/IP опубликованного FE MySQL endpoint.Возьмите из FE Service, LoadBalancer, Ingress/Gateway или DNS-записи.
-P 9030MySQL port FE.Меняйте только если в Engine/Service явно выбран другой external port.
-u rootAdmin-подключение для первичной настройки storage volume.Используйте только для admin setup. Пользовательские подключения идут через CLI secret, не под root.
CREATE STORAGE VOLUME IF NOT EXISTS {storage_volume_name}Создает named storage volume в Selena, если его еще нет.Замените {storage_volume_name} на понятное имя, например default_s3_volume. Используйте lowercase letters, digits и underscores.
TYPE = S3Тип backend storage. Для S3-compatible storage, включая MinIO, используется S3.Оставьте S3, если storage совместим с S3 API.
LOCATIONS = ("s3://{bucket_name}/{bucket_prefix}/")Bucket и prefix, куда Selena будет писать данные.{bucket_name} должен существовать. {bucket_prefix} можно выбрать под окружение, например prod/warehouse; не начинайте prefix с /.
"enabled" = "true"Включает volume для использования.Обычно оставьте true.
"aws.s3.region" = "{s3_region}"Region S3 endpoint.Для AWS укажите реальный region, например eu-central-1. Для MinIO часто используют условное значение вроде us-east-1, если другого требования нет.
"aws.s3.endpoint" = "{s3_endpoint}"Endpoint S3 API.Для internal MinIO это обычно http://minio.{minio_namespace}.svc.cluster.local:80. Для external S3 используйте endpoint, который доступен FE/CN pods.
"aws.s3.use_aws_sdk_default_behavior" = "false"Selena не берет credentials из AWS SDK default chain, а использует явно заданные properties ниже.Оставьте false, если задаете access_key и secret_key в SQL.
"aws.s3.use_instance_profile" = "false"Selena не использует cloud instance profile/managed identity.Оставьте false, если не согласован отдельный cloud-native identity flow.
"aws.s3.access_key" = "{s3_access_key}"Access key S3/MinIO user-а.Используйте application user с минимально нужными правами на bucket/prefix, не root/admin MinIO user.
"aws.s3.secret_key" = "{s3_secret_key}"Secret key S3/MinIO user-а.Не сохраняйте это значение в Git. Передавайте его только в защищенном admin runbook/secret process.
"aws.s3.enable_ssl" = "false"Использовать ли HTTPS/TLS для S3 endpoint.Для production external S3 обычно true. Для internal demo MinIO по HTTP может быть false.
"aws.s3.enable_path_style_access" = "true"Использовать path-style URL, где bucket идет в path, а не в hostname.Для MinIO обычно true. Для AWS S3 можно использовать customer/platform recommendation.
SET {storage_volume_name} AS DEFAULT STORAGE VOLUMEДелает volume default для обычного CREATE TABLE, если table не указала storage явно.Имя должно совпадать с volume, созданным выше.
SHOW STORAGE VOLUMESПроверка, что volume создан и виден Selena.Оставьте как verification step.

Для internal MinIO endpoint обычно используется:

http://minio.{minio_namespace}.svc.cluster.local:80

Проверка таблицы:

mysql --protocol=TCP \
-h {selena_fe_mysql_host} \
-P 9030 \
-u root \
-e "CREATE DATABASE IF NOT EXISTS demo_storage; CREATE TABLE IF NOT EXISTS demo_storage.t1 (id INT); INSERT INTO demo_storage.t1 VALUES (1); SELECT * FROM demo_storage.t1;"

9. Engine operations через CM API​

CM API endpoints для статуса и event log:

EndpointКогда вызыватьЧто смотреть в ответе
GET {cm_url}/engine/cluster/status?refresh=trueПосле install/apply/bootstrap/scale/restart и при любой диагностике.status, lastApplyError, FE/BE/CN component readiness, FE service, lastOperationId.
GET {cm_url}/engine/cluster/operations/{operation_id}Когда operation только что создана или status вернул lastOperationId.Operation status, operationType, timestamps, affected components, error message.
GET {cm_url}/engine/cluster/operations/{operation_id}/eventsДля подробного event log операции.Append-only events: step name, level, message, timestamp. Это основной лог прогресса CM operation.

Проверить текущий cluster status:

curl -fsS '{cm_url}/engine/cluster/status?refresh=true' \
-H 'Authorization: Bearer {cm_admin_access_token}' \
| jq

Проверить operation status:

curl -fsS {cm_url}/engine/cluster/operations/{operation_id} \
-H 'Authorization: Bearer {cm_admin_access_token}' \
| jq

Получить operation event log:

curl -fsS {cm_url}/engine/cluster/operations/{operation_id}/events \
-H 'Authorization: Bearer {cm_admin_access_token}' \
| jq

Scale CN:

curl -fsS -X POST {cm_url}/engine/cluster/components/cn:scale \
-H 'Authorization: Bearer {cm_admin_access_token}' \
-H 'Content-Type: application/json' \
-d '{"replicas":2}' \
| jq

Scale FE:

curl -fsS -X POST {cm_url}/engine/cluster/components/fe:scale \
-H 'Authorization: Bearer {cm_admin_access_token}' \
-H 'Content-Type: application/json' \
-d '{"replicas":3}' \
| jq

Restart:

curl -fsS -X POST {cm_url}/engine/cluster:restart \
-H 'Authorization: Bearer {cm_admin_access_token}' \
| jq

После каждой operation проверяйте не только operation status, но и реальный cluster status:

curl -fsS '{cm_url}/engine/cluster/status?refresh=true' \
-H 'Authorization: Bearer {cm_admin_access_token}' \
| jq