Every system like this grows three or four places where a piece of content appears to exist: a database, a scheduling tool, a client-facing workspace, a chat message. The failure mode is not that they disagree — they will always disagree briefly — it is that nobody can say which one is correct.
The rule here is that one table has one writer:
- The local content database owns the lifecycle. One CLI writes it. Nothing else writes it — not the dashboard, not the chat bot, not the reconciliation job.
- The publishing tool holds a preview draft. It is a projection.
- The client-facing workspace holds the calendar and the report. Also a projection.
- The reconciliation jobs — the webhook receiver, the status poller — read the database and shell out to the one CLI. They never write directly.
When a projection drifts, the fix is always in the same direction: recompute the projection from the source. There is never a negotiation about which surface wins, because that was decided before the code was written.