Netpulse_SasS/docker-compose.yml
byrsapty 4d1fd40e91
Some checks are pending
CI / web (push) Waiting to run
CI / server (push) Waiting to run
CI / agent (push) Waiting to run
Режим NOC TV: дашборд на екрані в диспетчерській без входу
Телевізор нікуди не залогиниш — зранку на стіні висітиме форма входу
замість карти мережі. Тому /tv/<токен> розгалужується до перевірки
сесії, а доступ дає токен у посиланні.

Публічний зріз навмисно вузький: розкладка, алерти, хости й метрики
ЛИШЕ тих хостів, які показані на цьому дашборді. Ширший доступ був би
простішим у коді й перетворив би забутий лінк на ключ до кабінету.

Плитки ті самі, що в кабінеті: джерело даних підмінюється контекстом.

Дорогою знайдено дві помилки. Вбудовані icmp-тригери мали умову у
формі, якої движок не розуміє, і мовчали, засипаючи журнал помилками —
виправлено міграцією 0026 і в редакторі. База стенда виявилась у
SQL_ASCII: тепер міграція відмовляється накочуватись на не-UTF8, а
compose задає кодування явно.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-08-25 15:41:22 +03:00

190 lines
7.5 KiB
YAML
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Повний стек NetPulse: БД, кеш, міграції, API з інтерфейсом, колектор
# зондів і зворотний проксі з автоматичним TLS.
#
# Швидкий старт:
# cp deploy/.env.example .env # і заповнити секрети
# docker compose up -d
# docker compose run --rm api netpulse-user -tenant default -login admin -role owner
#
# Тільки стенд для розробки (БД і кеш, решта — з go run):
# docker compose up -d db cache
name: netpulse
x-server-env: &server-env
NETPULSE_DSN: postgres://netpulse:${POSTGRES_PASSWORD:?потрібен POSTGRES_PASSWORD}@db:5432/netpulse?sslmode=disable
NETPULSE_DEK: ${NETPULSE_DEK:?потрібен NETPULSE_DEK — див. deploy/README.md}
NETPULSE_LOG_LEVEL: ${NETPULSE_LOG_LEVEL:-info}
TZ: ${TZ:-Europe/Kyiv}
services:
db:
image: timescale/timescaledb:2.17.2-pg16
environment:
POSTGRES_USER: netpulse
POSTGRES_PASSWORD: ${POSTGRES_PASSWORD:?потрібен POSTGRES_PASSWORD}
POSTGRES_DB: netpulse
TIMESCALEDB_TELEMETRY: "off"
# Без цього initdb бере кодування з локалі середовища й цілком
# може створити базу як SQL_ASCII. Тексти при цьому виглядають
# цілими, а ламається інше: jsonb із екранованим не-ASCII не
# вставляється, а lower() і сортування працюють як над латиницею.
# Виправити можна лише перестворенням бази, тож задаємо одразу.
POSTGRES_INITDB_ARGS: "--encoding=UTF8 --locale=C.UTF-8"
command:
- postgres
- -c
- shared_preload_libraries=timescaledb
- -c
- max_connections=200
- -c
- shared_buffers=${PG_SHARED_BUFFERS:-512MB}
- -c
- timescaledb.max_background_workers=8
volumes:
- db-data:/var/lib/postgresql/data
healthcheck:
test: ["CMD-SHELL", "pg_isready -U netpulse -d netpulse"]
interval: 5s
timeout: 5s
retries: 20
restart: unless-stopped
cache:
image: docker.dragonflydb.io/dragonflydb/dragonfly:v1.25.5
ulimits:
memlock: -1
volumes:
- cache-data:/data
restart: unless-stopped
# Міграції окремою службою, а не на старті API.
#
# API запускається в кількох примірниках, і накочування схеми зі старту
# означало б гонку між ними. Тут же — один запуск, який мусить
# завершитись успіхом, перш ніж піднімуться API й колектор.
migrate:
build: &server-build
context: .
dockerfile: deploy/Dockerfile.server
args:
VERSION: ${NETPULSE_VERSION:-dev}
COMMIT: ${NETPULSE_COMMIT:-none}
image: netpulse/server:${NETPULSE_VERSION:-dev}
entrypoint: ["netpulse-migrate"]
environment: *server-env
depends_on:
db:
condition: service_healthy
restart: "no"
api:
build: *server-build
image: netpulse/server:${NETPULSE_VERSION:-dev}
entrypoint: ["netpulse-api"]
command:
- -listen=:8080
- -alert-interval=${NETPULSE_ALERT_INTERVAL:-30s}
environment:
<<: *server-env
NETPULSE_JWT_SECRET: ${NETPULSE_JWT_SECRET:?потрібен NETPULSE_JWT_SECRET — не менше 32 байтів}
# Історія конфігів у Git. Спільний том для API й колектора:
# колектор туди пише під час бекапу, API звідти читає для порівняння
# версій. Різні томи означали б, що половина історії видна одному
# процесу, а половина другому.
volumes:
- git-data:/var/lib/netpulse
depends_on:
migrate:
condition: service_completed_successfully
cache:
condition: service_started
healthcheck:
test: ["CMD", "wget", "-qO-", "http://127.0.0.1:8080/healthz"]
interval: 10s
timeout: 3s
retries: 6
start_period: 15s
restart: unless-stopped
# Колектор зондів. TLS знімає Caddy, всередині мережі — h2c, тому
# -insecure. Порт назовні сам не публікує: до нього ходять через
# проксі, який має справжній сертифікат.
collector:
build: *server-build
image: netpulse/server:${NETPULSE_VERSION:-dev}
entrypoint: ["netpulse-server"]
command:
- -listen=:9443
- -insecure
environment: *server-env
# Історія конфігів у Git. Спільний том для API й колектора:
# колектор туди пише під час бекапу, API звідти читає для порівняння
# версій. Різні томи означали б, що половина історії видна одному
# процесу, а половина другому.
volumes:
- git-data:/var/lib/netpulse
depends_on:
migrate:
condition: service_completed_successfully
restart: unless-stopped
proxy:
image: caddy:2.8-alpine
environment:
NETPULSE_DOMAIN: ${NETPULSE_DOMAIN:?потрібен NETPULSE_DOMAIN}
# Порожній рядок Caddy не приймає: директива email без значення —
# помилка розбору, і проксі не підніметься взагалі. Тому підстановка
# спрацьовує і на незадану змінну, і на задану порожньою.
ACME_EMAIL: ${ACME_EMAIL:-admin@${NETPULSE_DOMAIN}}
volumes:
- ./deploy/Caddyfile:/etc/caddy/Caddyfile:ro
- caddy-data:/data
- caddy-config:/config
ports:
- "80:80"
- "443:443"
# Окремий порт для зондів: вони говорять gRPC, а не HTTP, і
# ділити з ним 443 означало б розрізняти протоколи за шляхом —
# зайва крихкість там, де порт коштує нічого.
- "9443:9443"
depends_on:
- api
- collector
restart: unless-stopped
# Зонд на тому ж хості, що й сервер: базовий моніторинг самої
# інсталяції. Профіль, а не звичайна служба: у типовому розгортанні
# зонди стоять у мережах клієнтів, а не поруч із сервером.
agent:
build:
context: .
dockerfile: deploy/Dockerfile.agent
args:
VERSION: ${NETPULSE_VERSION:-dev}
COMMIT: ${NETPULSE_COMMIT:-none}
image: netpulse/agent:${NETPULSE_VERSION:-dev}
profiles: ["agent"]
command:
- -server=collector:9443
- -insecure
- -modules=icmp,snmp,topology,ncm
environment:
NETPULSE_ENROLL: ${NETPULSE_ENROLL:-}
NETPULSE_NAME: ${NETPULSE_AGENT_NAME:-локальний зонд}
TZ: ${TZ:-Europe/Kyiv}
cap_add:
- NET_RAW
volumes:
- agent-identity:/var/lib/netpulse
depends_on:
- collector
restart: unless-stopped
volumes:
db-data:
git-data:
cache-data:
caddy-data:
caddy-config:
agent-identity: