feat(notifications): backfill default rules for pre-existing tenants #117

Merged
vas2000-work merged 2 commits from feat/notifications-seed-existing-tenants into main 2026-06-05 23:10:09 +02:00
Owner

New tenants get their in-app worker notification rules seeded by TenantService::copy_default_config (appointment.reminder, sla.at_risk, sla.breached, copied per-tenant from the default tenant). Tenants created before that path lacked the rules, so notifications did not auto-deliver for them.

Fix

Migration 030_backfill_notification_rules.sql: a verbatim, generalized mirror of copy_default_config (same event filter, same columns, same template_id re-link by (event_type, channel_type)) run for every tenant except the default source. Idempotent via WHERE NOT EXISTS on both the template and rule inserts, so re-running is a no-op and tenants already holding the rules are untouched.

Test: tests/notifications_backfill.rs (#[sqlx::test]) - a bare tenant ends with exactly the 3 worker templates+rules, each linked to its own tenant template (no cross-tenant leak), and a second run does not duplicate.

Confirm

Scope intentionally matches new tenants: only the 3 in-app worker rules, NOT the auth./ticket. transactional email templates from migration 021 (those stay on the migration seed / per-tenant CRUD for new tenants too). Needs a gate run (just check + the test with the tests/ mount).

New tenants get their in-app worker notification rules seeded by `TenantService::copy_default_config` (appointment.reminder, sla.at_risk, sla.breached, copied per-tenant from the default tenant). Tenants created before that path lacked the rules, so notifications did not auto-deliver for them. ## Fix Migration `030_backfill_notification_rules.sql`: a verbatim, generalized mirror of `copy_default_config` (same event filter, same columns, same template_id re-link by (event_type, channel_type)) run for every tenant except the default source. Idempotent via `WHERE NOT EXISTS` on both the template and rule inserts, so re-running is a no-op and tenants already holding the rules are untouched. Test: `tests/notifications_backfill.rs` (#[sqlx::test]) - a bare tenant ends with exactly the 3 worker templates+rules, each linked to its own tenant template (no cross-tenant leak), and a second run does not duplicate. ## Confirm Scope intentionally matches new tenants: only the 3 in-app worker rules, NOT the auth.*/ticket.* transactional email templates from migration 021 (those stay on the migration seed / per-tenant CRUD for new tenants too). Needs a gate run (`just check` + the test with the tests/ mount).
feat(notifications): backfill default worker rules for existing tenants
Some checks failed
Check / fmt + clippy + compile + tests (pull_request) Failing after 11s
E2E (staging) / Playwright against staging (pull_request) Successful in 22s
Build OCI container / Build and push mokosh-api image (push) Successful in 7m6s
d03ff7f679
New tenants get the in-app worker notification templates + rules for event_type ('appointment.reminder', 'sla.at_risk', 'sla.breached') from TenantService::copy_default_config, but tenants created before that seeding landed lack those rows, so the SLA sweep and appointment-reminder workers never auto-deliver for them. Migration 030 backfills the same rows the new-tenant path produces: for every tenant other than the default source tenant, it copies the three worker templates and re-links each copied rule's template_id to the copied template by (event_type, channel_type), exactly mirroring copy_default_config (src/modules/tenants/service.rs lines 458-502).

Idempotency: both INSERTs are guarded with NOT EXISTS keyed on (tenant_id, event_type, channel_type) for templates and (tenant_id, event_type, template_id) for rules, so a tenant that already has the rows (new-tenant path or a prior run) is untouched and re-running is a no-op. The transactional auth.* / ticket.* email rows from migration 021 are intentionally not backfilled, matching the new-tenant path which also omits them.

Adds tests/notifications_backfill.rs: creates a bare tenant with no rules, runs the backfill, asserts it gains exactly the three worker templates + rules each linked to its own tenant's template, then runs the backfill again and asserts no duplicates. The migration SQL is duplicated in the test because sqlx::test applies all migrations before the body runs.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
style: apply cargo fmt
All checks were successful
E2E (staging) / Playwright against staging (pull_request) Successful in 26s
Check / fmt + clippy + compile + tests (pull_request) Successful in 1m17s
Create release / Create release from merged PR (pull_request) Has been skipped
bd72ab68b0
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
vas2000-work deleted branch feat/notifications-seed-existing-tenants 2026-06-05 23:10:09 +02:00
Sign in to join this conversation.
No reviewers
No labels
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set

Reference
psa-systems/mokosh-server!117
No description provided.