Netpulse_SasS/server/migrations/0023_agent_enrollment.sql
byrsapty 205dd5e079 Пакування: runner міграцій і вшитий у бінарник фронтенд
netpulse-migrate замість PowerShell-скрипта: у контейнері немає ані
psql, ані PowerShell, а тягнути клієнт Postgres в образ заради одного
запуску — це половина дистрибутива на порожньому місці.

Міграції вшиті через embed і переїхали в server/migrations: embed не
бачить нічого за межами кореня свого модуля, а міграції поруч із
бінарником, який їх накочує, не можуть розійтися версіями.

Накочування під advisory-блокуванням: два інстанси при rolling update
інакше застосували б ту саму міграцію двічі. Кожен файл в одній
транзакції разом із записом у schema_migrations; виняток — continuous
aggregates, які TimescaleDB забороняє в транзакції. Змінена вже
застосована міграція зупиняє запуск: у різних інсталяціях інакше
опиниться різна схема під одним номером.

Перевірено на чистій базі: 23 міграції, 101 таблиця, повторний запуск
каже «схема актуальна».

Веб віддає сам API через embed: на self-hosted це прибирає з інструкції
встановлення цілий компонент. Три політики кешування — назавжди для
assets із хешем у імені, ніколи для index.html, коротко для решти.

Знайдено живим прогоном: невідомий шлях під /api/ віддавав 200 з
index.html, і клієнт падав на розборі HTML як JSON замість чесного 404.

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

52 lines
3.1 KiB
SQL
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 :: 0023_agent_enrollment.sql
-- Реєстрація зонда одноразовим токеном.
--
-- Досі зонд заводився INSERT-ом у БД, а токен вписувався в командний
-- рядок руками. На стенді це прийнятно; у клієнта — ні: людина, яка
-- ставить агента, не має доступу до бази й не повинна його мати.
--
-- Схема така: адміністратор створює запрошення в UI, копіює команду
-- встановлення, агент обмінює одноразовий токен на постійний. Токен
-- згорає при першому використанні.
-- =====================================================================
CREATE TABLE core.agent_enrollments (
id uuid PRIMARY KEY DEFAULT core.new_id(),
tenant_id uuid NOT NULL REFERENCES core.tenants(id) ON DELETE CASCADE,
-- sha256 токена. Сам токен існує рівно один раз — у відповіді на
-- створення. Зберігати його означало б тримати в базі чинний доступ.
token_hash bytea NOT NULL UNIQUE,
-- Перші символи для впізнавання в списку: «np_enr_a1b2…».
prefix text NOT NULL,
-- Підказка імені майбутнього зонда. Саме підказка: остаточне ім'я
-- може прийти від самого агента або отримати суфікс при збігу.
name_hint text,
site_id uuid REFERENCES inv.sites(id) ON DELETE SET NULL,
-- Модулі, з якими зонд стартує. Далі керуються з UI.
modules core.slug[] NOT NULL DEFAULT '{icmp}',
expires_at timestamptz NOT NULL,
used_at timestamptz,
used_by uuid REFERENCES core.agents(id) ON DELETE SET NULL,
created_by uuid REFERENCES core.users(id) ON DELETE SET NULL,
created_at timestamptz NOT NULL DEFAULT now()
);
CREATE INDEX agent_enrollments_tenant_idx ON core.agent_enrollments (tenant_id)
WHERE used_at IS NULL;
ALTER TABLE core.agent_enrollments ENABLE ROW LEVEL SECURITY;
ALTER TABLE core.agent_enrollments FORCE ROW LEVEL SECURITY;
CREATE POLICY tenant_isolation ON core.agent_enrollments
USING (tenant_id = core.current_tenant())
WITH CHECK (tenant_id = core.current_tenant());
GRANT SELECT, INSERT, UPDATE, DELETE ON core.agent_enrollments
TO netpulse_app, netpulse_worker;
-- Звідки взявся зонд: заведений руками чи прийшов сам по запрошенню.
-- Потрібно журналу аудиту й тому, хто через рік питає «а це що за
-- агент і хто його ставив».
ALTER TABLE core.agents
ADD COLUMN enrolled_at timestamptz,
ADD COLUMN enrolled_by uuid REFERENCES core.users(id) ON DELETE SET NULL;