From a7cff141f75fd9d605e4bc6eaeae0552b2bc7636 Mon Sep 17 00:00:00 2001 From: Dusan Vojacek Date: Sun, 5 Apr 2026 02:57:43 +0200 Subject: [PATCH] fix flyway --- ...V031__telemetry_views_security_invoker.sql | 9 +++++++++ db/views/R__vw_latest_telemetry.sql | 13 +++++++++--- db/views/R__z_postgrest_ems_anon_grants.sql | 20 +++++-------------- deploy/deploy.sh | 6 ++++++ 4 files changed, 30 insertions(+), 18 deletions(-) create mode 100644 db/migration/V031__telemetry_views_security_invoker.sql diff --git a/db/migration/V031__telemetry_views_security_invoker.sql b/db/migration/V031__telemetry_views_security_invoker.sql new file mode 100644 index 0000000..30df220 --- /dev/null +++ b/db/migration/V031__telemetry_views_security_invoker.sql @@ -0,0 +1,9 @@ +-- vw nad Timescale continuous aggregate: ems_anon potřebuje jen SELECT na view, +-- ne na telemetry_inverter_hourly (vyhneme se GRANTům na CA/hypertably v repeatable). +-- Viz R__vw_latest_telemetry (vw_latest_*) + R__z_postgrest_ems_anon_grants. + +ALTER VIEW ems.vw_telemetry_hourly_7d SET (security_invoker = false); + +COMMENT ON VIEW ems.vw_telemetry_hourly_7d IS +'Hodinová telemetrie střídače za 7 dní (zdroj: continuous aggregate telemetry_inverter_hourly). +security_invoker=false: čtení přes PostgREST role ems_anon bez GRANT na podkladový CA.'; diff --git a/db/views/R__vw_latest_telemetry.sql b/db/views/R__vw_latest_telemetry.sql index 6461336..eae3992 100644 --- a/db/views/R__vw_latest_telemetry.sql +++ b/db/views/R__vw_latest_telemetry.sql @@ -4,7 +4,10 @@ -- Repeatable migration -- ============================================================= -CREATE OR REPLACE VIEW ems.vw_latest_inverter AS +-- security_invoker = false: oprávnění na podkladové hypertably nemusí mít ems_anon (PostgREST). +CREATE OR REPLACE VIEW ems.vw_latest_inverter +WITH (security_invoker = false) +AS SELECT DISTINCT ON (t.inverter_id) t.site_id, t.inverter_id, @@ -34,7 +37,9 @@ COMMENT ON VIEW ems.vw_latest_inverter IS -- ------------------------------------------------------------ -CREATE OR REPLACE VIEW ems.vw_latest_ev_charger AS +CREATE OR REPLACE VIEW ems.vw_latest_ev_charger +WITH (security_invoker = false) +AS SELECT DISTINCT ON (t.charger_id, t.connector_id) t.site_id, t.charger_id, @@ -57,7 +62,9 @@ COMMENT ON VIEW ems.vw_latest_ev_charger IS -- ------------------------------------------------------------ -CREATE OR REPLACE VIEW ems.vw_latest_heat_pump AS +CREATE OR REPLACE VIEW ems.vw_latest_heat_pump +WITH (security_invoker = false) +AS SELECT DISTINCT ON (t.heat_pump_id) t.site_id, t.heat_pump_id, diff --git a/db/views/R__z_postgrest_ems_anon_grants.sql b/db/views/R__z_postgrest_ems_anon_grants.sql index 794847a..3400dbe 100644 --- a/db/views/R__z_postgrest_ems_anon_grants.sql +++ b/db/views/R__z_postgrest_ems_anon_grants.sql @@ -2,6 +2,11 @@ -- -- Po importu DB dumpu bez cluster rolí často chybí samotná role; V009 pak na cílovém -- clusteru neběžela. Tento blok je idempotentní a při změně souboru znovu spáruje granty. +-- +-- GRANT SELECT na Timescale hypertably / continuous aggregate v repeatable NEpatří: při +-- opakovaném běhu Flyway Timescale propaguje oprávnění na chunky; u nekonzistentního +-- katalogu (_hyper_* „chunk not found“) migrace spadne. Oprávnění na hypertabulky zůstávají +-- ve verzovaných migracích (V009, …); PostgREST čte přes views s security_invoker = false. DO $$ BEGIN IF NOT EXISTS (SELECT FROM pg_roles WHERE rolname = 'ems_anon') THEN @@ -11,19 +16,6 @@ END $$; GRANT USAGE ON SCHEMA ems TO ems_anon; --- Tabulky (stejné jako V009 + V020; idempotentní – bezpečné po importu DB bez rolí) -GRANT SELECT ON ems.market_interval_price TO ems_anon; -GRANT SELECT ON ems.planning_run TO ems_anon; -GRANT SELECT ON ems.planning_interval TO ems_anon; -GRANT SELECT ON ems.forecast_pv_interval TO ems_anon; -GRANT SELECT ON ems.forecast_pv_run TO ems_anon; -GRANT SELECT ON ems.operating_mode_def TO ems_anon; -GRANT SELECT ON ems.site_operating_mode TO ems_anon; -GRANT SELECT ON ems.site_operating_mode_log TO ems_anon; -GRANT SELECT ON ems.ev_session TO ems_anon; -GRANT SELECT ON ems.asset_vehicle TO ems_anon; -GRANT SELECT ON ems.ev_arrival_stats TO ems_anon; - GRANT SELECT ON ems.vw_site_status TO ems_anon; GRANT SELECT ON ems.vw_site_effective_price TO ems_anon; GRANT SELECT ON ems.vw_latest_inverter TO ems_anon; @@ -33,9 +25,7 @@ GRANT SELECT ON ems.vw_audit_daily TO ems_anon; GRANT SELECT ON ems.vw_audit_weekly TO ems_anon; GRANT SELECT ON ems.vw_mode_log_recent TO ems_anon; GRANT SELECT ON ems.vw_operating_mode TO ems_anon; -GRANT SELECT ON ems.telemetry_inverter_hourly TO ems_anon; GRANT SELECT ON ems.vw_telemetry_hourly_7d TO ems_anon; -GRANT SELECT ON ems.telemetry_heat_pump TO ems_anon; GRANT SELECT ON ems.forecast_accuracy TO ems_anon; GRANT SELECT ON ems.vw_forecast_accuracy_by_lead_time TO ems_anon; GRANT SELECT ON ems.vw_forecast_accuracy_daily TO ems_anon; diff --git a/deploy/deploy.sh b/deploy/deploy.sh index 8521cb5..537f86f 100755 --- a/deploy/deploy.sh +++ b/deploy/deploy.sh @@ -50,6 +50,12 @@ install -m 0644 "$COMPOSE_SRC" "$COMPOSE_DST" log "docker compose config (validate)" docker compose -f "$COMPOSE_DST" --env-file "$ENV_FILE" config >/dev/null +# Vždy spustit migrace z aktuálního ./app/db (mount ve flyway službě). Čisté `up -d` často +# znovu nespustí jednorázový kontejner flyway, takže změny jen v R__/*.sql by se neaplikovaly. +# Při chybě je v logu jobu celý Flyway výstup (konkrétní SQL / řádek). +log "Flyway migrate (docker compose run --rm flyway)" +docker compose -f "$COMPOSE_DST" --env-file "$ENV_FILE" run --rm flyway migrate + log "docker compose build" docker compose -f "$COMPOSE_DST" --env-file "$ENV_FILE" build