# Jan–June 2026 scheduled-data E2E

Status: **EXISTING-SOURCE-STATE BACKFILL AUTHORIZED; ENGINE SCHEDULING IS NOT
PART OF THIS TEST.** This scope does not relabel or resume the failed synthetic
`LOAD-02` run. Phase 2, reverse delivery, load, and DR remain disabled.

The approved prospective dataset is the one active Timetabler academic term
whose start month is January 2026, end month is June 2026, and exact raw
activity count is 46. The guarded workflow
the `attest-jan-jun-2026-term` action in `.github/workflows/deploy.yml` executes
`deploy/phase1_term_e2e_attest.py` in a PostgreSQL `READ ONLY` transaction. It
uses no API identity, dispatches no Scheduling Engine or Kafka request, writes
no evidence or application row, and never accesses Resource Booking.

The attestation binds the exact deployed Timetabler SHA, hashed default database
identity, Phase 1 flags, publisher/source health, and the exact approved source
watermark. It inventories every activity ID, scheduled state, current
allocation, occurrence weeks, Staff/Location requirement and candidate IDs,
resource-map coverage, and foreign scheduled activities using candidate
resources. Any existing allocation is reported as an overwrite risk. The full
candidate Staff and Location universes are emitted once with canonical hashes.

Static database facts are not an engine-success claim. The audit deliberately
records that actual feasibility is unproven until a separately authorized,
advisory Pre-Schedule request reaches a terminal engine response. A later final
schedule may use exactly one engine-backed request containing the 46 IDs only
when all 46 are unscheduled, no current allocation would be overwritten, every
input/resource-map check passes, the advisory result is feasible, and Resource
Booking independently proves no blocking RB-origin allocation overlaps the
term window on the complete candidate resource universe.

API acknowledgement is never success. A future execution must correlate the
enqueue request to its generated engine request ID and response hash, the
`AppliedEngineResponse` receipt, one atomic Timetabler change set/source
transaction, publisher completion, and the matching Resource Booking receipt.
It must wait for terminal application for every activity before any dependent
step. The terminal evidence must include the exact change-set/source transaction
ID, final watermark, affected activity count, absolute occurrence count/hash,
and Staff/Location allocation hash. One successful 46-activity engine response
is expected to advance the source by one transaction sequence; the exact event
member count cannot be fixed before parsing the response because no-slot items
and variant create/merge/tombstones alter the final member set.

Dispatch the read-only audit only with the exact cross-service source fence:

```text
workflow: Deploy Timetabler BE
phase1_load_action: attest-jan-jun-2026-term
phase1_term_expected_source_watermark: <exact approved integer>
phase1_load_confirm_mutation: false
phase1_load_confirm_operational: false
```

If the watermark, configuration, publisher health, database identity, unique
term selection, or exact 46-row count differs, the workflow fails closed before
any scheduling operation.

The completed source audit established the truthful current facts instead of
the original UI claim: term `26` is `2026-01-05` through `2026-06-26`, has 45
raw active non-JTA activities with IDs `672..716` and identity hash
`1b599dcd8709fcdb29b292b110ef1e5cb011929ba371011ef1ae055c9e408453`,
and all 45 are already scheduled. The historical global 46-activity mirror
milestone was not a term-26 count; no deleted, departed, variant, JTA child, or
template explains a 46th term activity. This 45-vs-46 mismatch remains explicit
and cannot be converted into a scheduling success claim.

## Guarded existing-state backfill

`deploy/phase1_term_projection_backfill.py` emits the authoritative current
state through the ordinary Phase 1 capture/outbox service without changing any
activity, week, Staff, Location, or allocation row and without contacting the
Scheduling Engine. The exact operation is one deterministic, retry-idempotent,
finalized source transaction containing 45 `timetabler.activity.snapshot`
members. It is restricted to source fence 2639, exact term/database/configuration
facts, all 45 scheduled activities, and the reviewed allocation state. Activity
686 and 690 truthfully contain Location allocations and no Staff allocation;
the deployed Resource Booking adapter accepts typed resource arrays as supplied
and never fabricates the missing type.

The read-only `plan` action computes the complete 45-member state and previous
replacement bundle, absolute occurrence count/hash, typed allocation hash, next
aggregate versions, exact-size canonical transport preview, transport margin,
and a canonical plan SHA-256. `execute` requires that exact digest and a separate
outbox-only mutation confirmation. It re-locks the term/activities in ID order,
then locks and rechecks the global source cursor; any domain/configuration/DB/
publisher/fence drift aborts before a write. Finalization validates the complete
single-record envelope below 2 MiB inside the same transaction. The publisher
is polled to the next exact sequence with no backlog/dead letter. `verify` is
read-only and checks the immutable operation identity, member set, plan binding,
publication, liveness, and final source fence.

```text
workflow: Deploy Timetabler BE
phase1_load_action: plan-jan-jun-2026-backfill
phase1_term_expected_source_watermark: 2639
phase1_term_confirm_outbox_mutation: false
phase1_load_confirm_mutation: false
phase1_load_confirm_operational: false

# only after reviewing the emitted plan SHA-256
phase1_load_action: execute-jan-jun-2026-backfill
phase1_term_expected_source_watermark: 2639
phase1_term_backfill_plan_sha256: <exact plan digest>
phase1_term_confirm_outbox_mutation: true
phase1_load_confirm_mutation: false
phase1_load_confirm_operational: false
```

Resource Booking owns receiver-terminal and reconciliation evidence. Timetabler
does not receive RB credentials or read/write an RB database. A successful
backfill proves existing scheduled source state flowed atomically; it is not an
engine schedule E2E and does not make the failed synthetic load run pass.
