14 — Reconcile historical outbox events without duplicating old effects
## Objective Account for existing pending events before enabling consumption without blindly replaying effects old controllers may already have executed. ## Evidence and locations Existing app/models/voting_engine/outbox_event.rb only checks delivered_at IS NULL; no old consumer wrote acknowledgements. Therefore an old pending row proves durable event intent, not that broadcasts/integrations never happened. Extend the proposed outbox operational task/service, diagnostics and docs/voting_engine_operations.md. app/services/voting_engine/destroy_meeting_state.rb and old no-effect/import-origin records need explicit handling. ## Changes - Inventory legacy unplanned events by meeting, command, source/version, age and current/remote state. Provide dry-run report and bounded, restartable plan backfill; preserve receipts and semantic payloads. - Current-state UI refreshes are safe to replay. Derive available IDs from immutable receipt input/result, not stale controller assumptions; avoid fabricating deleted recipients or missing request-only context. - Reconcile external effects against persisted remote IDs/provider evidence. Explicitly record verified completed/not-applicable outcomes and reasons. Keep ambiguous effects blocked for scoped operator resolution; do not label unknown work delivered. - Repeated/interrupted backfill cannot create duplicate delivery rows or restart completed effects. Unknown versions remain visible. Do not silently narrow recovery to new events only. - Preserve original event/effect identity for safe retry and audit. Deletion/retention must not remove unresolved ownership needed for remote cleanup. - Supply pre-cutover counts and a disposition for every legacy category. Resolve outstanding strict-guarantee violations before final release, or identify the exact approved exception and owner. ## Acceptance and tests Proposed spec/services/voting_engine/outbox/legacy_reconciliation_spec.rb plus spec/tasks/voting_engine_outbox_spec.rb. Cover absent context/deleted resources, already completed remote effects, verified no-op, ambiguous remote success, restart after partial batch, concurrent retries, unique rows and unchanged receipts. Run bundle exec rspec spec/services/voting_engine/outbox/legacy_reconciliation_spec.rb spec/tasks/voting_engine_outbox_spec.rb. Rehearse dry-run/backfill on a safe database copy; record counts and evidence, not customer payloads. RuboCop changed Ruby. ## Depends on https://task.matda.me/tasks/tsk_2qravp6n9b — version/no-op contract. https://task.matda.me/tasks/tsk_5t6us3yxjk — ledger schema. https://task.matda.me/tasks/tsk_jjv56ryz3b — safe status/retry tooling. Provider reconciliation rules from https://task.matda.me/tasks/tsk_z2yguhkg9b, https://task.matda.me/tasks/tsk_asp6xca5mq, https://task.matda.me/tasks/tsk_pvsm786fz8 and https://task.matda.me/tasks/tsk_zfh3udqh57; report conflict handling from https://task.matda.me/tasks/tsk_43ubu6a7pr. Inventory/dry-run can begin before provider implementation is complete; execution must respect their contracts. ## Questions - Which environment/data copy contains the legacy backlog to rehearse, and who can verify ambiguous historical remote effects from restricted service evidence? - For historical events whose prior email/bookmark/session outcome cannot be established, what explicit disposition is approved? Default is blocked, never blind replay or bulk delivered marking. This is a release decision, not authority to discard work.
Checklist
0 of 0 completeNo checklist items.
- Area
- Kaukus
- Kind
- Operations
- Priority
- Medium
- Task ID
tsk_anwq9m2dfc- Updated