Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

10 — Interaction Specification (Scheduler Module)

Interactions of the Scheduled Jobs console, including the polling loop, trigger/remove flows and DLQ actions. Screen refs per 05/06; motion tokens per 00-shared/08.


1. List → Detail drill-down (S1 → S2)

  • Row tap → /admin/scheduler/jobs/:queue/:name (queue+name disambiguate two 0 8 * * * jobs: fee-reminderpayment-reminder, admission-reminder-scanadmission-reminder, scheduler.service.ts:92-110).
  • Detail loads run history (proposed); header keeps C1/C2/C3 identity.
  • Back returns to list preserving scroll + filters.

2. Polling loop (S1)

flowchart LR
    A[Loaded] --> B[Timer 60s] --> C{cache age < 60s?}
    C -->|yes| D[skip request]
    C -->|no| E[GET /scheduler]
    E --> F[render; update badges]
    E -->|error| G[keep last-good + snackbar]
    F --> B
  • Single-flight: one request in flight; new ticks coalesce.
  • Background: timer paused via WidgetsBindingObserver; on resume → immediate staleness check.
  • Status enrichments (proposed) are fetched together with the list, not per row (N+1 avoided).

3. Create schedule (S3)

  • FAB "+ New" → AppBottomSheet (max-width 640 dp); fields per F1.
  • Preset chips (C8) fill the pattern field; regex re-validates on blur (dto:20-24).
  • Submit → POST /scheduler (scheduler.controller.ts:30-35); optimistic row insert with rollback on error; duplicate warn per 08 §F1.

4. Manual trigger (S5, (proposed))

  • Row menu "Run now" → F2 dialog → (proposed) POST /scheduler/:queue/:name/trigger.
  • In-flight: confirm button spinner, dialog not re-openable; success → snackbar + S2 history refresh; the trigger is fire-and-forget server-side (matches job classes, jobs/*.job.ts).
  • Idempotency note displayed in dialog (F2).

5. Remove schedule (S1/S2)

  • "Remove" → F3 dialog (name+pattern+queue) → DELETE /scheduler?queue=&name=&pattern= (scheduler.controller.ts:37-46) → removeRepeatable(jobName, {pattern, tz:'UTC'}) (scheduler.service.ts:188-196). Optimistic removal, rollback + snackbar on failure.

6. DLQ actions (S6, (proposed))

  • Replay → F4 confirm → (proposed) POST /scheduler/dlq/:id/retry; must preserve correlationId/tenantId from the record (dlq.setup.ts:12-21) so IdempotencyService dedup keys stay stable (idempotency.service.ts:12).
  • Delete → F4 confirm → (proposed) DELETE /scheduler/dlq/:id.
  • Status of replay visible in S1/S2 after one poll cycle.

7. Motion & feedback

ActionMotion (00-shared/08)Feedback
Row status changebadge cross-fade m-fastlive region announce
Sheet openm-base slide up
Trigger/removebutton spinner in placesnackbar (success) / inline error
Poll failurenonekeep-last-good + snackbar once per minute
Offlinebanner slide m-baseAppOfflineBanner

8. a11y

  • Badge: icon + text, never color alone (C1).
  • Forms: labels linked, errors in live regions, focus first invalid (F1).
  • Cron text: Semantics(label: "cron pattern, 5 fields") — never spoken as raw five tokens.
  • Dialog focus trap while open (S3/S5/S6 confirms).